mim.c (32606B)
1 /* 2 * 3 * This license is set out in https://raw.githubusercontent.com/Broadcom-Network-Switching-Software/OpenBCM/master/Legal/LICENSE file. 4 * 5 * Copyright 2007-2019 Broadcom Inc. All rights reserved. 6 * 7 * File: mim.c 8 * Purpose: Manages MiM functions for triumph3 9 */ 10 11 #include <soc/defs.h> 12 #include <sal/core/libc.h> 13 14 #if defined(BCM_TRIUMPH3_SUPPORT) && defined(INCLUDE_L3) 15 16 #include <soc/drv.h> 17 #include <soc/hash.h> 18 #include <soc/mem.h> 19 #include <soc/util.h> 20 #include <soc/debug.h> 21 #include <soc/triumph.h> 22 23 #include <bcm/error.h> 24 #include <bcm/mim.h> 25 26 #include <bcm_int/esw/mbcm.h> 27 #include <bcm_int/esw/l3.h> 28 #include <bcm_int/esw/firebolt.h> 29 #include <bcm_int/esw/triumph.h> 30 #include <bcm_int/esw/triumph2.h> 31 #include <bcm_int/esw/xgs3.h> 32 #include <bcm_int/esw/mim.h> 33 #include <bcm_int/common/multicast.h> 34 #include <bcm_int/esw/virtual.h> 35 #include <bcm_int/esw/trx.h> 36 #include <bcm_int/esw/stack.h> 37 #include <bcm_int/esw/triumph3.h> 38 39 #include <bcm_int/esw_dispatch.h> 40 #include <bcm_int/api_xlate_port.h> 41 42 43 #define L3_INFO(unit) (&_bcm_l3_bk_info[unit]) 44 #define MIM_INFO(_unit_) (&_bcm_tr2_mim_bk_info[_unit_]) 45 #define VPN_ISID(_unit_, _vfi_) \ 46 (_bcm_tr2_mim_bk_info[_unit_].vpn_info[_vfi_].isid) 47 48 /* 49 * Function: 50 * _bcm_tr3_mim_match_add 51 * Purpose: 52 * Add MiM match parameters 53 * 54 * Parameters: 55 * unit - (IN) bcm device 56 * mim_port - (IN) mim port 57 * vp - (IN) vp 58 * 59 * Returns: 60 * BCM_E_NONE - Success 61 * BCM_E_XXX 62 * Notes: 63 */ 64 int 65 _bcm_tr3_mim_match_add(int unit, bcm_mim_port_t *mim_port, int vp) 66 { 67 int rv = BCM_E_NONE, i, gport_id; 68 bcm_module_t mod_out; 69 bcm_port_t port_out; 70 bcm_trunk_t trunk_id; 71 bcm_mac_t mac_mask; 72 73 74 rv = _bcm_esw_gport_resolve(unit, mim_port->port, &mod_out, 75 &port_out, &trunk_id, &gport_id); 76 BCM_IF_ERROR_RETURN(rv); 77 78 if ((mim_port->criteria == BCM_MIM_PORT_MATCH_PORT_VLAN) || 79 (mim_port->criteria == BCM_MIM_PORT_MATCH_PORT_VLAN_STACKED)) { 80 vlan_xlate_extd_entry_t vent; 81 soc_mem_t xlate_mem; 82 int xlate_index = -1; 83 vlan_xlate_extd_entry_t return_vent; 84 85 sal_memset(&vent, 0, sizeof(vent)); 86 xlate_mem = VLAN_XLATE_EXTDm; 87 soc_mem_field32_set(unit, xlate_mem, &vent, KEY_TYPE_0f, 88 TR3_VLXLT_X_HASH_KEY_TYPE_OVID); 89 soc_mem_field32_set(unit, xlate_mem, &vent, KEY_TYPE_1f, 90 TR3_VLXLT_X_HASH_KEY_TYPE_OVID); 91 soc_mem_field32_set(unit, xlate_mem, &vent, VALID_0f, 0x1); 92 soc_mem_field32_set(unit, xlate_mem, &vent, VALID_1f, 0x1); 93 /* vlan xlate data */ 94 soc_mem_field32_set(unit, xlate_mem, &vent, MPLS_ACTIONf, 0x1); /* SVP */ 95 soc_mem_field32_set(unit, xlate_mem, &vent, DISABLE_VLAN_CHECKSf, 1); 96 soc_mem_field32_set(unit, xlate_mem, &vent, SOURCE_VPf, vp); 97 98 99 /* vlan xlate key */ 100 if (mim_port->criteria == BCM_MIM_PORT_MATCH_PORT_VLAN) { 101 if (!BCM_VLAN_VALID(mim_port->match_vlan)) { 102 return BCM_E_PARAM; 103 } 104 soc_mem_field32_set(unit, xlate_mem, &vent, OVIDf, 105 mim_port->match_vlan); 106 MIM_INFO(unit)->port_info[vp].flags |= 107 _BCM_MIM_PORT_TYPE_ACCESS_PORT_VLAN; 108 MIM_INFO(unit)->port_info[vp].match_vlan = mim_port->match_vlan; 109 110 } else { 111 if (!BCM_VLAN_VALID(mim_port->match_vlan) || 112 !BCM_VLAN_VALID(mim_port->match_inner_vlan)) { 113 return BCM_E_PARAM; 114 } 115 soc_mem_field32_set(unit, xlate_mem, &vent, KEY_TYPE_0f, 116 TR3_VLXLT_X_HASH_KEY_TYPE_OVID); 117 soc_mem_field32_set(unit, xlate_mem, &vent, KEY_TYPE_1f, 118 TR3_VLXLT_X_HASH_KEY_TYPE_OVID); 119 soc_mem_field32_set(unit, xlate_mem, &vent, VALID_0f, 0x1); 120 soc_mem_field32_set(unit, xlate_mem, &vent, VALID_1f, 0x1); 121 soc_mem_field32_set(unit, xlate_mem, &vent, OVIDf, 122 mim_port->match_vlan); 123 soc_mem_field32_set(unit, xlate_mem, &vent, IVIDf, 124 mim_port->match_inner_vlan); 125 MIM_INFO(unit)->port_info[vp].flags |= 126 _BCM_MIM_PORT_TYPE_ACCESS_PORT_VLAN_STACKED; 127 MIM_INFO(unit)->port_info[vp].match_vlan = mim_port->match_vlan; 128 MIM_INFO(unit)->port_info[vp].match_inner_vlan = 129 mim_port->match_inner_vlan; 130 } 131 132 if (BCM_GPORT_IS_TRUNK(mim_port->port)) { 133 soc_mem_field32_set(unit, xlate_mem, &vent, Tf, 1); 134 soc_mem_field32_set(unit, xlate_mem, &vent, TGIDf, trunk_id); 135 } else { 136 soc_mem_field32_set(unit, xlate_mem, &vent, MODULE_IDf, mod_out); 137 soc_mem_field32_set(unit, xlate_mem, &vent, PORT_NUMf, port_out); 138 } 139 rv = soc_mem_search(unit, xlate_mem, MEM_BLOCK_ANY, &xlate_index, 140 &vent, &return_vent, 0); 141 if (BCM_E_NONE == rv) { 142 if (mim_port->flags & BCM_MIM_PORT_REPLACE) { 143 BCM_IF_ERROR_RETURN( 144 soc_mem_write(unit, 145 xlate_mem, MEM_BLOCK_ALL, xlate_index, &vent)); 146 } else { 147 return BCM_E_EXISTS; 148 } 149 } else if (BCM_E_NOT_FOUND == rv) { 150 if (mim_port->flags & BCM_MIM_PORT_REPLACE) { 151 return BCM_E_NOT_FOUND; 152 } 153 rv = soc_mem_insert(unit, xlate_mem, MEM_BLOCK_ALL, &vent); 154 BCM_IF_ERROR_RETURN(rv); 155 _bcm_tr2_mim_port_match_count_adjust(unit, vp, 1); 156 } else { 157 return rv; 158 } 159 } else if (mim_port->criteria == BCM_MIM_PORT_MATCH_PORT) { 160 if (BCM_GPORT_IS_TRUNK(mim_port->port)) { 161 rv = _bcm_tr2_mim_match_trunk_add(unit, trunk_id, vp); 162 if (rv >= 0) { 163 MIM_INFO(unit)->port_info[vp].flags |= 164 _BCM_MIM_PORT_TYPE_ACCESS_PORT_TRUNK; 165 MIM_INFO(unit)->port_info[vp].index = trunk_id; 166 } 167 BCM_IF_ERROR_RETURN(rv); 168 } else { 169 source_trunk_map_modbase_entry_t modbase_entry; 170 int mod_id_idx=0; /* Module Id */ 171 int isLocal; 172 173 BCM_IF_ERROR_RETURN(_bcm_esw_modid_is_local(unit, mod_out, &isLocal)); 174 BCM_IF_ERROR_RETURN(bcm_esw_stk_my_modid_get(unit, &mod_id_idx)); 175 176 if ((!isLocal) && (mod_out != BCM_MODID_INVALID)) { 177 mod_id_idx = mod_out; 178 } 179 180 BCM_IF_ERROR_RETURN 181 (soc_mem_read(unit, SOURCE_TRUNK_MAP_MODBASEm, MEM_BLOCK_ANY, 182 mod_id_idx, &modbase_entry)); 183 184 i = soc_mem_field32_get(unit, SOURCE_TRUNK_MAP_MODBASEm, 185 &modbase_entry, BASEf) + port_out; 186 rv = soc_mem_field32_modify(unit, SOURCE_TRUNK_MAP_TABLEm, 187 i, SOURCE_VPf, vp); 188 BCM_IF_ERROR_RETURN(rv); 189 190 rv = soc_mem_field32_modify(unit, PORT_TABm, port_out, 191 PORT_OPERATIONf, 0x1); /* L2_SVP */ 192 BCM_IF_ERROR_RETURN(rv); 193 194 MIM_INFO(unit)->port_info[vp].flags |= 195 _BCM_MIM_PORT_TYPE_ACCESS_PORT; 196 MIM_INFO(unit)->port_info[vp].index = i; 197 } 198 } else if ((mim_port->criteria == BCM_MIM_PORT_MATCH_LABEL)) { 199 mpls_entry_entry_t ment; 200 int index = -1; 201 mpls_entry_entry_t return_ment; 202 203 sal_memset(&ment, 0, sizeof(mpls_entry_entry_t)); 204 if (BCM_GPORT_IS_TRUNK(mim_port->port)) { 205 soc_MPLS_ENTRYm_field32_set(unit, &ment, Tf, 1); 206 soc_MPLS_ENTRYm_field32_set(unit, &ment, TGIDf, trunk_id); 207 } else { 208 soc_MPLS_ENTRYm_field32_set(unit, &ment, MODULE_IDf, mod_out); 209 soc_MPLS_ENTRYm_field32_set(unit, &ment, PORT_NUMf, port_out); 210 } 211 soc_MPLS_ENTRYm_field32_set(unit, &ment, MPLS_LABELf, 212 mim_port->match_label); 213 soc_MPLS_ENTRYm_field32_set(unit, &ment, VALIDf, 1); 214 soc_MPLS_ENTRYm_field32_set(unit, &ment, SOURCE_VPf, vp); 215 soc_MPLS_ENTRYm_field32_set(unit, &ment, MPLS_ACTION_IF_BOSf, 216 0x1); /* L2 SVP */ 217 soc_MPLS_ENTRYm_field32_set(unit, &ment, MPLS_ACTION_IF_NOT_BOSf, 218 0x0); /* INVALID */ 219 rv = soc_mem_search(unit, MPLS_ENTRYm, MEM_BLOCK_ANY, &index, 220 &ment, &return_ment, 0); 221 if (BCM_E_NONE == rv) { 222 if (mim_port->flags & BCM_MIM_PORT_REPLACE) { 223 BCM_IF_ERROR_RETURN( 224 soc_mem_write(unit, 225 MPLS_ENTRYm, MEM_BLOCK_ALL, index, &ment)); 226 } else { 227 return BCM_E_EXISTS; 228 } 229 } else if (BCM_E_NOT_FOUND == rv) { 230 if (mim_port->flags & BCM_MIM_PORT_REPLACE) { 231 return BCM_E_NOT_FOUND; 232 } 233 rv = soc_mem_insert(unit, MPLS_ENTRYm, MEM_BLOCK_ALL, &ment); 234 BCM_IF_ERROR_RETURN(rv); 235 } else { 236 return rv; 237 } 238 MIM_INFO(unit)->port_info[vp].flags |= 239 _BCM_MIM_PORT_TYPE_ACCESS_LABEL; 240 MIM_INFO(unit)->port_info[vp].match_label = mim_port->match_label; 241 242 } else if ((mim_port->criteria == BCM_MIM_PORT_MATCH_TUNNEL_VLAN_SRCMAC)) { 243 mpls_entry_extd_entry_t ment; 244 soc_mem_t mpls_mem; 245 uint64 temp_mac; 246 int index = -1; 247 mpls_entry_extd_entry_t return_ment; 248 249 /* Configure peer Network Virtual port ( NVP) */ 250 if (!BCM_VLAN_VALID(mim_port->match_tunnel_vlan)) { 251 return BCM_E_PARAM; 252 } 253 254 sal_memset(&ment, 0, sizeof(ment)); 255 mpls_mem = MPLS_ENTRY_EXTDm; 256 soc_mem_field32_set(unit, mpls_mem, &ment, KEY_TYPE_0f, 0x17); /* MIM NVP */ 257 soc_mem_field32_set(unit, mpls_mem, &ment, KEY_TYPE_1f, 0x17); 258 soc_mem_field32_set(unit, mpls_mem, &ment, VALID_0f, 1); 259 soc_mem_field32_set(unit, mpls_mem, &ment, VALID_1f, 1); 260 261 /* MIM_NVP key */ 262 soc_mem_field32_set(unit, mpls_mem, &ment, MIM_NVP__BVIDf, 263 mim_port->match_tunnel_vlan); 264 soc_mem_mac_addr_set(unit, mpls_mem, &ment, MIM_NVP__BMACSAf, 265 mim_port->match_tunnel_srcmac); 266 267 /* MIM_NVP data */ 268 if (BCM_GPORT_IS_TRUNK(mim_port->port)) { 269 soc_mem_field32_set(unit, mpls_mem, &ment, MIM_NVP__Tf, 1); 270 soc_mem_field32_set(unit, mpls_mem, &ment, MIM_NVP__TGIDf, trunk_id); 271 } else { 272 soc_mem_field32_set(unit, mpls_mem, &ment, MIM_NVP__MODULE_IDf, mod_out); 273 soc_mem_field32_set(unit, mpls_mem, &ment, MIM_NVP__PORT_NUMf, port_out); 274 } 275 if (mim_port->flags & BCM_MIM_PORT_TYPE_PEER) { 276 soc_mem_t tunnel_mem; 277 soc_tunnel_term_t tnl_entry; 278 uint32 index; 279 280 sal_memset(&tnl_entry, 0, sizeof(tnl_entry)); 281 tunnel_mem = L3_TUNNELm; 282 283 /* MIM L3 TUNNEL Type */ 284 soc_mem_field32_set(unit, tunnel_mem, &tnl_entry, KEY_TYPEf, 0x3); 285 286 /* MIM L3 TUNNEL KEY BMACSA+BVID */ 287 soc_mem_mac_addr_set(unit, tunnel_mem, &tnl_entry, MIM__BMACSAf, 288 mim_port->match_tunnel_srcmac); 289 soc_mem_field32_set(unit, tunnel_mem, &tnl_entry, MIM__BVIDf, 290 mim_port->match_tunnel_vlan); 291 292 /* Enable ISID,BMACSA, BVID lookup in mpls entry table */ 293 soc_mem_field32_set(unit, tunnel_mem, &tnl_entry, 294 MIM__ISID_LOOKUP_KEY_CONTROLf, 1); 295 296 sal_memset(&mac_mask, 0xff, sizeof(mac_mask)); 297 soc_mem_field32_set(unit, tunnel_mem, 298 &tnl_entry, MIM__SGLP_MASKf, 0xffff); 299 soc_mem_field32_set(unit, tunnel_mem, 300 &tnl_entry, MIM__BVID_MASKf, 0xfff); 301 soc_mem_mac_addr_set(unit, tunnel_mem, 302 &tnl_entry, MIM__BMACSA_MASKf, mac_mask); 303 soc_mem_field32_set(unit, tunnel_mem, 304 &tnl_entry, MIM__KEY_TYPE_MASKf, 0x3); 305 soc_mem_field32_set(unit, tunnel_mem, &tnl_entry, VALIDf, 1); 306 307 rv = soc_tunnel_term_insert(unit, &tnl_entry, &index); 308 BCM_IF_ERROR_RETURN(rv); 309 MIM_INFO(unit)->port_info[vp].flags |= 310 _BCM_MIM_PORT_TYPE_PEER; 311 } else { 312 MIM_INFO(unit)->port_info[vp].flags |= 313 _BCM_MIM_PORT_TYPE_NETWORK; 314 } 315 soc_mem_field32_set(unit, mpls_mem, &ment, MIM_NVP__SVPf, vp); 316 317 rv = soc_mem_search(unit, mpls_mem, MEM_BLOCK_ANY, &index, 318 &ment, &return_ment, 0); 319 if (BCM_E_NONE == rv) { 320 if (mim_port->flags & BCM_MIM_PORT_REPLACE) { 321 BCM_IF_ERROR_RETURN( 322 soc_mem_write(unit, 323 mpls_mem, MEM_BLOCK_ALL, index, &ment)); 324 } else { 325 return BCM_E_EXISTS; 326 } 327 } else if (BCM_E_NOT_FOUND == rv) { 328 if (mim_port->flags & BCM_MIM_PORT_REPLACE) { 329 return BCM_E_NOT_FOUND; 330 } 331 rv = soc_mem_insert(unit, mpls_mem, MEM_BLOCK_ALL, &ment); 332 BCM_IF_ERROR_RETURN(rv); 333 } else { 334 return rv; 335 } 336 SAL_MAC_ADDR_TO_UINT64(mim_port->match_tunnel_srcmac, temp_mac); 337 SAL_MAC_ADDR_FROM_UINT64 338 (MIM_INFO(unit)->port_info[vp].match_tunnel_srcmac, temp_mac); 339 MIM_INFO(unit)->port_info[vp].match_tunnel_vlan = 340 mim_port->match_tunnel_vlan; 341 } 342 return rv; 343 } 344 345 /* 346 * Function: 347 * _bcm_tr3_mim_match_delete 348 * Purpose: 349 * Delete MIM match parameters 350 * 351 * Parameters: 352 * unit - (IN) bcm device 353 * vp - (IN) virtual port 354 * 355 * Returns: 356 * BCM_E_NONE - Success 357 * BCM_E_XXX 358 * Notes: 359 */ 360 361 int 362 _bcm_tr3_mim_match_delete(int unit, int vp) 363 { 364 int port, rv; 365 366 if (MIM_INFO(unit)->port_info[vp].flags & 367 _BCM_MIM_PORT_TYPE_ACCESS_PORT_VLAN) { 368 vlan_xlate_extd_entry_t vent; 369 soc_mem_t xlate_mem; 370 sal_memset(&vent, 0, sizeof(vent)); 371 372 xlate_mem = VLAN_XLATE_EXTDm; 373 soc_mem_field32_set(unit, xlate_mem, &vent, KEY_TYPE_0f, 374 TR3_VLXLT_X_HASH_KEY_TYPE_OVID); 375 soc_mem_field32_set(unit, xlate_mem, &vent, KEY_TYPE_1f, 376 TR3_VLXLT_X_HASH_KEY_TYPE_OVID); 377 soc_mem_field32_set(unit, xlate_mem, &vent, VALID_0f, 0x1); 378 soc_mem_field32_set(unit, xlate_mem, &vent, VALID_1f, 0x1); 379 380 /* vlan xlate key */ 381 soc_mem_field32_set(unit, xlate_mem, &vent, OVIDf, 382 MIM_INFO(unit)->port_info[vp].match_vlan); 383 if (MIM_INFO(unit)->port_info[vp].modid != -1) { 384 soc_mem_field32_set(unit, xlate_mem, &vent, MODULE_IDf, 385 MIM_INFO(unit)->port_info[vp].modid); 386 soc_mem_field32_set(unit, xlate_mem, &vent, PORT_NUMf, 387 MIM_INFO(unit)->port_info[vp].port); 388 } else { 389 soc_mem_field32_set(unit, xlate_mem, &vent, Tf, 1); 390 soc_mem_field32_set(unit, xlate_mem, &vent, TGIDf, 391 MIM_INFO(unit)->port_info[vp].tgid); 392 } 393 rv = soc_mem_delete(unit, xlate_mem, MEM_BLOCK_ANY, &vent); 394 if (rv != BCM_E_NOT_FOUND) { 395 _bcm_tr2_mim_port_match_count_adjust(unit, vp, -1); 396 return rv; /* Match has been deleted by bcm_port_match_delete */ 397 } 398 399 } else if (MIM_INFO(unit)->port_info[vp].flags & 400 _BCM_MIM_PORT_TYPE_ACCESS_PORT_VLAN_STACKED) { 401 vlan_xlate_extd_entry_t vent; 402 soc_mem_t xlate_mem; 403 sal_memset(&vent, 0, sizeof(vent)); 404 405 xlate_mem = VLAN_XLATE_EXTDm; 406 soc_mem_field32_set(unit, xlate_mem, &vent, KEY_TYPE_0f, 407 TR3_VLXLT_X_HASH_KEY_TYPE_IVID_OVID); 408 soc_mem_field32_set(unit, xlate_mem, &vent, KEY_TYPE_1f, 409 TR3_VLXLT_X_HASH_KEY_TYPE_OVID); 410 soc_mem_field32_set(unit, xlate_mem, &vent, VALID_0f, 0x1); 411 soc_mem_field32_set(unit, xlate_mem, &vent, VALID_1f, 0x1); 412 413 /* vlan xlate key */ 414 soc_mem_field32_set(unit, xlate_mem, &vent, OVIDf, 415 MIM_INFO(unit)->port_info[vp].match_vlan); 416 soc_mem_field32_set(unit, xlate_mem, &vent, IVIDf, 417 MIM_INFO(unit)->port_info[vp].match_inner_vlan); 418 if (MIM_INFO(unit)->port_info[vp].modid != -1) { 419 soc_mem_field32_set(unit, xlate_mem, &vent, MODULE_IDf, 420 MIM_INFO(unit)->port_info[vp].modid); 421 soc_mem_field32_set(unit, xlate_mem, &vent, PORT_NUMf, 422 MIM_INFO(unit)->port_info[vp].port); 423 } else { 424 soc_mem_field32_set(unit, xlate_mem, &vent, Tf, 1); 425 soc_mem_field32_set(unit, xlate_mem, &vent, TGIDf, 426 MIM_INFO(unit)->port_info[vp].tgid); 427 } 428 rv = soc_mem_delete(unit, xlate_mem, MEM_BLOCK_ANY, &vent); 429 BCM_IF_ERROR_RETURN(rv); 430 431 } else if (MIM_INFO(unit)->port_info[vp].flags & 432 _BCM_MIM_PORT_TYPE_ACCESS_PORT) { 433 rv = soc_mem_field32_modify(unit, SOURCE_TRUNK_MAP_TABLEm, 434 MIM_INFO(unit)->port_info[vp].index, 435 SOURCE_VPf, 0); 436 BCM_IF_ERROR_RETURN(rv); 437 port = MIM_INFO(unit)->port_info[vp].index & SOC_PORT_ADDR_MAX(unit); 438 rv = soc_mem_field32_modify(unit, PORT_TABm, port, 439 PORT_OPERATIONf, 0x0); /* NORMAL */ 440 BCM_IF_ERROR_RETURN(rv); 441 442 } else if(MIM_INFO(unit)->port_info[vp].flags & 443 _BCM_MIM_PORT_TYPE_ACCESS_PORT_TRUNK) { 444 int trunk_id; 445 trunk_id = MIM_INFO(unit)->port_info[vp].index; 446 rv = _bcm_tr_mim_match_trunk_delete(unit, trunk_id, vp); 447 BCM_IF_ERROR_RETURN(rv); 448 } else if (MIM_INFO(unit)->port_info[vp].flags & 449 _BCM_MIM_PORT_TYPE_ACCESS_LABEL) { 450 mpls_entry_entry_t ment; 451 sal_memset(&ment, 0, sizeof(mpls_entry_entry_t)); 452 if (MIM_INFO(unit)->port_info[vp].modid != -1) { 453 soc_MPLS_ENTRYm_field32_set(unit, &ment, MODULE_IDf, 454 MIM_INFO(unit)->port_info[vp].modid); 455 soc_MPLS_ENTRYm_field32_set(unit, &ment, PORT_NUMf, 456 MIM_INFO(unit)->port_info[vp].port); 457 } else { 458 soc_MPLS_ENTRYm_field32_set(unit, &ment, Tf, 1); 459 soc_MPLS_ENTRYm_field32_set(unit, &ment, TGIDf, 460 MIM_INFO(unit)->port_info[vp].tgid); 461 } 462 soc_MPLS_ENTRYm_field32_set(unit, &ment, MPLS_LABELf, 463 MIM_INFO(unit)->port_info[vp].match_label); 464 rv = soc_mem_delete(unit, MPLS_ENTRYm, MEM_BLOCK_ANY, &ment); 465 BCM_IF_ERROR_RETURN(rv); 466 467 } else if (MIM_INFO(unit)->port_info[vp].flags & 468 (_BCM_MIM_PORT_TYPE_NETWORK | _BCM_MIM_PORT_TYPE_PEER)) { 469 mpls_entry_extd_entry_t ment; 470 soc_mem_t mpls_mem; 471 472 sal_memset(&ment, 0, sizeof(ment)); 473 mpls_mem = MPLS_ENTRY_EXTDm; 474 soc_mem_field32_set(unit, mpls_mem, &ment, KEY_TYPE_0f, 0x17); /* MIM NVP */ 475 soc_mem_field32_set(unit, mpls_mem, &ment, KEY_TYPE_1f, 0x17); 476 soc_mem_field32_set(unit, mpls_mem, &ment, VALID_0f, 1); 477 soc_mem_field32_set(unit, mpls_mem, &ment, VALID_1f, 1); 478 479 /* MIM_NVP key */ 480 soc_mem_field32_set(unit, mpls_mem, &ment, MIM_NVP__BVIDf, 481 MIM_INFO(unit)->port_info[vp].match_tunnel_vlan); 482 soc_mem_mac_addr_set(unit, mpls_mem, &ment, MIM_NVP__BMACSAf, 483 MIM_INFO(unit)->port_info[vp].match_tunnel_srcmac); 484 rv = soc_mem_delete(unit, mpls_mem, MEM_BLOCK_ALL, &ment); 485 BCM_IF_ERROR_RETURN(rv); 486 487 /* Delete L3_Tunnel MIM entry for peer port */ 488 if (MIM_INFO(unit)->port_info[vp].flags & _BCM_MIM_PORT_TYPE_PEER) { 489 soc_mem_t tunnel_mem; 490 soc_tunnel_term_t tnl_entry; 491 492 sal_memset(&tnl_entry, 0, sizeof(tnl_entry)); 493 tunnel_mem = L3_TUNNELm; 494 495 /* MIM L3 TUNNEL Type */ 496 soc_mem_field32_set(unit, tunnel_mem, &tnl_entry, KEY_TYPEf, 0x3); 497 498 /* MIM L3 TUNNEL KEY BMACSA+BVID */ 499 soc_mem_mac_addr_set(unit, tunnel_mem, &tnl_entry, MIM__BMACSAf, 500 MIM_INFO(unit)->port_info[vp].match_tunnel_srcmac); 501 soc_mem_field32_set(unit, tunnel_mem, &tnl_entry, MIM__BVIDf, 502 MIM_INFO(unit)->port_info[vp].match_tunnel_vlan); 503 rv = soc_tunnel_term_delete(unit, &tnl_entry); 504 BCM_IF_ERROR_RETURN(rv); 505 } 506 } 507 return BCM_E_NONE; 508 } 509 510 511 /* 512 * Function: 513 * _bcm_tr3_mim_peer_port_config_add 514 * Purpose: 515 * Add ISID and VP for peer ports. 516 * Parameters: 517 * unit - (IN) bcm device 518 * mim_port - (IN) mim port 519 * vp - (IN) virtual port 520 * vpn - (IN) VPN ID (VFI) 521 * Returns: 522 * BCM_E_NONE - Success 523 * BCM_E_XXX 524 * Notes: 525 */ 526 int 527 _bcm_tr3_mim_peer_port_config_add(int unit, bcm_mim_port_t *mim_port, 528 int vp, bcm_mim_vpn_t vpn) 529 { 530 mpls_entry_extd_entry_t ment; 531 uint32 egr_vlan_xlate_entry[SOC_MAX_MEM_WORDS]; 532 int index, vfi, rv = BCM_E_NONE; 533 534 /* Need an ISID-SVP entry in MPLS_ENTRY */ 535 _BCM_MIM_VPN_GET(vfi, _BCM_MIM_VPN_TYPE_MIM, vpn); 536 537 sal_memset(&ment, 0, sizeof(ment)); 538 soc_MPLS_ENTRY_EXTDm_field32_set(unit, &ment, KEY_TYPE_0f, 0x19); /* MIM_ISID_SVP */ 539 soc_MPLS_ENTRY_EXTDm_field32_set(unit, &ment, KEY_TYPE_1f, 0x19); /* MIM_ISID_SVP */ 540 soc_MPLS_ENTRY_EXTDm_field32_set(unit, &ment, VALID_0f, 0x1); 541 soc_MPLS_ENTRY_EXTDm_field32_set(unit, &ment, VALID_1f, 0x1); 542 /* MIM_ISID_SVP key */ 543 soc_MPLS_ENTRY_EXTDm_field32_set(unit, &ment, MIM_ISID__ISIDf, 544 VPN_ISID(unit, vfi)); 545 546 /* MIM_ISID_SVP data */ 547 548 soc_MPLS_ENTRY_EXTDm_field32_set(unit, &ment, MIM_ISID__VFIf, vfi); 549 rv = soc_mem_search(unit, MPLS_ENTRY_EXTDm, MEM_BLOCK_ANY, &index, 550 &ment, &ment, 0); 551 if (rv == SOC_E_NONE) { 552 return BCM_E_EXISTS; 553 } else if (rv != SOC_E_NOT_FOUND) { 554 return rv; 555 } 556 BCM_IF_ERROR_RETURN(soc_mem_insert(unit, MPLS_ENTRY_EXTDm, MEM_BLOCK_ALL, &ment)); 557 558 /* Also need the reverse entry in the egress */ 559 sal_memset(egr_vlan_xlate_entry, 0, sizeof(egr_vlan_xlate_entry[SOC_MAX_MEM_WORDS])); 560 soc_EGR_VLAN_XLATEm_field32_set(unit, egr_vlan_xlate_entry, KEY_TYPEf, 561 0x3); 562 soc_EGR_VLAN_XLATEm_field32_set(unit, egr_vlan_xlate_entry, VALIDf, 0x1); 563 /* MIM_ISID_DVP key */ 564 soc_EGR_VLAN_XLATEm_field32_set(unit, egr_vlan_xlate_entry, MIM_ISID__VFIf, 565 vfi); 566 soc_EGR_VLAN_XLATEm_field32_set(unit, egr_vlan_xlate_entry, 567 MIM_ISID__DVPf, vp); 568 /* MIM_ISID_DVP data */ 569 soc_EGR_VLAN_XLATEm_field32_set(unit, egr_vlan_xlate_entry, 570 MIM_ISID__ISIDf, VPN_ISID(unit, vfi)); 571 572 /* Deal with egress SD tag actions */ 573 if (mim_port->flags & BCM_MIM_PORT_EGRESS_SERVICE_VLAN_TAGGED) { 574 BCM_IF_ERROR_RETURN 575 (_bcm_tr2_mim_egr_vxlt_sd_tag_actions(unit, mim_port, NULL, 576 egr_vlan_xlate_entry)); 577 } 578 579 rv = soc_mem_search(unit, EGR_VLAN_XLATEm, MEM_BLOCK_ANY, &index, 580 egr_vlan_xlate_entry, egr_vlan_xlate_entry, 0); 581 if (rv == SOC_E_NONE) { 582 return BCM_E_EXISTS; 583 } else if (rv != SOC_E_NOT_FOUND) { 584 return rv; 585 } 586 rv = soc_mem_insert(unit, EGR_VLAN_XLATEm, MEM_BLOCK_ALL, egr_vlan_xlate_entry); 587 588 return rv; 589 } 590 591 /* 592 * Function: 593 * _bcm_tr3_mim_peer_port_config_delete 594 * Purpose: 595 * Delete MPLS_ENTRy and EGR_VLAN_XLATE ISID/VFI instances 596 * 597 * Parameters: 598 * unit - (IN) bcm device 599 * vp - (IN) vp 600 * vpn - (IN) VPN Id ( VFI) 601 * Returns: 602 * BCM_E_NONE - Success 603 * BCM_E_XXX 604 * Notes: 605 */ 606 int 607 _bcm_tr3_mim_peer_port_config_delete(int unit, int vp, bcm_mim_vpn_t vpn) 608 { 609 mpls_entry_extd_entry_t ment; 610 egr_vlan_xlate_entry_t egr_vlan_xlate_entry; 611 int vfi, rv = BCM_E_NONE; 612 int index = -1; 613 614 _BCM_MIM_VPN_GET(vfi, _BCM_MIM_VPN_TYPE_MIM, vpn); 615 616 sal_memset(&egr_vlan_xlate_entry, 0, sizeof(egr_vlan_xlate_entry_t)); 617 soc_EGR_VLAN_XLATEm_field32_set(unit, &egr_vlan_xlate_entry, KEY_TYPEf, 618 0x3); 619 soc_EGR_VLAN_XLATEm_field32_set(unit, &egr_vlan_xlate_entry, VALIDf, 0x1); 620 soc_EGR_VLAN_XLATEm_field32_set(unit, &egr_vlan_xlate_entry, MIM_ISID__VFIf, 621 vfi); 622 soc_EGR_VLAN_XLATEm_field32_set(unit, &egr_vlan_xlate_entry, 623 MIM_ISID__DVPf, vp); 624 625 rv = soc_mem_search(unit, EGR_VLAN_XLATEm, MEM_BLOCK_ANY, &index, 626 &egr_vlan_xlate_entry, &egr_vlan_xlate_entry, 0); 627 BCM_IF_ERROR_RETURN(rv); 628 629 /* Delete the ISID-SVP entry in MPLS_ENTRY */ 630 sal_memset(&ment, 0, sizeof(ment)); 631 soc_MPLS_ENTRY_EXTDm_field32_set(unit, &ment, KEY_TYPE_0f, 0x19); /* MIM_ISID_SVP */ 632 soc_MPLS_ENTRY_EXTDm_field32_set(unit, &ment, KEY_TYPE_1f, 0x19); /* MIM_ISID_SVP */ 633 soc_MPLS_ENTRY_EXTDm_field32_set(unit, &ment, VALID_0f, 0x1); 634 soc_MPLS_ENTRY_EXTDm_field32_set(unit, &ment, VALID_1f, 0x1); 635 /* MIM_ISID_SVP key */ 636 soc_MPLS_ENTRY_EXTDm_field32_set(unit, &ment, MIM_ISID__ISIDf, 637 VPN_ISID(unit, vfi)); 638 639 rv = soc_mem_delete(unit, MPLS_ENTRY_EXTDm, MEM_BLOCK_ANY, &ment); 640 BCM_IF_ERROR_RETURN(rv); 641 #if defined(BCM_TRIDENT2_SUPPORT) || defined(BCM_TRIUMPH3_SUPPORT) 642 /*delete TP_ID from software*/ 643 BCM_IF_ERROR_RETURN( 644 _bcm_tr2_mim_egr_vxlt_sd_tag_actions_delete(unit, 645 (void *)&egr_vlan_xlate_entry)); 646 #endif 647 /* Delete the reverse entry in the egress */ 648 rv = soc_mem_delete(unit, EGR_VLAN_XLATEm, MEM_BLOCK_ANY, 649 &egr_vlan_xlate_entry); 650 return rv; 651 } 652 653 /* 654 * Function: 655 * _bcm_tr3_mim_lookup_id_stat_get_table_info 656 * Description: 657 * Provides relevant flex table information(table-name,index with 658 * direction) for given MiM I-SID entry. 659 * 660 * Parameters: 661 * unit - (IN) unit number 662 * lookup_id - (IN) I-SID value 663 * num_of_tables - (OUT) Number of flex counter tables 664 * table_info - (OUT) Flex counter tables information 665 * 666 * Return Value: 667 * BCM_E_XXX 668 * Notes: 669 */ 670 bcm_error_t _bcm_tr3_mim_lookup_id_stat_get_table_info( 671 int unit, 672 int lookup_id, 673 uint32 *num_of_tables, 674 bcm_stat_flex_table_info_t *table_info) 675 { 676 int index, rv = BCM_E_NONE; 677 int vfi = -1; 678 uint32 mpls_vent[SOC_MAX_MEM_WORDS] = {0}; 679 uint32 vxlate_mem_vent[SOC_MAX_MEM_WORDS] = {0}; 680 soc_mem_t mpls_mem = MPLS_ENTRYm; 681 soc_mem_t vxlate_mem = EGR_VLAN_XLATEm; 682 683 /* Get MPLS_ENTRYm MIM_ISID Entry */ 684 #if defined(BCM_TRIDENT2_SUPPORT) 685 if (SOC_IS_TRIDENT2X(unit) || SOC_IS_TOMAHAWKX(unit)) { 686 /* MIM_ISID */ 687 soc_mem_field32_set(unit, mpls_mem, mpls_vent, KEY_TYPEf, 0x2); 688 soc_mem_field32_set(unit, mpls_mem, mpls_vent, VALIDf, 0x1); 689 } else 690 #endif /* BCM_TRIDENT2_SUPPORT */ 691 #if defined(BCM_TRIDENT3_SUPPORT) 692 if (SOC_IS_TRIDENT3X(unit)) { 693 soc_mem_field32_set(unit, mpls_mem, mpls_vent, KEY_TYPEf, 0x2); 694 soc_mem_field32_set(unit, mpls_mem, mpls_vent, BASE_VALID_0f, 0x3); 695 soc_mem_field32_set(unit, mpls_mem, mpls_vent, BASE_VALID_1f, 0x7); 696 } else 697 #endif /* BCM_TRIDENT2_SUPPORT */ 698 { 699 mpls_mem = MPLS_ENTRY_EXTDm; 700 /* MIM_ISID */ 701 soc_mem_field32_set(unit, mpls_mem, mpls_vent, KEY_TYPE_0f, 0x18); 702 soc_mem_field32_set(unit, mpls_mem, mpls_vent, KEY_TYPE_1f, 0x18); 703 soc_mem_field32_set(unit, mpls_mem, mpls_vent, VALID_0f, 0x1); 704 soc_mem_field32_set(unit, mpls_mem, mpls_vent, VALID_1f, 0x1); 705 } 706 /* MIM_ISID key */ 707 soc_mem_field32_set(unit, mpls_mem, &mpls_vent, MIM_ISID__ISIDf, lookup_id); 708 709 rv = soc_mem_search(unit, mpls_mem, MEM_BLOCK_ANY, &index, 710 mpls_vent, mpls_vent, 0); 711 if (rv == BCM_E_NONE) { 712 table_info[*num_of_tables].table = mpls_mem; 713 table_info[*num_of_tables].index = index; 714 table_info[*num_of_tables].direction = bcmStatFlexDirectionIngress; 715 (*num_of_tables)++; 716 } 717 718 vfi = soc_mem_field32_get(unit, mpls_mem, &mpls_vent, MIM_ISID__VFIf); 719 720 /* Get EGR_VLAN_XLATEm MIM_ISID Entry */ 721 #if defined(BCM_TRIUMPH3_SUPPORT) 722 if (SOC_IS_TRIUMPH3(unit)) { 723 soc_mem_field32_set(unit, vxlate_mem, vxlate_mem_vent, 724 KEY_TYPEf, 0x2); /* MIM_ISID */ 725 } else 726 #endif /* BCM_TRIUMPH3_SUPPORT */ 727 #if defined(BCM_TRIDENT3_SUPPORT) 728 if (SOC_IS_TRIDENT3X(unit)) { 729 vxlate_mem = EGR_VLAN_XLATE_1_DOUBLEm; 730 soc_mem_field32_set(unit, vxlate_mem, vxlate_mem_vent, BASE_VALID_0f, 3); 731 soc_mem_field32_set(unit, vxlate_mem, vxlate_mem_vent, BASE_VALID_1f, 7); 732 soc_mem_field32_set(unit, vxlate_mem, vxlate_mem_vent, DATA_TYPEf, 0x3); 733 soc_mem_field32_set(unit, vxlate_mem, vxlate_mem_vent, KEY_TYPEf, 0x3); 734 } else 735 #endif 736 { 737 soc_mem_field32_set(unit, vxlate_mem, vxlate_mem_vent, ENTRY_TYPEf, 0x3); 738 } 739 740 /* MIIM_ISID key */ 741 soc_mem_field32_set(unit, vxlate_mem, vxlate_mem_vent, MIM_ISID__VFIf, vfi); 742 rv = soc_mem_search(unit, vxlate_mem, MEM_BLOCK_ANY, &index, 743 vxlate_mem_vent, vxlate_mem_vent, 0); 744 745 if (rv == BCM_E_NONE) { 746 table_info[*num_of_tables].table = vxlate_mem; 747 table_info[*num_of_tables].index = index; 748 table_info[*num_of_tables].direction = bcmStatFlexDirectionEgress; 749 (*num_of_tables)++; 750 } 751 752 return rv; 753 } 754 755 /* 756 * Function: 757 * _bcm_tr3_mim_vpn_stat_get_table_info 758 * Description: 759 * Provides relevant flex table information(table-name,index with 760 * direction) for given MiM VPN entry 761 * 762 * Parameters: 763 * unit - (IN) unit number 764 * vpn - (IN) MiM VPN 765 * num_of_tables - (OUT) Number of flex counter tables 766 * table_info - (OUT) Flex counter tables information 767 * 768 * Return Value: 769 * BCM_E_XXX 770 * Notes: 771 */ 772 bcm_error_t _bcm_tr3_mim_vpn_stat_get_table_info( 773 int unit, 774 bcm_mim_vpn_t vpn, 775 uint32 *num_of_tables, 776 bcm_stat_flex_table_info_t *table_info) 777 { 778 int vfi; 779 780 *num_of_tables = 0; 781 782 /* Get Ingress stats index */ 783 _BCM_MIM_VPN_GET(vfi, _BCM_MIM_VPN_TYPE_MIM, vpn); 784 if (!_bcm_vfi_used_get(unit, vfi, _bcmVfiTypeMim)) { 785 return BCM_E_NOT_FOUND; 786 } 787 table_info[*num_of_tables].table = VFIm; 788 table_info[*num_of_tables].index = vfi; 789 table_info[*num_of_tables].direction = bcmStatFlexDirectionIngress; 790 (*num_of_tables)++; 791 792 /* Get Egress stats index */ 793 table_info[*num_of_tables].table=EGR_VFIm; 794 table_info[*num_of_tables].index=vfi; 795 table_info[*num_of_tables].direction=bcmStatFlexDirectionEgress; 796 (*num_of_tables)++; 797 798 return BCM_E_NONE; 799 } 800 801 /* 802 * Function: 803 * bcm_tr3_mim_peer_port_config_delete 804 * Purpose: 805 * 806 * 807 * Parameters: 808 * unit - (IN) bcm device 809 * 810 * Returns: 811 * BCM_E_NONE - Success 812 * BCM_E_XXX 813 * Notes: 814 */ 815 816 #endif /* defined(BCM_TRIUMPH3_SUPPORT) && defined(INCLUDE_L3) */