1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright(c) 2019-2020 Broadcom 3 * All rights reserved. 4 */ 5 6 #include "bnxt_tf_common.h" 7 #include "ulp_template_struct.h" 8 #include "ulp_template_db_enum.h" 9 #include "ulp_template_db_field.h" 10 #include "ulp_utils.h" 11 #include "ulp_port_db.h" 12 #include "ulp_flow_db.h" 13 #include "ulp_mapper.h" 14 15 #define BNXT_ULP_FREE_PARIF_BASE 11 16 17 struct bnxt_ulp_def_param_handler { 18 int32_t (*vfr_func)(struct bnxt_ulp_context *ulp_ctx, 19 struct ulp_tlv_param *param, 20 struct bnxt_ulp_mapper_create_parms *mapper_params); 21 }; 22 23 static int32_t 24 ulp_set_svif_in_comp_fld(struct bnxt_ulp_context *ulp_ctx, 25 uint32_t ifindex, uint8_t svif_type, 26 struct bnxt_ulp_mapper_create_parms *mapper_params) 27 { 28 uint16_t svif; 29 uint8_t idx; 30 int rc; 31 32 rc = ulp_port_db_svif_get(ulp_ctx, ifindex, svif_type, &svif); 33 if (rc) 34 return rc; 35 36 if (svif_type == BNXT_ULP_PHY_PORT_SVIF) 37 idx = BNXT_ULP_CF_IDX_PHY_PORT_SVIF; 38 else if (svif_type == BNXT_ULP_DRV_FUNC_SVIF) 39 idx = BNXT_ULP_CF_IDX_DRV_FUNC_SVIF; 40 else 41 idx = BNXT_ULP_CF_IDX_VF_FUNC_SVIF; 42 43 ULP_COMP_FLD_IDX_WR(mapper_params, idx, svif); 44 45 return 0; 46 } 47 48 static int32_t 49 ulp_set_spif_in_comp_fld(struct bnxt_ulp_context *ulp_ctx, 50 uint32_t ifindex, uint8_t spif_type, 51 struct bnxt_ulp_mapper_create_parms *mapper_params) 52 { 53 uint16_t spif; 54 uint8_t idx; 55 int rc; 56 57 rc = ulp_port_db_spif_get(ulp_ctx, ifindex, spif_type, &spif); 58 if (rc) 59 return rc; 60 61 if (spif_type == BNXT_ULP_PHY_PORT_SPIF) 62 idx = BNXT_ULP_CF_IDX_PHY_PORT_SPIF; 63 else if (spif_type == BNXT_ULP_DRV_FUNC_SPIF) 64 idx = BNXT_ULP_CF_IDX_DRV_FUNC_SPIF; 65 else 66 idx = BNXT_ULP_CF_IDX_VF_FUNC_SPIF; 67 68 ULP_COMP_FLD_IDX_WR(mapper_params, idx, spif); 69 70 return 0; 71 } 72 73 static int32_t 74 ulp_set_parif_in_comp_fld(struct bnxt_ulp_context *ulp_ctx, 75 uint32_t ifindex, uint8_t parif_type, 76 struct bnxt_ulp_mapper_create_parms *mapper_params) 77 { 78 uint16_t parif; 79 uint8_t idx; 80 int rc; 81 82 rc = ulp_port_db_parif_get(ulp_ctx, ifindex, parif_type, &parif); 83 if (rc) 84 return rc; 85 86 if (parif_type == BNXT_ULP_PHY_PORT_PARIF) { 87 idx = BNXT_ULP_CF_IDX_PHY_PORT_PARIF; 88 } else if (parif_type == BNXT_ULP_DRV_FUNC_PARIF) { 89 idx = BNXT_ULP_CF_IDX_DRV_FUNC_PARIF; 90 /* Parif needs to be reset to a free partition */ 91 parif += BNXT_ULP_FREE_PARIF_BASE; 92 } else { 93 idx = BNXT_ULP_CF_IDX_VF_FUNC_PARIF; 94 } 95 96 ULP_COMP_FLD_IDX_WR(mapper_params, idx, parif); 97 98 return 0; 99 } 100 101 static int32_t 102 ulp_set_vport_in_comp_fld(struct bnxt_ulp_context *ulp_ctx, uint32_t ifindex, 103 struct bnxt_ulp_mapper_create_parms *mapper_params) 104 { 105 uint16_t vport; 106 int rc; 107 108 rc = ulp_port_db_vport_get(ulp_ctx, ifindex, &vport); 109 if (rc) 110 return rc; 111 112 ULP_COMP_FLD_IDX_WR(mapper_params, BNXT_ULP_CF_IDX_PHY_PORT_VPORT, 113 vport); 114 return 0; 115 } 116 117 static int32_t 118 ulp_set_vnic_in_comp_fld(struct bnxt_ulp_context *ulp_ctx, 119 uint32_t ifindex, uint8_t vnic_type, 120 struct bnxt_ulp_mapper_create_parms *mapper_params) 121 { 122 uint16_t vnic; 123 uint8_t idx; 124 int rc; 125 126 rc = ulp_port_db_default_vnic_get(ulp_ctx, ifindex, vnic_type, &vnic); 127 if (rc) 128 return rc; 129 130 if (vnic_type == BNXT_ULP_DRV_FUNC_VNIC) 131 idx = BNXT_ULP_CF_IDX_DRV_FUNC_VNIC; 132 else 133 idx = BNXT_ULP_CF_IDX_VF_FUNC_VNIC; 134 135 ULP_COMP_FLD_IDX_WR(mapper_params, idx, vnic); 136 137 return 0; 138 } 139 140 static int32_t 141 ulp_set_vlan_in_act_prop(uint16_t port_id, 142 struct bnxt_ulp_mapper_create_parms *mapper_params) 143 { 144 struct ulp_rte_act_prop *act_prop = mapper_params->act_prop; 145 146 if (ULP_BITMAP_ISSET(mapper_params->act->bits, 147 BNXT_ULP_ACTION_BIT_SET_VLAN_VID)) { 148 BNXT_TF_DBG(ERR, 149 "VLAN already set, multiple VLANs unsupported\n"); 150 return BNXT_TF_RC_ERROR; 151 } 152 153 port_id = rte_cpu_to_be_16(port_id); 154 155 ULP_BITMAP_SET(mapper_params->act->bits, 156 BNXT_ULP_ACTION_BIT_SET_VLAN_VID); 157 158 memcpy(&act_prop->act_details[BNXT_ULP_ACT_PROP_IDX_ENCAP_VTAG], 159 &port_id, sizeof(port_id)); 160 161 return 0; 162 } 163 164 static int32_t 165 ulp_set_mark_in_act_prop(uint16_t port_id, 166 struct bnxt_ulp_mapper_create_parms *mapper_params) 167 { 168 if (ULP_BITMAP_ISSET(mapper_params->act->bits, 169 BNXT_ULP_ACTION_BIT_MARK)) { 170 BNXT_TF_DBG(ERR, 171 "MARK already set, multiple MARKs unsupported\n"); 172 return BNXT_TF_RC_ERROR; 173 } 174 175 ULP_COMP_FLD_IDX_WR(mapper_params, BNXT_ULP_CF_IDX_DEV_PORT_ID, 176 port_id); 177 178 return 0; 179 } 180 181 static int32_t 182 ulp_df_dev_port_handler(struct bnxt_ulp_context *ulp_ctx, 183 struct ulp_tlv_param *param, 184 struct bnxt_ulp_mapper_create_parms *mapper_params) 185 { 186 uint16_t port_id; 187 uint32_t ifindex; 188 int rc; 189 190 port_id = param->value[0] | param->value[1]; 191 192 rc = ulp_port_db_dev_port_to_ulp_index(ulp_ctx, port_id, &ifindex); 193 if (rc) { 194 BNXT_TF_DBG(ERR, 195 "Invalid port id\n"); 196 return BNXT_TF_RC_ERROR; 197 } 198 199 /* Set port SVIF */ 200 rc = ulp_set_svif_in_comp_fld(ulp_ctx, ifindex, BNXT_ULP_PHY_PORT_SVIF, 201 mapper_params); 202 if (rc) 203 return rc; 204 205 /* Set DRV Func SVIF */ 206 rc = ulp_set_svif_in_comp_fld(ulp_ctx, ifindex, BNXT_ULP_DRV_FUNC_SVIF, 207 mapper_params); 208 if (rc) 209 return rc; 210 211 /* Set VF Func SVIF */ 212 rc = ulp_set_svif_in_comp_fld(ulp_ctx, ifindex, BNXT_ULP_VF_FUNC_SVIF, 213 mapper_params); 214 if (rc) 215 return rc; 216 217 /* Set port SPIF */ 218 rc = ulp_set_spif_in_comp_fld(ulp_ctx, ifindex, BNXT_ULP_PHY_PORT_SPIF, 219 mapper_params); 220 if (rc) 221 return rc; 222 223 /* Set DRV Func SPIF */ 224 rc = ulp_set_spif_in_comp_fld(ulp_ctx, ifindex, BNXT_ULP_DRV_FUNC_SPIF, 225 mapper_params); 226 if (rc) 227 return rc; 228 229 /* Set VF Func SPIF */ 230 rc = ulp_set_spif_in_comp_fld(ulp_ctx, ifindex, BNXT_ULP_DRV_FUNC_SPIF, 231 mapper_params); 232 if (rc) 233 return rc; 234 235 /* Set port PARIF */ 236 rc = ulp_set_parif_in_comp_fld(ulp_ctx, ifindex, 237 BNXT_ULP_PHY_PORT_PARIF, mapper_params); 238 if (rc) 239 return rc; 240 241 /* Set DRV Func PARIF */ 242 rc = ulp_set_parif_in_comp_fld(ulp_ctx, ifindex, 243 BNXT_ULP_DRV_FUNC_PARIF, mapper_params); 244 if (rc) 245 return rc; 246 247 /* Set VF Func PARIF */ 248 rc = ulp_set_parif_in_comp_fld(ulp_ctx, ifindex, BNXT_ULP_VF_FUNC_PARIF, 249 mapper_params); 250 if (rc) 251 return rc; 252 253 /* Set uplink VNIC */ 254 rc = ulp_set_vnic_in_comp_fld(ulp_ctx, ifindex, true, mapper_params); 255 if (rc) 256 return rc; 257 258 /* Set VF VNIC */ 259 rc = ulp_set_vnic_in_comp_fld(ulp_ctx, ifindex, false, mapper_params); 260 if (rc) 261 return rc; 262 263 /* Set VPORT */ 264 rc = ulp_set_vport_in_comp_fld(ulp_ctx, ifindex, mapper_params); 265 if (rc) 266 return rc; 267 268 /* Set VLAN */ 269 rc = ulp_set_vlan_in_act_prop(port_id, mapper_params); 270 if (rc) 271 return rc; 272 273 /* Set MARK */ 274 rc = ulp_set_mark_in_act_prop(port_id, mapper_params); 275 if (rc) 276 return rc; 277 278 return 0; 279 } 280 281 struct bnxt_ulp_def_param_handler ulp_def_handler_tbl[] = { 282 [BNXT_ULP_DF_PARAM_TYPE_DEV_PORT_ID] = { 283 .vfr_func = ulp_df_dev_port_handler } 284 }; 285 286 /* 287 * Function to create default rules for the following paths 288 * 1) Device PORT to DPDK App 289 * 2) DPDK App to Device PORT 290 * 3) VF Representor to VF 291 * 4) VF to VF Representor 292 * 293 * eth_dev [in] Ptr to rte eth device. 294 * param_list [in] Ptr to a list of parameters (Currently, only DPDK port_id). 295 * ulp_class_tid [in] Class template ID number. 296 * flow_id [out] Ptr to flow identifier. 297 * 298 * Returns 0 on success or negative number on failure. 299 */ 300 int32_t 301 ulp_default_flow_create(struct rte_eth_dev *eth_dev, 302 struct ulp_tlv_param *param_list, 303 uint32_t ulp_class_tid, 304 uint32_t *flow_id) 305 { 306 struct ulp_rte_hdr_field hdr_field[BNXT_ULP_PROTO_HDR_MAX]; 307 uint32_t comp_fld[BNXT_ULP_CF_IDX_LAST]; 308 struct bnxt_ulp_mapper_create_parms mapper_params = { 0 }; 309 struct ulp_rte_act_prop act_prop; 310 struct ulp_rte_act_bitmap act = { 0 }; 311 struct bnxt_ulp_context *ulp_ctx; 312 uint32_t type; 313 int rc; 314 315 memset(&mapper_params, 0, sizeof(mapper_params)); 316 memset(hdr_field, 0, sizeof(hdr_field)); 317 memset(comp_fld, 0, sizeof(comp_fld)); 318 memset(&act_prop, 0, sizeof(act_prop)); 319 320 mapper_params.hdr_field = hdr_field; 321 mapper_params.act = &act; 322 mapper_params.act_prop = &act_prop; 323 mapper_params.comp_fld = comp_fld; 324 325 ulp_ctx = bnxt_ulp_eth_dev_ptr2_cntxt_get(eth_dev); 326 if (!ulp_ctx) { 327 BNXT_TF_DBG(ERR, "ULP context is not initialized. " 328 "Failed to create default flow.\n"); 329 return -EINVAL; 330 } 331 332 type = param_list->type; 333 while (type != BNXT_ULP_DF_PARAM_TYPE_LAST) { 334 if (ulp_def_handler_tbl[type].vfr_func) { 335 rc = ulp_def_handler_tbl[type].vfr_func(ulp_ctx, 336 param_list, 337 &mapper_params); 338 if (rc) { 339 BNXT_TF_DBG(ERR, 340 "Failed to create default flow.\n"); 341 return rc; 342 } 343 } 344 345 param_list++; 346 type = param_list->type; 347 } 348 349 mapper_params.class_tid = ulp_class_tid; 350 351 rc = ulp_mapper_flow_create(ulp_ctx, &mapper_params, flow_id); 352 if (rc) { 353 BNXT_TF_DBG(ERR, "Failed to create default flow.\n"); 354 return rc; 355 } 356 357 return 0; 358 } 359 360 /* 361 * Function to destroy default rules for the following paths 362 * 1) Device PORT to DPDK App 363 * 2) DPDK App to Device PORT 364 * 3) VF Representor to VF 365 * 4) VF to VF Representor 366 * 367 * eth_dev [in] Ptr to rte eth device. 368 * flow_id [in] Flow identifier. 369 * 370 * Returns 0 on success or negative number on failure. 371 */ 372 int32_t 373 ulp_default_flow_destroy(struct rte_eth_dev *eth_dev, uint32_t flow_id) 374 { 375 struct bnxt_ulp_context *ulp_ctx; 376 int rc; 377 378 ulp_ctx = bnxt_ulp_eth_dev_ptr2_cntxt_get(eth_dev); 379 if (!ulp_ctx) { 380 BNXT_TF_DBG(ERR, "ULP context is not initialized\n"); 381 return -EINVAL; 382 } 383 384 rc = ulp_mapper_flow_destroy(ulp_ctx, flow_id, 385 BNXT_ULP_DEFAULT_FLOW_TABLE); 386 if (rc) 387 BNXT_TF_DBG(ERR, "Failed to destroy flow.\n"); 388 389 return rc; 390 } 391