1 /* SPDX-License-Identifier: BSD-3-Clause
2 * Copyright(C) 2021 Marvell.
5 #include "cnxk_ethdev.h"
6 #include <rte_mtr_driver.h>
8 #define NIX_MTR_COUNT_MAX 73 /* 64(leaf) + 8(mid) + 1(top) */
9 #define NIX_MTR_COUNT_PER_FLOW 3 /* 1(leaf) + 1(mid) + 1(top) */
11 #define NIX_BPF_STATS_MASK_ALL \
13 ROC_NIX_BPF_GREEN_PKT_F_PASS | ROC_NIX_BPF_GREEN_OCTS_F_PASS | \
14 ROC_NIX_BPF_GREEN_PKT_F_DROP | \
15 ROC_NIX_BPF_GREEN_OCTS_F_DROP | \
16 ROC_NIX_BPF_YELLOW_PKT_F_PASS | \
17 ROC_NIX_BPF_YELLOW_OCTS_F_PASS | \
18 ROC_NIX_BPF_YELLOW_PKT_F_DROP | \
19 ROC_NIX_BPF_YELLOW_OCTS_F_DROP | \
20 ROC_NIX_BPF_RED_PKT_F_PASS | \
21 ROC_NIX_BPF_RED_OCTS_F_PASS | \
22 ROC_NIX_BPF_RED_PKT_F_DROP | \
23 ROC_NIX_BPF_RED_OCTS_F_DROP \
26 static const enum roc_nix_bpf_level_flag lvl_map[] = {ROC_NIX_BPF_LEVEL_F_LEAF,
27 ROC_NIX_BPF_LEVEL_F_MID,
28 ROC_NIX_BPF_LEVEL_F_TOP};
30 static struct rte_mtr_capabilities mtr_capa = {
31 .n_shared_max = NIX_MTR_COUNT_PER_FLOW,
33 .shared_identical = true,
34 /* .shared_n_flows_per_mtr_max = ,*/
35 .chaining_n_mtrs_per_flow_max = NIX_MTR_COUNT_PER_FLOW,
36 .chaining_use_prev_mtr_color_supported = true,
37 .chaining_use_prev_mtr_color_enforced = true,
38 .meter_rate_max = NIX_BPF_RATE_MAX / 8, /* Bytes per second */
39 .color_aware_srtcm_rfc2697_supported = true,
40 .color_aware_trtcm_rfc2698_supported = true,
41 .color_aware_trtcm_rfc4115_supported = true,
42 .srtcm_rfc2697_byte_mode_supported = true,
43 .srtcm_rfc2697_packet_mode_supported = true,
44 .trtcm_rfc2698_byte_mode_supported = true,
45 .trtcm_rfc2698_packet_mode_supported = true,
46 .trtcm_rfc4115_byte_mode_supported = true,
47 .trtcm_rfc4115_packet_mode_supported = true,
48 .stats_mask = RTE_MTR_STATS_N_PKTS_GREEN | RTE_MTR_STATS_N_PKTS_YELLOW |
49 RTE_MTR_STATS_N_PKTS_RED | RTE_MTR_STATS_N_PKTS_DROPPED |
50 RTE_MTR_STATS_N_BYTES_GREEN |
51 RTE_MTR_STATS_N_BYTES_YELLOW | RTE_MTR_STATS_N_BYTES_RED |
52 RTE_MTR_STATS_N_BYTES_DROPPED};
54 static struct cnxk_meter_node *
55 nix_mtr_find(struct cnxk_eth_dev *dev, uint32_t meter_id)
57 struct cnxk_mtr *fms = &dev->mtr;
58 struct cnxk_meter_node *fm;
60 TAILQ_FOREACH(fm, fms, next)
61 if (meter_id == fm->id)
66 static struct cnxk_mtr_profile_node *
67 nix_mtr_profile_find(struct cnxk_eth_dev *dev, uint32_t profile_id)
69 struct cnxk_mtr_profiles *fmps = &dev->mtr_profiles;
70 struct cnxk_mtr_profile_node *fmp;
72 TAILQ_FOREACH(fmp, fmps, next)
73 if (profile_id == fmp->id)
79 static struct cnxk_mtr_policy_node *
80 nix_mtr_policy_find(struct cnxk_eth_dev *dev, uint32_t meter_policy_id)
82 struct cnxk_mtr_policy *fmps = &dev->mtr_policy;
83 struct cnxk_mtr_policy_node *fmp;
85 TAILQ_FOREACH(fmp, fmps, next)
86 if (meter_policy_id == fmp->id)
92 nix_mtr_profile_validate(struct cnxk_eth_dev *dev, uint32_t profile_id,
93 struct rte_mtr_meter_profile *profile,
94 struct rte_mtr_error *error)
101 return -rte_mtr_error_set(error, EINVAL,
102 RTE_MTR_ERROR_TYPE_METER_PROFILE,
103 NULL, "Meter profile is null.");
105 if (profile_id == UINT32_MAX)
106 return -rte_mtr_error_set(error, EINVAL,
107 RTE_MTR_ERROR_TYPE_METER_PROFILE_ID,
108 NULL, "Meter profile id not valid.");
110 switch (profile->alg) {
111 case RTE_MTR_SRTCM_RFC2697:
112 if (profile->srtcm_rfc2697.cir > mtr_capa.meter_rate_max)
113 rc = -rte_mtr_error_set(error, EINVAL,
114 RTE_MTR_ERROR_TYPE_METER_PROFILE, NULL,
115 "CIR exceeds max meter rate");
117 if (profile->srtcm_rfc2697.cbs > NIX_BPF_BURST_MAX)
118 rc = -rte_mtr_error_set(error, EINVAL,
119 RTE_MTR_ERROR_TYPE_METER_PROFILE, NULL,
120 "CBS exceeds max meter burst size");
122 if (profile->srtcm_rfc2697.ebs > NIX_BPF_BURST_MAX)
123 rc = -rte_mtr_error_set(error, EINVAL,
124 RTE_MTR_ERROR_TYPE_METER_PROFILE, NULL,
125 "EBS exceeds max meter burst size");
128 case RTE_MTR_TRTCM_RFC2698:
129 if (profile->trtcm_rfc2698.cir > mtr_capa.meter_rate_max)
130 rc = -rte_mtr_error_set(error, EINVAL,
131 RTE_MTR_ERROR_TYPE_METER_PROFILE, NULL,
132 "CIR exceeds max meter rate");
134 if (profile->trtcm_rfc2698.pir > mtr_capa.meter_rate_max)
135 rc = -rte_mtr_error_set(error, EINVAL,
136 RTE_MTR_ERROR_TYPE_METER_PROFILE, NULL,
137 "PIR exceeds max meter rate");
139 if (profile->trtcm_rfc2698.cbs > NIX_BPF_BURST_MAX)
140 rc = -rte_mtr_error_set(error, EINVAL,
141 RTE_MTR_ERROR_TYPE_METER_PROFILE, NULL,
142 "CBS exceeds max meter burst size");
144 if (profile->trtcm_rfc2698.pbs > NIX_BPF_BURST_MAX)
145 rc = -rte_mtr_error_set(error, EINVAL,
146 RTE_MTR_ERROR_TYPE_METER_PROFILE, NULL,
147 "PBS exceeds max meter burst size");
150 case RTE_MTR_TRTCM_RFC4115:
151 if ((profile->trtcm_rfc4115.cir + profile->trtcm_rfc4115.eir) >
152 mtr_capa.meter_rate_max)
153 rc = -rte_mtr_error_set(error, EINVAL,
154 RTE_MTR_ERROR_TYPE_METER_PROFILE, NULL,
155 "PIR + EIR exceeds max rate");
157 if (profile->trtcm_rfc4115.cbs > NIX_BPF_BURST_MAX)
158 rc = -rte_mtr_error_set(error, EINVAL,
159 RTE_MTR_ERROR_TYPE_METER_PROFILE, NULL,
160 "CBS exceeds max meter burst size");
162 if (profile->trtcm_rfc4115.ebs > NIX_BPF_BURST_MAX)
163 rc = -rte_mtr_error_set(error, EINVAL,
164 RTE_MTR_ERROR_TYPE_METER_PROFILE, NULL,
165 "PBS exceeds max meter burst size");
169 rc = -rte_mtr_error_set(error, EINVAL,
170 RTE_MTR_ERROR_TYPE_METER_PROFILE, NULL,
179 cnxk_nix_mtr_capabilities_get(struct rte_eth_dev *dev,
180 struct rte_mtr_capabilities *capa,
181 struct rte_mtr_error *error)
183 struct cnxk_eth_dev *eth_dev = cnxk_eth_pmd_priv(dev);
184 uint16_t count[ROC_NIX_BPF_LEVEL_MAX] = {0};
185 uint8_t lvl_mask = ROC_NIX_BPF_LEVEL_F_LEAF | ROC_NIX_BPF_LEVEL_F_MID |
186 ROC_NIX_BPF_LEVEL_F_TOP;
187 struct roc_nix *nix = ð_dev->nix;
194 return -rte_mtr_error_set(error, EINVAL,
195 RTE_MTR_ERROR_TYPE_MTR_PARAMS, NULL,
196 "NULL input parameter");
198 rc = roc_nix_bpf_count_get(nix, lvl_mask, count);
202 for (i = 0; i < ROC_NIX_BPF_LEVEL_MAX; i++)
203 mtr_capa.n_max += count[i];
205 mtr_capa.meter_srtcm_rfc2697_n_max = mtr_capa.n_max;
206 mtr_capa.meter_trtcm_rfc2698_n_max = mtr_capa.n_max;
207 mtr_capa.meter_trtcm_rfc4115_n_max = mtr_capa.n_max;
208 mtr_capa.meter_policy_n_max = mtr_capa.n_max;
215 cnxk_nix_mtr_profile_add(struct rte_eth_dev *eth_dev, uint32_t profile_id,
216 struct rte_mtr_meter_profile *profile,
217 struct rte_mtr_error *error)
219 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
220 struct cnxk_mtr_profiles *fmps = &dev->mtr_profiles;
221 struct cnxk_mtr_profile_node *fmp;
224 /* Check input params. */
225 ret = nix_mtr_profile_validate(dev, profile_id, profile, error);
229 fmp = nix_mtr_profile_find(dev, profile_id);
231 return -rte_mtr_error_set(error, EEXIST,
232 RTE_MTR_ERROR_TYPE_METER_PROFILE_ID,
233 NULL, "Profile already exist");
236 fmp = plt_zmalloc(sizeof(struct cnxk_mtr_profile_node), ROC_ALIGN);
238 return -rte_mtr_error_set(error, ENOMEM,
239 RTE_MTR_ERROR_TYPE_UNSPECIFIED, NULL,
240 "Meter profile memory "
243 fmp->id = profile_id;
244 fmp->profile = *profile;
246 TAILQ_INSERT_TAIL(fmps, fmp, next);
252 cnxk_nix_mtr_profile_delete(struct rte_eth_dev *eth_dev, uint32_t profile_id,
253 struct rte_mtr_error *error)
255 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
256 struct cnxk_mtr_profile_node *fmp;
258 if (profile_id == UINT32_MAX)
259 return -rte_mtr_error_set(error, EINVAL,
260 RTE_MTR_ERROR_TYPE_METER_PROFILE_ID,
261 NULL, "Meter profile id not valid.");
263 fmp = nix_mtr_profile_find(dev, profile_id);
265 return -rte_mtr_error_set(error, ENOENT,
266 RTE_MTR_ERROR_TYPE_METER_PROFILE_ID,
268 "Meter profile is invalid.");
271 return -rte_mtr_error_set(error, EBUSY,
272 RTE_MTR_ERROR_TYPE_METER_PROFILE_ID,
273 NULL, "Meter profile is in use.");
275 TAILQ_REMOVE(&dev->mtr_profiles, fmp, next);
281 cnxk_nix_mtr_policy_validate(struct rte_eth_dev *dev,
282 struct rte_mtr_meter_policy_params *policy,
283 struct rte_mtr_error *error)
285 static const char *const action_color[] = {"Green", "Yellow", "Red"};
286 bool supported[RTE_COLORS] = {false, false, false};
287 const struct rte_flow_action *action;
294 return 0; /* Nothing to be validated */
296 for (i = 0; i < RTE_COLORS; i++) {
297 if (policy->actions[i]) {
298 for (action = policy->actions[i];
299 action->type != RTE_FLOW_ACTION_TYPE_END;
301 if (action->type == RTE_FLOW_ACTION_TYPE_METER)
304 if (action->type == RTE_FLOW_ACTION_TYPE_DROP)
309 "%s action is not valid",
311 return -rte_mtr_error_set(error,
313 RTE_MTR_ERROR_TYPE_METER_POLICY, NULL,
318 sprintf(message, "%s action is null", action_color[i]);
319 return -rte_mtr_error_set(error, EINVAL,
320 RTE_MTR_ERROR_TYPE_METER_POLICY, NULL,
329 cnxk_fill_policy_actions(struct cnxk_mtr_policy_node *fmp,
330 struct rte_mtr_meter_policy_params *policy)
333 const struct rte_flow_action_meter *mtr;
334 const struct rte_flow_action *action;
337 for (i = 0; i < RTE_COLORS; i++) {
338 if (policy->actions[i]) {
339 for (action = policy->actions[i];
340 action->type != RTE_FLOW_ACTION_TYPE_END;
343 RTE_FLOW_ACTION_TYPE_METER) {
344 fmp->actions[i].action_fate =
347 rte_flow_action_meter *)
349 fmp->actions[i].mtr_id = mtr->mtr_id;
352 if (action->type == RTE_FLOW_ACTION_TYPE_DROP) {
353 fmp->actions[i].action_fate =
362 cnxk_nix_mtr_policy_add(struct rte_eth_dev *eth_dev, uint32_t policy_id,
363 struct rte_mtr_meter_policy_params *policy,
364 struct rte_mtr_error *error)
366 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
367 struct cnxk_mtr_policy *fmps = &dev->mtr_policy;
368 struct cnxk_mtr_policy_node *fmp;
371 fmp = nix_mtr_policy_find(dev, policy_id);
373 return -rte_mtr_error_set(error, EEXIST,
374 RTE_MTR_ERROR_TYPE_METER_POLICY_ID,
375 NULL, "Policy already exist");
378 fmp = plt_zmalloc(sizeof(struct cnxk_mtr_policy_node), ROC_ALIGN);
380 return -rte_mtr_error_set(error, ENOMEM,
381 RTE_MTR_ERROR_TYPE_UNSPECIFIED, NULL,
382 "Memory allocation failure");
384 rc = cnxk_nix_mtr_policy_validate(eth_dev, policy, error);
390 cnxk_fill_policy_actions(fmp, policy);
391 TAILQ_INSERT_TAIL(fmps, fmp, next);
400 cnxk_nix_mtr_policy_delete(struct rte_eth_dev *eth_dev, uint32_t policy_id,
401 struct rte_mtr_error *error)
403 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
404 struct cnxk_mtr_policy_node *fmp;
406 fmp = nix_mtr_policy_find(dev, policy_id);
408 return -rte_mtr_error_set(error, ENOENT,
409 RTE_MTR_ERROR_TYPE_METER_POLICY_ID,
410 NULL, "No policy found");
414 return -rte_mtr_error_set(error, EBUSY,
415 RTE_MTR_ERROR_TYPE_METER_POLICY_ID,
416 NULL, "Meter policy is in use.");
418 TAILQ_REMOVE(&dev->mtr_policy, fmp, next);
425 cnxk_nix_mtr_create(struct rte_eth_dev *eth_dev, uint32_t mtr_id,
426 struct rte_mtr_params *params, int shared,
427 struct rte_mtr_error *error)
429 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
430 struct cnxk_mtr_profile_node *profile;
431 struct cnxk_mtr_policy_node *policy;
432 struct cnxk_mtr *fm = &dev->mtr;
433 struct cnxk_meter_node *mtr;
436 RTE_SET_USED(shared);
439 return -rte_mtr_error_set(error, ENOENT,
440 RTE_MTR_ERROR_TYPE_MTR_PARAMS, NULL,
441 "Meter params are invalid.");
443 profile = nix_mtr_profile_find(dev, params->meter_profile_id);
445 return -rte_mtr_error_set(error, ENOENT,
446 RTE_MTR_ERROR_TYPE_METER_PROFILE_ID,
447 ¶ms->meter_profile_id,
448 "Meter profile is invalid.");
450 policy = nix_mtr_policy_find(dev, params->meter_policy_id);
452 return -rte_mtr_error_set(error, ENOENT,
453 RTE_MTR_ERROR_TYPE_METER_POLICY_ID,
454 ¶ms->meter_policy_id,
455 "Meter policy is invalid.");
457 mtr = nix_mtr_find(dev, mtr_id);
459 return -rte_mtr_error_set(error, EEXIST,
460 RTE_MTR_ERROR_TYPE_MTR_ID, NULL,
461 "Meter already exist");
464 mtr = plt_zmalloc(sizeof(struct cnxk_meter_node), ROC_ALIGN);
466 return -rte_mtr_error_set(error, ENOMEM,
467 RTE_MTR_ERROR_TYPE_UNSPECIFIED, NULL,
468 "Meter memory alloc failed.");
472 mtr->profile = profile;
473 mtr->policy = policy;
474 mtr->params = *params;
475 mtr->bpf_id = ROC_NIX_BPF_ID_INVALID;
477 for (i = 0; i < MAX_PRV_MTR_NODES; i++)
478 mtr->prev_id[i] = ROC_NIX_BPF_ID_INVALID;
480 mtr->next_id = ROC_NIX_BPF_ID_INVALID;
481 mtr->is_next = false;
482 mtr->level = ROC_NIX_BPF_LEVEL_IDX_INVALID;
484 if (params->dscp_table) {
485 mtr->params.dscp_table =
486 plt_zmalloc(ROC_NIX_BPF_PRE_COLOR_MAX, ROC_ALIGN);
487 if (mtr->params.dscp_table == NULL) {
489 return -rte_mtr_error_set(error, ENOMEM,
490 RTE_MTR_ERROR_TYPE_UNSPECIFIED,
491 NULL, "Memory alloc failed.");
494 for (i = 0; i < ROC_NIX_BPF_PRE_COLOR_MAX; i++)
495 mtr->params.dscp_table[i] = params->dscp_table[i];
500 TAILQ_INSERT_TAIL(fm, mtr, next);
505 cnxk_nix_mtr_destroy(struct rte_eth_dev *eth_dev, uint32_t mtr_id,
506 struct rte_mtr_error *error)
508 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
509 struct roc_nix_bpf_objs profs = {0};
510 struct cnxk_mtr *fm = &dev->mtr;
511 struct roc_nix *nix = &dev->nix;
512 struct cnxk_meter_node *mtr;
513 struct cnxk_meter_node *mid_mtr;
514 struct cnxk_meter_node *top_mtr;
517 mtr = nix_mtr_find(dev, mtr_id);
519 return -rte_mtr_error_set(error, ENOENT,
520 RTE_MTR_ERROR_TYPE_MTR_ID, &mtr_id,
521 "Meter id is invalid.");
525 return -rte_mtr_error_set(error, EADDRINUSE,
526 RTE_MTR_ERROR_TYPE_MTR_ID, &mtr_id,
530 switch (lvl_map[mtr->level]) {
531 case ROC_NIX_BPF_LEVEL_F_LEAF:
533 rc = roc_nix_bpf_connect(nix, ROC_NIX_BPF_LEVEL_F_LEAF,
535 ROC_NIX_BPF_ID_INVALID);
538 case ROC_NIX_BPF_LEVEL_F_MID:
539 while ((mtr->prev_cnt) + 1) {
541 nix_mtr_find(dev, mtr->prev_id[mtr->prev_cnt]);
542 rc = roc_nix_bpf_connect(nix, ROC_NIX_BPF_LEVEL_F_LEAF,
544 ROC_NIX_BPF_ID_INVALID);
548 rc = roc_nix_bpf_connect(nix, ROC_NIX_BPF_LEVEL_F_MID,
550 ROC_NIX_BPF_ID_INVALID);
553 case ROC_NIX_BPF_LEVEL_F_TOP:
554 while (mtr->prev_cnt) {
556 nix_mtr_find(dev, mtr->prev_id[mtr->prev_cnt]);
557 rc = roc_nix_bpf_connect(nix, ROC_NIX_BPF_LEVEL_F_MID,
559 ROC_NIX_BPF_ID_INVALID);
564 return -rte_mtr_error_set(error, EINVAL,
565 RTE_MTR_ERROR_TYPE_MTR_ID, NULL,
566 "Invalid meter level");
572 profs.level = mtr->level;
574 profs.ids[0] = mtr->bpf_id;
575 rc = roc_nix_bpf_free(nix, &profs, 1);
579 mtr->policy->ref_cnt--;
580 mtr->profile->ref_cnt--;
581 TAILQ_REMOVE(fm, mtr, next);
582 plt_free(mtr->params.dscp_table);
590 cnxk_nix_mtr_enable(struct rte_eth_dev *eth_dev, uint32_t mtr_id,
591 struct rte_mtr_error *error)
593 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
594 struct roc_nix *nix = &dev->nix;
595 struct cnxk_meter_node *mtr;
596 struct roc_nix_rq *rq;
600 mtr = nix_mtr_find(dev, mtr_id);
602 return -rte_mtr_error_set(error, ENOENT,
603 RTE_MTR_ERROR_TYPE_MTR_ID, NULL,
604 "Meter id is invalid.");
610 for (i = 0; i < mtr->rq_num; i++) {
611 rq = &dev->rqs[mtr->rq_id[i]];
612 rc |= roc_nix_bpf_ena_dis(nix, mtr->bpf_id, rq, true);
619 cnxk_nix_mtr_disable(struct rte_eth_dev *eth_dev, uint32_t mtr_id,
620 struct rte_mtr_error *error)
622 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
623 struct roc_nix *nix = &dev->nix;
624 struct cnxk_meter_node *mtr;
625 struct roc_nix_rq *rq;
629 mtr = nix_mtr_find(dev, mtr_id);
631 return -rte_mtr_error_set(error, ENOENT,
632 RTE_MTR_ERROR_TYPE_MTR_ID, NULL,
633 "Meter id is invalid.");
639 for (i = 0; i < mtr->rq_num; i++) {
640 rq = &dev->rqs[mtr->rq_id[i]];
641 rc |= roc_nix_bpf_ena_dis(nix, mtr->bpf_id, rq, false);
648 cnxk_nix_mtr_dscp_table_update(struct rte_eth_dev *eth_dev, uint32_t mtr_id,
649 enum rte_color *dscp_table,
650 struct rte_mtr_error *error)
652 enum roc_nix_bpf_color nix_dscp_tbl[ROC_NIX_BPF_PRE_COLOR_MAX];
653 enum roc_nix_bpf_color color_map[] = {ROC_NIX_BPF_COLOR_GREEN,
654 ROC_NIX_BPF_COLOR_YELLOW,
655 ROC_NIX_BPF_COLOR_RED};
656 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
657 struct roc_nix_bpf_precolor table;
658 struct roc_nix *nix = &dev->nix;
659 struct cnxk_meter_node *mtr;
662 mtr = nix_mtr_find(dev, mtr_id);
664 return -rte_mtr_error_set(error, ENOENT,
665 RTE_MTR_ERROR_TYPE_MTR_ID, NULL,
666 "Meter object not found");
670 for (i = 0; i < ROC_NIX_BPF_PRE_COLOR_MAX; i++)
671 nix_dscp_tbl[i] = ROC_NIX_BPF_COLOR_GREEN;
673 for (i = 0; i < ROC_NIX_BPF_PRE_COLOR_MAX; i++)
674 nix_dscp_tbl[i] = color_map[dscp_table[i]];
677 table.count = ROC_NIX_BPF_PRE_COLOR_MAX;
678 table.mode = ROC_NIX_BPF_PC_MODE_DSCP_OUTER;
679 for (i = 0; i < ROC_NIX_BPF_PRE_COLOR_MAX; i++)
680 table.color[i] = nix_dscp_tbl[i];
682 rc = roc_nix_bpf_pre_color_tbl_setup(nix, mtr->bpf_id,
683 lvl_map[mtr->level], &table);
685 rte_mtr_error_set(error, rc, RTE_MTR_ERROR_TYPE_UNSPECIFIED,
690 for (i = 0; i < ROC_NIX_BPF_PRE_COLOR_MAX; i++)
691 dev->precolor_tbl[i] = nix_dscp_tbl[i];
698 cnxk_nix_mtr_stats_update(struct rte_eth_dev *eth_dev, uint32_t mtr_id,
699 uint64_t stats_mask, struct rte_mtr_error *error)
701 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
702 struct cnxk_meter_node *mtr;
705 return -rte_mtr_error_set(error, EINVAL,
706 RTE_MTR_ERROR_TYPE_MTR_PARAMS, NULL,
707 "no bit is set to stats mask");
709 mtr = nix_mtr_find(dev, mtr_id);
711 return -rte_mtr_error_set(error, ENOENT,
712 RTE_MTR_ERROR_TYPE_MTR_ID, NULL,
713 "Meter object not found");
716 mtr->params.stats_mask = stats_mask;
721 cnxk_nix_mtr_stats_read(struct rte_eth_dev *eth_dev, uint32_t mtr_id,
722 struct rte_mtr_stats *stats, uint64_t *stats_mask,
723 int clear, struct rte_mtr_error *error)
725 uint8_t yellow_pkt_pass, yellow_octs_pass, yellow_pkt_drop;
726 uint8_t green_octs_drop, yellow_octs_drop, red_octs_drop;
727 uint8_t green_pkt_pass, green_octs_pass, green_pkt_drop;
728 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
729 uint8_t red_pkt_pass, red_octs_pass, red_pkt_drop;
730 uint64_t bpf_stats[ROC_NIX_BPF_STATS_MAX] = {0};
731 uint64_t mask = NIX_BPF_STATS_MASK_ALL;
732 struct roc_nix *nix = &dev->nix;
733 struct cnxk_meter_node *mtr;
737 return -rte_mtr_error_set(error, EINVAL,
738 RTE_MTR_ERROR_TYPE_MTR_PARAMS, NULL,
739 "stats pointer is NULL");
741 mtr = nix_mtr_find(dev, mtr_id);
743 return -rte_mtr_error_set(error, ENOENT,
744 RTE_MTR_ERROR_TYPE_MTR_ID, NULL,
745 "Meter object not found");
748 rc = roc_nix_bpf_stats_read(nix, mtr->bpf_id, mask, lvl_map[mtr->level],
751 rte_mtr_error_set(error, rc, RTE_MTR_ERROR_TYPE_UNSPECIFIED,
756 green_pkt_pass = roc_nix_bpf_stats_to_idx(ROC_NIX_BPF_GREEN_PKT_F_PASS);
758 roc_nix_bpf_stats_to_idx(ROC_NIX_BPF_GREEN_OCTS_F_PASS);
759 green_pkt_drop = roc_nix_bpf_stats_to_idx(ROC_NIX_BPF_GREEN_PKT_F_DROP);
761 roc_nix_bpf_stats_to_idx(ROC_NIX_BPF_GREEN_OCTS_F_DROP);
763 roc_nix_bpf_stats_to_idx(ROC_NIX_BPF_YELLOW_PKT_F_PASS);
765 roc_nix_bpf_stats_to_idx(ROC_NIX_BPF_YELLOW_OCTS_F_PASS);
767 roc_nix_bpf_stats_to_idx(ROC_NIX_BPF_YELLOW_PKT_F_DROP);
769 roc_nix_bpf_stats_to_idx(ROC_NIX_BPF_YELLOW_OCTS_F_DROP);
770 red_pkt_pass = roc_nix_bpf_stats_to_idx(ROC_NIX_BPF_RED_PKT_F_PASS);
771 red_octs_pass = roc_nix_bpf_stats_to_idx(ROC_NIX_BPF_RED_OCTS_F_PASS);
772 red_pkt_drop = roc_nix_bpf_stats_to_idx(ROC_NIX_BPF_RED_PKT_F_DROP);
773 red_octs_drop = roc_nix_bpf_stats_to_idx(ROC_NIX_BPF_RED_OCTS_F_DROP);
775 if (mtr->params.stats_mask & RTE_MTR_STATS_N_PKTS_GREEN)
776 stats->n_pkts[RTE_COLOR_GREEN] = bpf_stats[green_pkt_pass];
778 if (mtr->params.stats_mask & RTE_MTR_STATS_N_PKTS_YELLOW)
779 stats->n_pkts[RTE_COLOR_YELLOW] = bpf_stats[yellow_pkt_pass];
781 if (mtr->params.stats_mask & RTE_MTR_STATS_N_PKTS_RED)
782 stats->n_pkts[RTE_COLOR_RED] = bpf_stats[red_pkt_pass];
784 if (mtr->params.stats_mask & RTE_MTR_STATS_N_BYTES_GREEN)
785 stats->n_bytes[RTE_COLOR_GREEN] = bpf_stats[green_octs_pass];
787 if (mtr->params.stats_mask & RTE_MTR_STATS_N_BYTES_YELLOW)
788 stats->n_bytes[RTE_COLOR_YELLOW] = bpf_stats[yellow_octs_pass];
790 if (mtr->params.stats_mask & RTE_MTR_STATS_N_BYTES_RED)
791 stats->n_bytes[RTE_COLOR_RED] = bpf_stats[red_octs_pass];
793 if (mtr->params.stats_mask & RTE_MTR_STATS_N_PKTS_DROPPED)
794 stats->n_pkts_dropped = bpf_stats[green_pkt_drop] +
795 bpf_stats[yellow_pkt_drop] +
796 bpf_stats[red_pkt_drop];
798 if (mtr->params.stats_mask & RTE_MTR_STATS_N_BYTES_DROPPED)
799 stats->n_bytes_dropped = bpf_stats[green_octs_drop] +
800 bpf_stats[yellow_octs_drop] +
801 bpf_stats[red_octs_drop];
804 *stats_mask = mtr->params.stats_mask;
807 rc = roc_nix_bpf_stats_reset(nix, mtr->bpf_id, mask,
808 lvl_map[mtr->level]);
810 rte_mtr_error_set(error, rc,
811 RTE_MTR_ERROR_TYPE_UNSPECIFIED, NULL,
821 const struct rte_mtr_ops nix_mtr_ops = {
822 .capabilities_get = cnxk_nix_mtr_capabilities_get,
823 .meter_profile_add = cnxk_nix_mtr_profile_add,
824 .meter_profile_delete = cnxk_nix_mtr_profile_delete,
825 .meter_policy_validate = cnxk_nix_mtr_policy_validate,
826 .meter_policy_add = cnxk_nix_mtr_policy_add,
827 .meter_policy_delete = cnxk_nix_mtr_policy_delete,
828 .create = cnxk_nix_mtr_create,
829 .destroy = cnxk_nix_mtr_destroy,
830 .meter_enable = cnxk_nix_mtr_enable,
831 .meter_disable = cnxk_nix_mtr_disable,
832 .meter_dscp_table_update = cnxk_nix_mtr_dscp_table_update,
833 .stats_update = cnxk_nix_mtr_stats_update,
834 .stats_read = cnxk_nix_mtr_stats_read,
838 cnxk_nix_mtr_ops_get(struct rte_eth_dev *dev, void *ops)
842 *(const void **)ops = &nix_mtr_ops;
847 nix_mtr_validate(struct rte_eth_dev *eth_dev, uint32_t id)
849 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
850 struct cnxk_mtr_profile_node *profile;
851 struct cnxk_mtr_policy_node *policy;
852 struct cnxk_meter_node *mtr;
854 mtr = nix_mtr_find(dev, id);
858 profile = nix_mtr_profile_find(dev, mtr->params.meter_profile_id);
862 policy = nix_mtr_policy_find(dev, mtr->params.meter_policy_id);
870 nix_mtr_policy_act_get(struct rte_eth_dev *eth_dev, uint32_t id,
871 struct cnxk_mtr_policy_node **policy_act)
873 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
874 struct cnxk_mtr_policy_node *policy;
875 struct cnxk_meter_node *mtr;
877 mtr = nix_mtr_find(dev, id);
881 policy = nix_mtr_policy_find(dev, mtr->params.meter_policy_id);
885 *policy_act = policy;
891 nix_mtr_rq_update(struct rte_eth_dev *eth_dev, uint32_t id, uint32_t queue_num,
892 const uint16_t *queue)
894 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
895 struct cnxk_meter_node *mtr;
898 mtr = nix_mtr_find(dev, id);
902 mtr->rq_id = plt_zmalloc(queue_num * sizeof(uint32_t), ROC_ALIGN);
903 if (mtr->rq_id == NULL)
906 mtr->rq_num = queue_num;
907 for (i = 0; i < queue_num; i++)
908 mtr->rq_id[i] = queue[i];
914 nix_mtr_chain_reset(struct rte_eth_dev *eth_dev, uint32_t cur_id)
916 struct cnxk_meter_node *mtr[ROC_NIX_BPF_LEVEL_MAX] = {0};
917 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
918 uint32_t mtr_id = cur_id;
921 for (i = 0; i < ROC_NIX_BPF_LEVEL_MAX; i++) {
922 mtr[i] = nix_mtr_find(dev, mtr_id);
924 mtr_id = mtr[i]->next_id;
926 for (i = 0; i < ROC_NIX_BPF_LEVEL_MAX; i++) {
928 for (j = 0; j < MAX_PRV_MTR_NODES; j++)
929 mtr[i]->prev_id[i] = ROC_NIX_BPF_ID_INVALID;
930 mtr[i]->level = ROC_NIX_BPF_LEVEL_IDX_INVALID;
931 mtr[i]->next_id = ROC_NIX_BPF_ID_INVALID;
932 mtr[i]->is_next = false;
933 mtr[i]->prev_cnt = 0;
940 nix_mtr_chain_update(struct rte_eth_dev *eth_dev, uint32_t cur_id,
941 uint32_t prev_id, uint32_t next_id)
943 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
944 struct cnxk_meter_node *mtr;
946 mtr = nix_mtr_find(dev, cur_id);
950 switch (lvl_map[mtr->level]) {
951 case ROC_NIX_BPF_LEVEL_F_LEAF:
952 mtr->prev_id[mtr->prev_cnt] = ROC_NIX_BPF_ID_INVALID;
953 mtr->next_id = next_id;
956 case ROC_NIX_BPF_LEVEL_F_MID:
957 mtr->prev_id[mtr->prev_cnt] = prev_id;
958 mtr->next_id = next_id;
961 case ROC_NIX_BPF_LEVEL_F_TOP:
962 mtr->prev_id[mtr->prev_cnt] = prev_id;
963 mtr->next_id = ROC_NIX_BPF_ID_INVALID;
964 mtr->is_next = false;
967 plt_err("Invalid meter level");
974 struct cnxk_meter_node *
975 nix_get_mtr(struct rte_eth_dev *eth_dev, uint32_t id)
977 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
978 struct cnxk_meter_node *mtr;
980 mtr = nix_mtr_find(dev, id);
988 nix_mtr_level_update(struct rte_eth_dev *eth_dev, uint32_t id, uint32_t level)
990 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
991 struct cnxk_meter_node *mtr;
993 mtr = nix_mtr_find(dev, id);
1002 nix_mtr_config_map(struct cnxk_meter_node *mtr, struct roc_nix_bpf_cfg *cfg)
1004 enum roc_nix_bpf_algo alg_map[] = {
1005 ROC_NIX_BPF_ALGO_NONE, ROC_NIX_BPF_ALGO_2697,
1006 ROC_NIX_BPF_ALGO_2698, ROC_NIX_BPF_ALGO_4115};
1007 struct cnxk_mtr_profile_node *profile = mtr->profile;
1008 struct cnxk_mtr_policy_node *policy = mtr->policy;
1010 cfg->alg = alg_map[profile->profile.alg];
1011 cfg->lmode = profile->profile.packet_mode;
1014 case ROC_NIX_BPF_ALGO_2697:
1015 cfg->algo2697.cir = profile->profile.srtcm_rfc2697.cir * 8;
1016 cfg->algo2697.cbs = profile->profile.srtcm_rfc2697.cbs;
1017 cfg->algo2697.ebs = profile->profile.srtcm_rfc2697.ebs;
1019 case ROC_NIX_BPF_ALGO_2698:
1020 cfg->algo2698.cir = profile->profile.trtcm_rfc2698.cir * 8;
1021 cfg->algo2698.pir = profile->profile.trtcm_rfc2698.pir * 8;
1022 cfg->algo2698.cbs = profile->profile.trtcm_rfc2698.cbs;
1023 cfg->algo2698.pbs = profile->profile.trtcm_rfc2698.pbs;
1025 case ROC_NIX_BPF_ALGO_4115:
1026 cfg->algo4115.cir = profile->profile.trtcm_rfc4115.cir * 8;
1027 cfg->algo4115.eir = profile->profile.trtcm_rfc4115.eir * 8;
1028 cfg->algo4115.cbs = profile->profile.trtcm_rfc4115.cbs;
1029 cfg->algo4115.ebs = profile->profile.trtcm_rfc4115.ebs;
1035 cfg->action[ROC_NIX_BPF_COLOR_GREEN] = ROC_NIX_BPF_ACTION_PASS;
1036 cfg->action[ROC_NIX_BPF_COLOR_YELLOW] = ROC_NIX_BPF_ACTION_PASS;
1037 cfg->action[ROC_NIX_BPF_COLOR_RED] = ROC_NIX_BPF_ACTION_PASS;
1039 if (policy->actions[RTE_COLOR_GREEN].action_fate ==
1040 RTE_FLOW_ACTION_TYPE_DROP)
1041 cfg->action[ROC_NIX_BPF_COLOR_GREEN] = ROC_NIX_BPF_ACTION_DROP;
1043 if (policy->actions[RTE_COLOR_YELLOW].action_fate ==
1044 RTE_FLOW_ACTION_TYPE_DROP)
1045 cfg->action[ROC_NIX_BPF_COLOR_YELLOW] = ROC_NIX_BPF_ACTION_DROP;
1047 if (policy->actions[RTE_COLOR_RED].action_fate ==
1048 RTE_FLOW_ACTION_TYPE_DROP)
1049 cfg->action[ROC_NIX_BPF_COLOR_RED] = ROC_NIX_BPF_ACTION_DROP;
1053 nix_dscp_table_map(struct cnxk_meter_node *mtr,
1054 struct roc_nix_bpf_precolor *tbl)
1056 enum roc_nix_bpf_color color_map[] = {ROC_NIX_BPF_COLOR_GREEN,
1057 ROC_NIX_BPF_COLOR_YELLOW,
1058 ROC_NIX_BPF_COLOR_RED};
1061 tbl->count = ROC_NIX_BPF_PRE_COLOR_MAX;
1062 tbl->mode = ROC_NIX_BPF_PC_MODE_DSCP_OUTER;
1064 for (i = 0; i < ROC_NIX_BPF_PRE_COLOR_MAX; i++)
1065 tbl->color[i] = ROC_NIX_BPF_COLOR_GREEN;
1067 if (mtr->params.dscp_table) {
1068 for (i = 0; i < ROC_NIX_BPF_PRE_COLOR_MAX; i++)
1069 tbl->color[i] = color_map[mtr->params.dscp_table[i]];
1074 nix_mtr_destroy(struct rte_eth_dev *eth_dev, uint32_t id,
1075 struct rte_mtr_error *error)
1077 return cnxk_nix_mtr_destroy(eth_dev, id, error);
1081 nix_mtr_connect(struct rte_eth_dev *eth_dev, uint32_t id)
1083 enum roc_nix_bpf_level_flag lvl_flag = ROC_NIX_BPF_LEVEL_IDX_INVALID;
1084 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
1085 struct cnxk_meter_node *base_mtr, *next_mtr;
1086 struct roc_nix *nix = &dev->nix;
1087 uint32_t cur_mtr_id = id;
1090 for (i = 0; i < ROC_NIX_BPF_LEVEL_MAX; i++) {
1091 base_mtr = nix_mtr_find(dev, cur_mtr_id);
1093 lvl_flag = lvl_map[base_mtr->level];
1094 if (base_mtr->is_next) {
1095 next_mtr = nix_mtr_find(dev, base_mtr->next_id);
1097 if (!base_mtr->is_used) {
1098 rc = roc_nix_bpf_connect(nix,
1106 cur_mtr_id = base_mtr->next_id;
1114 nix_mtr_configure(struct rte_eth_dev *eth_dev, uint32_t id)
1116 struct cnxk_meter_node *mtr[ROC_NIX_BPF_LEVEL_MAX] = {0};
1117 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
1118 struct roc_nix_bpf_objs profs[ROC_NIX_BPF_LEVEL_MAX];
1119 uint8_t idx0 = ROC_NIX_BPF_LEVEL_IDX_INVALID;
1120 uint8_t idx1 = ROC_NIX_BPF_LEVEL_IDX_INVALID;
1121 uint8_t idx2 = ROC_NIX_BPF_LEVEL_IDX_INVALID;
1122 uint16_t per_lvl_cnt[ROC_NIX_BPF_LEVEL_MAX];
1123 int num_mtr[ROC_NIX_BPF_LEVEL_MAX] = {0};
1124 struct roc_nix *nix = &dev->nix;
1125 struct roc_nix_bpf_precolor tbl;
1126 struct roc_nix_bpf_cfg cfg;
1127 struct roc_nix_rq *rq;
1133 mtr[0] = nix_mtr_find(dev, id);
1138 idx0 = roc_nix_bpf_level_to_idx(lvl_map[mtr[0]->level]);
1139 if (idx0 == ROC_NIX_BPF_LEVEL_IDX_INVALID)
1142 lvl_mask = ROC_NIX_BPF_LEVEL_F_LEAF;
1143 if (mtr[0]->is_used)
1144 per_lvl_cnt[idx0] = 0;
1146 per_lvl_cnt[idx0] = 1;
1148 if (mtr[0]->is_next) {
1149 mtr[1] = nix_mtr_find(dev, mtr[0]->next_id);
1153 idx1 = roc_nix_bpf_level_to_idx(lvl_map[mtr[1]->level]);
1154 if (idx1 == ROC_NIX_BPF_LEVEL_IDX_INVALID)
1157 lvl_mask |= ROC_NIX_BPF_LEVEL_F_MID;
1158 if (mtr[1]->is_used)
1159 per_lvl_cnt[idx1] = 0;
1161 per_lvl_cnt[idx1] = 1;
1164 if (mtr[1] && mtr[1]->is_next) {
1165 mtr[2] = nix_mtr_find(dev, mtr[1]->next_id);
1170 idx2 = roc_nix_bpf_level_to_idx(lvl_map[mtr[2]->level]);
1171 if (idx2 == ROC_NIX_BPF_LEVEL_IDX_INVALID)
1174 lvl_mask |= ROC_NIX_BPF_LEVEL_F_TOP;
1175 if (mtr[2]->is_used)
1176 per_lvl_cnt[idx2] = 0;
1178 per_lvl_cnt[idx2] = 1;
1181 rc = roc_nix_bpf_alloc(nix, lvl_mask, per_lvl_cnt, profs);
1184 if (mtr[0]->bpf_id == ROC_NIX_BPF_ID_INVALID)
1185 mtr[0]->bpf_id = profs[idx0].ids[0];
1188 if (mtr[0]->is_next && idx1 != ROC_NIX_BPF_LEVEL_IDX_INVALID)
1189 if (mtr[1]->bpf_id == ROC_NIX_BPF_ID_INVALID)
1190 mtr[1]->bpf_id = profs[idx1].ids[0];
1193 if (mtr[1]->is_next && idx2 != ROC_NIX_BPF_LEVEL_IDX_INVALID)
1194 if (mtr[2]->bpf_id == ROC_NIX_BPF_ID_INVALID)
1195 mtr[2]->bpf_id = profs[idx2].ids[0];
1197 for (i = 0; i < ROC_NIX_BPF_LEVEL_MAX; i++) {
1199 if (!mtr[i]->is_used) {
1200 memset(&cfg, 0, sizeof(struct roc_nix_bpf_cfg));
1201 nix_mtr_config_map(mtr[i], &cfg);
1202 rc = roc_nix_bpf_config(nix, mtr[i]->bpf_id,
1203 lvl_map[mtr[i]->level],
1207 sizeof(struct roc_nix_bpf_precolor));
1208 nix_dscp_table_map(mtr[i], &tbl);
1209 rc = roc_nix_bpf_pre_color_tbl_setup(nix,
1210 mtr[i]->bpf_id, lvl_map[mtr[i]->level],
1213 if (mtr[i]->params.meter_enable) {
1214 for (j = 0; j < mtr[i]->rq_num; j++) {
1215 rq = &dev->rqs[mtr[i]->rq_id
1217 rc = roc_nix_bpf_ena_dis(nix,
1230 nix_mtr_color_action_validate(struct rte_eth_dev *eth_dev, uint32_t id,
1231 uint32_t *prev_id, uint32_t *next_id,
1232 struct cnxk_mtr_policy_node *policy,
1235 uint32_t action_fate_red = policy->actions[RTE_COLOR_RED].action_fate;
1236 uint32_t action_fate_green =
1237 policy->actions[RTE_COLOR_GREEN].action_fate;
1238 uint32_t action_fate_yellow =
1239 policy->actions[RTE_COLOR_YELLOW].action_fate;
1240 uint32_t cur_mtr_id = *next_id;
1241 uint32_t next_mtr_id = 0xffff;
1242 uint32_t prev_mtr_id = 0xffff;
1243 struct cnxk_meter_node *mtr;
1245 if (action_fate_green == RTE_FLOW_ACTION_TYPE_METER)
1246 next_mtr_id = policy->actions[RTE_COLOR_GREEN].mtr_id;
1248 if (action_fate_yellow == RTE_FLOW_ACTION_TYPE_METER)
1249 next_mtr_id = policy->actions[RTE_COLOR_YELLOW].mtr_id;
1251 if (action_fate_red == RTE_FLOW_ACTION_TYPE_METER)
1252 next_mtr_id = policy->actions[RTE_COLOR_RED].mtr_id;
1254 if (next_mtr_id != 0xffff) {
1255 switch (*tree_level) {
1257 mtr = nix_get_mtr(eth_dev, cur_mtr_id);
1258 if (mtr->level == ROC_NIX_BPF_LEVEL_IDX_INVALID) {
1259 nix_mtr_level_update(eth_dev, cur_mtr_id, 0);
1260 nix_mtr_chain_update(eth_dev, cur_mtr_id, -1,
1263 if (mtr->level == 0)
1264 mtr->is_used = true;
1269 *next_id = next_mtr_id;
1272 mtr = nix_get_mtr(eth_dev, cur_mtr_id);
1273 if (mtr->level == ROC_NIX_BPF_LEVEL_IDX_INVALID) {
1274 nix_mtr_level_update(eth_dev, cur_mtr_id, 1);
1276 nix_mtr_chain_update(eth_dev, cur_mtr_id,
1277 prev_mtr_id, next_mtr_id);
1279 if (mtr->level == 1) {
1282 nix_mtr_chain_update(eth_dev,
1283 cur_mtr_id, prev_mtr_id,
1286 mtr->is_used = true;
1292 *next_id = next_mtr_id;
1293 *prev_id = cur_mtr_id;
1296 nix_mtr_chain_reset(eth_dev, id);
1300 switch (*tree_level) {
1302 mtr = nix_get_mtr(eth_dev, cur_mtr_id);
1303 if (mtr->level == ROC_NIX_BPF_LEVEL_IDX_INVALID) {
1304 nix_mtr_level_update(eth_dev, cur_mtr_id, 0);
1306 if (mtr->level == 0)
1307 mtr->is_used = true;
1313 mtr = nix_get_mtr(eth_dev, cur_mtr_id);
1314 if (mtr->level == ROC_NIX_BPF_LEVEL_IDX_INVALID) {
1315 nix_mtr_level_update(eth_dev, cur_mtr_id, 1);
1317 nix_mtr_chain_update(eth_dev, cur_mtr_id,
1320 if (mtr->level == 1) {
1323 nix_mtr_chain_update(eth_dev,
1326 mtr->is_used = true;
1333 mtr = nix_get_mtr(eth_dev, cur_mtr_id);
1334 if (mtr->level == ROC_NIX_BPF_LEVEL_IDX_INVALID) {
1335 nix_mtr_level_update(eth_dev, cur_mtr_id, 2);
1336 prev_mtr_id = *prev_id;
1337 nix_mtr_chain_update(eth_dev, cur_mtr_id,
1340 if (mtr->level == 2) {
1342 prev_mtr_id = *prev_id;
1343 nix_mtr_chain_update(eth_dev,
1346 mtr->is_used = true;
1360 nix_mtr_capabilities_init(struct rte_eth_dev *eth_dev)
1362 struct rte_mtr_capabilities capa;
1363 struct rte_mtr_error error;
1365 return cnxk_nix_mtr_capabilities_get(eth_dev, &capa, &error);