X-Git-Url: http://git.droids-corp.org/?a=blobdiff_plain;ds=sidebyside;f=drivers%2Fnet%2Fbnxt%2Ftf_ulp%2Fulp_def_rules.c;h=f421e2ed6ecf083ecc1b4ff41b1b544c362ad06d;hb=1f1f4f53654a12d5b42de4591fb4fb3d04ebd473;hp=4d4f7c4eaff66d6be12a498c9f272f50947c8598;hpb=6eb4ccff3841b8f87ee82170c9cc601a655f246e;p=dpdk.git diff --git a/drivers/net/bnxt/tf_ulp/ulp_def_rules.c b/drivers/net/bnxt/tf_ulp/ulp_def_rules.c index 4d4f7c4eaf..f421e2ed6e 100644 --- a/drivers/net/bnxt/tf_ulp/ulp_def_rules.c +++ b/drivers/net/bnxt/tf_ulp/ulp_def_rules.c @@ -12,8 +12,6 @@ #include "ulp_flow_db.h" #include "ulp_mapper.h" -#define BNXT_ULP_FREE_PARIF_BASE 11 - struct bnxt_ulp_def_param_handler { int32_t (*vfr_func)(struct bnxt_ulp_context *ulp_ctx, struct ulp_tlv_param *param, @@ -83,15 +81,12 @@ ulp_set_parif_in_comp_fld(struct bnxt_ulp_context *ulp_ctx, if (rc) return rc; - if (parif_type == BNXT_ULP_PHY_PORT_PARIF) { + if (parif_type == BNXT_ULP_PHY_PORT_PARIF) idx = BNXT_ULP_CF_IDX_PHY_PORT_PARIF; - } else if (parif_type == BNXT_ULP_DRV_FUNC_PARIF) { + else if (parif_type == BNXT_ULP_DRV_FUNC_PARIF) idx = BNXT_ULP_CF_IDX_DRV_FUNC_PARIF; - /* Parif needs to be reset to a free partition */ - parif += BNXT_ULP_FREE_PARIF_BASE; - } else { + else idx = BNXT_ULP_CF_IDX_VF_FUNC_PARIF; - } ULP_COMP_FLD_IDX_WR(mapper_params, idx, parif); @@ -382,7 +377,7 @@ int32_t ulp_default_flow_destroy(struct rte_eth_dev *eth_dev, uint32_t flow_id) { struct bnxt_ulp_context *ulp_ctx; - int rc; + int rc = 0; ulp_ctx = bnxt_ulp_eth_dev_ptr2_cntxt_get(eth_dev); if (!ulp_ctx) { @@ -390,6 +385,11 @@ ulp_default_flow_destroy(struct rte_eth_dev *eth_dev, uint32_t flow_id) return -EINVAL; } + if (!flow_id) { + BNXT_TF_DBG(DEBUG, "invalid flow id zero\n"); + return rc; + } + rc = ulp_mapper_flow_destroy(ulp_ctx, flow_id, BNXT_ULP_DEFAULT_FLOW_TABLE); if (rc) @@ -397,3 +397,227 @@ ulp_default_flow_destroy(struct rte_eth_dev *eth_dev, uint32_t flow_id) return rc; } + +void +bnxt_ulp_destroy_df_rules(struct bnxt *bp, bool global) +{ + struct bnxt_ulp_df_rule_info *info; + uint8_t port_id; + + if (!BNXT_TRUFLOW_EN(bp) || + BNXT_ETH_DEV_IS_REPRESENTOR(bp->eth_dev)) + return; + + if (!bp->ulp_ctx || !bp->ulp_ctx->cfg_data) + return; + + /* Delete default rules per port */ + if (!global) { + port_id = bp->eth_dev->data->port_id; + info = &bp->ulp_ctx->cfg_data->df_rule_info[port_id]; + if (!info->valid) + return; + + ulp_default_flow_destroy(bp->eth_dev, + info->port_to_app_flow_id); + ulp_default_flow_destroy(bp->eth_dev, + info->app_to_port_flow_id); + memset(info, 0, sizeof(struct bnxt_ulp_df_rule_info)); + return; + } + + /* Delete default rules for all ports */ + for (port_id = 0; port_id < RTE_MAX_ETHPORTS; port_id++) { + info = &bp->ulp_ctx->cfg_data->df_rule_info[port_id]; + if (!info->valid) + continue; + + ulp_default_flow_destroy(bp->eth_dev, + info->port_to_app_flow_id); + ulp_default_flow_destroy(bp->eth_dev, + info->app_to_port_flow_id); + memset(info, 0, sizeof(struct bnxt_ulp_df_rule_info)); + } +} + +static int32_t +bnxt_create_port_app_df_rule(struct bnxt *bp, uint8_t flow_type, + uint32_t *flow_id) +{ + uint16_t port_id = bp->eth_dev->data->port_id; + struct ulp_tlv_param param_list[] = { + { + .type = BNXT_ULP_DF_PARAM_TYPE_DEV_PORT_ID, + .length = 2, + .value = {(port_id >> 8) & 0xff, port_id & 0xff} + }, + { + .type = BNXT_ULP_DF_PARAM_TYPE_LAST, + .length = 0, + .value = {0} + } + }; + + return ulp_default_flow_create(bp->eth_dev, param_list, flow_type, + flow_id); +} + +int32_t +bnxt_ulp_create_df_rules(struct bnxt *bp) +{ + struct bnxt_ulp_df_rule_info *info; + uint8_t port_id; + int rc; + + if (!BNXT_TRUFLOW_EN(bp) || + BNXT_ETH_DEV_IS_REPRESENTOR(bp->eth_dev) || !bp->ulp_ctx) + return 0; + + port_id = bp->eth_dev->data->port_id; + info = &bp->ulp_ctx->cfg_data->df_rule_info[port_id]; + rc = bnxt_create_port_app_df_rule(bp, BNXT_ULP_DF_TPL_PORT_TO_VS, + &info->port_to_app_flow_id); + if (rc) { + BNXT_TF_DBG(ERR, + "Failed to create port to app default rule\n"); + return rc; + } + + bp->tx_cfa_action = 0; + rc = bnxt_create_port_app_df_rule(bp, BNXT_ULP_DF_TPL_VS_TO_PORT, + &info->app_to_port_flow_id); + if (rc) { + BNXT_TF_DBG(ERR, + "Failed to create app to port default rule\n"); + goto port_to_app_free; + } + + rc = ulp_default_flow_db_cfa_action_get(bp->ulp_ctx, + info->app_to_port_flow_id, + &bp->tx_cfa_action); + if (rc) + goto app_to_port_free; + + info->valid = true; + return 0; + +app_to_port_free: + ulp_default_flow_destroy(bp->eth_dev, info->app_to_port_flow_id); +port_to_app_free: + ulp_default_flow_destroy(bp->eth_dev, info->port_to_app_flow_id); + info->valid = false; + + return rc; +} + +static int32_t +bnxt_create_port_vfr_default_rule(struct bnxt *bp, + uint8_t flow_type, + uint16_t vfr_port_id, + uint32_t *flow_id) +{ + struct ulp_tlv_param param_list[] = { + { + .type = BNXT_ULP_DF_PARAM_TYPE_DEV_PORT_ID, + .length = 2, + .value = {(vfr_port_id >> 8) & 0xff, vfr_port_id & 0xff} + }, + { + .type = BNXT_ULP_DF_PARAM_TYPE_LAST, + .length = 0, + .value = {0} + } + }; + return ulp_default_flow_create(bp->eth_dev, param_list, flow_type, + flow_id); +} + +int32_t +bnxt_ulp_create_vfr_default_rules(struct rte_eth_dev *vfr_ethdev) +{ + struct bnxt_ulp_vfr_rule_info *info; + struct bnxt_representor *vfr = vfr_ethdev->data->dev_private; + struct rte_eth_dev *parent_dev = vfr->parent_dev; + struct bnxt *bp = parent_dev->data->dev_private; + uint16_t vfr_port_id = vfr_ethdev->data->port_id; + uint8_t port_id; + int rc; + + if (!bp || !BNXT_TRUFLOW_EN(bp)) + return 0; + + port_id = vfr_ethdev->data->port_id; + info = bnxt_ulp_cntxt_ptr2_ulp_vfr_info_get(bp->ulp_ctx, port_id); + + if (!info) { + BNXT_TF_DBG(ERR, "Failed to get vfr ulp context\n"); + return -EINVAL; + } + + if (info->valid) { + BNXT_TF_DBG(ERR, "VFR already allocated\n"); + return -EINVAL; + } + + memset(info, 0, sizeof(struct bnxt_ulp_vfr_rule_info)); + rc = bnxt_create_port_vfr_default_rule(bp, BNXT_ULP_DF_TPL_VFREP_TO_VF, + vfr_port_id, + &info->rep2vf_flow_id); + if (rc) { + BNXT_TF_DBG(ERR, "Failed to create VFREP to VF default rule\n"); + goto error; + } + rc = bnxt_create_port_vfr_default_rule(bp, BNXT_ULP_DF_TPL_VF_TO_VFREP, + vfr_port_id, + &info->vf2rep_flow_id); + if (rc) { + BNXT_TF_DBG(ERR, "Failed to create VF to VFREP default rule\n"); + goto error; + } + rc = ulp_default_flow_db_cfa_action_get(bp->ulp_ctx, + info->rep2vf_flow_id, + &vfr->vfr_tx_cfa_action); + if (rc) { + BNXT_TF_DBG(ERR, "Failed to get the tx cfa action\n"); + goto error; + } + + /* Update the other details */ + info->valid = true; + info->parent_port_id = bp->eth_dev->data->port_id; + return 0; + +error: + if (info->rep2vf_flow_id) + ulp_default_flow_destroy(bp->eth_dev, info->rep2vf_flow_id); + if (info->vf2rep_flow_id) + ulp_default_flow_destroy(bp->eth_dev, info->vf2rep_flow_id); + return rc; +} + +int32_t +bnxt_ulp_delete_vfr_default_rules(struct bnxt_representor *vfr) +{ + struct bnxt_ulp_vfr_rule_info *info; + struct rte_eth_dev *parent_dev = vfr->parent_dev; + struct bnxt *bp = parent_dev->data->dev_private; + + if (!bp || !BNXT_TRUFLOW_EN(bp)) + return 0; + info = bnxt_ulp_cntxt_ptr2_ulp_vfr_info_get(bp->ulp_ctx, + vfr->dpdk_port_id); + if (!info) { + BNXT_TF_DBG(ERR, "Failed to get vfr ulp context\n"); + return -EINVAL; + } + + if (!info->valid) { + BNXT_TF_DBG(ERR, "VFR already freed\n"); + return -EINVAL; + } + ulp_default_flow_destroy(bp->eth_dev, info->rep2vf_flow_id); + ulp_default_flow_destroy(bp->eth_dev, info->vf2rep_flow_id); + vfr->vfr_tx_cfa_action = 0; + memset(info, 0, sizeof(struct bnxt_ulp_vfr_rule_info)); + return 0; +}