openbcm

Git mirror of https://github.com/Broadcom-Network-Switching-Software/OpenBCM
git clone git://git.finwo.net/mirror/broadcom/openbcm
Log | Files | Refs | README

failover.c (9917B)


      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  * Katana2 failover API
      8  */
      9 
     10 #include <shared/bsl.h>
     11 
     12 #include <soc/defs.h>
     13 #include <sal/core/libc.h>
     14 
     15 #if defined(BCM_KATANA2_SUPPORT) &&  defined(INCLUDE_L3)
     16 
     17 #include <soc/drv.h>
     18 #include <soc/mem.h>
     19 #include <soc/util.h>
     20 #include <soc/debug.h>
     21 #include <bcm/types.h>
     22 #include <bcm/error.h>
     23 #include <bcm/failover.h>
     24 #include <bcm_int/esw_dispatch.h>
     25 #include <bcm_int/esw/katana2.h>
     26 #include <bcm_int/esw/katana.h>
     27 #include <bcm_int/common/multicast.h>
     28 #include <bcm_int/esw/failover.h>
     29 #include <bcm_int/esw/mpls.h>
     30 #include <bcm_int/esw/triumph.h>
     31 #include <bcm_int/esw/triumph2.h>
     32 
     33 
     34 STATIC int
     35 _bcm_kt2_failover_nhi_get(int unit, bcm_gport_t port, int *nh_index)
     36 {
     37     int vp=0xFFFF;
     38     ing_dvp_table_entry_t dvp;
     39 
     40     if (!BCM_GPORT_IS_MPLS_PORT(port) &&
     41          !BCM_GPORT_IS_MIM_PORT(port) ) {
     42         return BCM_E_PARAM;
     43     }
     44 
     45     if ( BCM_GPORT_IS_MPLS_PORT(port)) {
     46          vp = BCM_GPORT_MPLS_PORT_ID_GET(port);
     47     } else if ( BCM_GPORT_IS_MIM_PORT(port)) {
     48          vp = BCM_GPORT_MIM_PORT_ID_GET(port);
     49     }
     50 
     51     if (vp >= soc_mem_index_count(unit, SOURCE_VPm)) {
     52         return BCM_E_PARAM;
     53     }
     54     BCM_IF_ERROR_RETURN (READ_ING_DVP_TABLEm(unit, MEM_BLOCK_ANY, vp, &dvp));
     55 
     56     /* Next-hop index is used for multicast replication */
     57     *nh_index = soc_ING_DVP_TABLEm_field32_get(unit, &dvp, NEXT_HOP_INDEXf);
     58     return BCM_E_NONE;
     59 }
     60 /*
     61  * Function:
     62  *        bcm_kt2_failover_status_set
     63  * Purpose:
     64  *        Set the parameters for a failover object
     65  * Parameters:
     66  *        IN :  unit
     67  *           IN :  failover_id
     68  *           IN :  value
     69  * Returns:
     70  *        BCM_E_XXX
     71  */
     72 
     73 int
     74 bcm_kt2_failover_status_set(int unit,
     75                                      bcm_failover_element_t *failover,
     76                                      int value)
     77 {
     78     int rv = BCM_E_UNAVAIL;
     79     int nh_index;
     80     uint32 label_action = -1;
     81     bcm_l3_egress_t egr;
     82     initial_prot_group_table_entry_t  prot_group_entry;
     83     rx_prot_group_table_entry_t  rx_prot_group_entry;
     84     initial_prot_nhi_table_1_entry_t   prot_nhi_1_entry;
     85 
     86     if ((value < 0) || (value > 1)) {
     87        return BCM_E_PARAM;
     88     }
     89 
     90     if (failover->failover_id != BCM_FAILOVER_INVALID) {
     91          /* Group protection for Port and Tunnel: Egress and Ingress */
     92          BCM_IF_ERROR_RETURN(
     93               bcm_tr2_failover_id_validate ( unit, failover->failover_id ));
     94 
     95          BCM_IF_ERROR_RETURN (soc_mem_read(unit, INITIAL_PROT_GROUP_TABLEm,
     96                    MEM_BLOCK_ANY, failover->failover_id, &prot_group_entry));
     97 
     98          soc_mem_field32_set(unit, INITIAL_PROT_GROUP_TABLEm,
     99                    &prot_group_entry, REPLACE_ENABLEf, value);
    100 
    101          BCM_IF_ERROR_RETURN(
    102               soc_mem_write(unit, INITIAL_PROT_GROUP_TABLEm,
    103                    MEM_BLOCK_ALL, failover->failover_id, &prot_group_entry));
    104 
    105          BCM_IF_ERROR_RETURN (soc_mem_read(unit, RX_PROT_GROUP_TABLEm,
    106                MEM_BLOCK_ANY, failover->failover_id, &rx_prot_group_entry));
    107 
    108          soc_mem_field32_set(unit, RX_PROT_GROUP_TABLEm,
    109                &rx_prot_group_entry, DROP_DATA_ENABLEf, value);
    110 
    111          rv =   soc_mem_write(unit, RX_PROT_GROUP_TABLEm,
    112                MEM_BLOCK_ALL, failover->failover_id,  &rx_prot_group_entry);
    113 
    114     }else if (failover->intf != BCM_IF_INVALID) {
    115         /* Only Egress is applicable */
    116         if (BCM_XGS3_L3_EGRESS_IDX_VALID(unit, failover->intf)) {
    117             nh_index = failover->intf - BCM_XGS3_EGRESS_IDX_MIN(unit);
    118         } else {
    119             nh_index = failover->intf  - BCM_XGS3_DVP_EGRESS_IDX_MIN(unit);
    120         }
    121 
    122          BCM_IF_ERROR_RETURN (soc_mem_read(unit, INITIAL_PROT_NHI_TABLE_1m,
    123                               MEM_BLOCK_ANY, nh_index, &prot_nhi_1_entry));
    124 
    125          soc_mem_field32_set(unit, INITIAL_PROT_NHI_TABLE_1m,
    126                              &prot_nhi_1_entry, REPLACE_ENABLEf, value);
    127 
    128          rv = soc_mem_write(unit, INITIAL_PROT_NHI_TABLE_1m,
    129                        MEM_BLOCK_ALL, nh_index, &prot_nhi_1_entry);
    130         if (rv < 0) {
    131             return rv;
    132         }
    133 
    134         /* handle 1+1 protection on MSP (multiplex section protection) */
    135         if (soc_feature(unit, soc_feature_mpls)) {
    136             bcm_l3_egress_t_init(&egr);
    137             BCM_IF_ERROR_RETURN(bcm_xgs3_l3_egress_get(unit,
    138                                 failover->intf, &egr));
    139             if (BCM_SUCCESS(_bcm_esw_failover_egr_check (unit, &egr))) {
    140                 if (_BCM_MULTICAST_IS_SET(egr.failover_mc_group)) {
    141 
    142                     if (BCM_XGS3_L3_MPLS_LBL_VALID(egr.mpls_label)) {
    143                         BCM_IF_ERROR_RETURN(
    144                                 bcm_tr_mpls_get_label_action(unit, nh_index,
    145                                     &label_action));
    146                         switch (label_action) {
    147                             case _BCM_MPLS_ACTION_SWAP:
    148                                 LOG_CLI((BSL_META_U(unit,
    149                                                     "swap\n")));
    150                                 rv = _bcm_kt_egress_object_p2mp_set(unit,
    151                                         egr.failover_mc_group,
    152                                         BCM_MPLS_SWITCH_ACTION_SWAP, value);
    153                                 break;
    154                             default:
    155                                 break;
    156                         }
    157                     }
    158                 }
    159             }
    160         }
    161     } else if (failover->port != BCM_GPORT_INVALID) {
    162          /* Individual protection for Pseudo-wire: Egress and Ingress */
    163          BCM_IF_ERROR_RETURN (
    164                _bcm_kt2_failover_nhi_get(unit, failover->port , &nh_index));
    165 
    166          BCM_IF_ERROR_RETURN (soc_mem_read(unit, INITIAL_PROT_NHI_TABLE_1m,
    167                               MEM_BLOCK_ANY, nh_index, &prot_nhi_1_entry));
    168 
    169          soc_mem_field32_set(unit, INITIAL_PROT_NHI_TABLE_1m,
    170                              &prot_nhi_1_entry, REPLACE_ENABLEf, value);
    171 
    172          rv = soc_mem_write(unit, INITIAL_PROT_NHI_TABLE_1m,
    173                             MEM_BLOCK_ALL, nh_index, &prot_nhi_1_entry);
    174 
    175     }
    176     return rv;
    177 }
    178 
    179 
    180 /*
    181  * Function:
    182  *        bcm_kt2_failover_status_get
    183  * Purpose:
    184  *        Get the parameters for a failover object
    185  * Parameters:
    186  *        IN :  unit
    187  *           IN :  failover_id
    188  *           OUT :  value
    189  * Returns:
    190  *        BCM_E_XXX
    191  */
    192 
    193 int
    194 bcm_kt2_failover_status_get(int unit,
    195                                      bcm_failover_element_t *failover,
    196                                      int  *value)
    197 {
    198     initial_prot_group_table_entry_t  prot_group_entry;
    199     rx_prot_group_table_entry_t  rx_prot_group_entry;
    200     initial_prot_nhi_table_1_entry_t   prot_nhi_1_entry;
    201     int nh_index;
    202 
    203 
    204     if (failover->failover_id != BCM_FAILOVER_INVALID) {
    205 
    206          BCM_IF_ERROR_RETURN(
    207             bcm_tr2_failover_id_validate ( unit, failover->failover_id ));
    208 
    209          BCM_IF_ERROR_RETURN (soc_mem_read(unit, INITIAL_PROT_GROUP_TABLEm,
    210                    MEM_BLOCK_ANY, failover->failover_id, &prot_group_entry));
    211 
    212          *value =   soc_mem_field32_get(unit, INITIAL_PROT_GROUP_TABLEm,
    213                    &prot_group_entry, REPLACE_ENABLEf);
    214 
    215          BCM_IF_ERROR_RETURN (soc_mem_read(unit, RX_PROT_GROUP_TABLEm,
    216                MEM_BLOCK_ANY, failover->failover_id, &rx_prot_group_entry));
    217 
    218          *value &=   soc_mem_field32_get(unit, RX_PROT_GROUP_TABLEm,
    219                &rx_prot_group_entry, DROP_DATA_ENABLEf);
    220 
    221     } else if (failover->intf != BCM_IF_INVALID) {
    222 
    223         if (BCM_XGS3_L3_EGRESS_IDX_VALID(unit, failover->intf)) {
    224             nh_index = failover->intf - BCM_XGS3_EGRESS_IDX_MIN(unit);
    225         } else {
    226             nh_index = failover->intf  - BCM_XGS3_DVP_EGRESS_IDX_MIN(unit);
    227         }
    228 
    229          BCM_IF_ERROR_RETURN (soc_mem_read(unit, INITIAL_PROT_NHI_TABLE_1m,
    230                              MEM_BLOCK_ANY, nh_index, &prot_nhi_1_entry));
    231 
    232          *value =   soc_mem_field32_get(unit, INITIAL_PROT_NHI_TABLE_1m,
    233                    &prot_nhi_1_entry, REPLACE_ENABLEf);
    234 
    235     } else if (failover->port != BCM_GPORT_INVALID) {
    236 
    237          BCM_IF_ERROR_RETURN (
    238                _bcm_kt2_failover_nhi_get(unit, failover->port , &nh_index));
    239 
    240          BCM_IF_ERROR_RETURN (soc_mem_read(unit, INITIAL_PROT_NHI_TABLE_1m,
    241                              MEM_BLOCK_ANY, nh_index, &prot_nhi_1_entry));
    242 
    243          *value =   soc_mem_field32_get(unit, INITIAL_PROT_NHI_TABLE_1m,
    244                    &prot_nhi_1_entry, REPLACE_ENABLEf);
    245 
    246     }
    247     return BCM_E_NONE;
    248 }
    249 
    250 /*
    251  * Function:
    252  *        bcm_kt2_failover_prot_nhi_cleanup
    253  * Purpose:
    254  *        Cleanup  the  entry  for  PROT_NHI
    255  * Parameters:
    256  *        IN :  unit
    257  *           IN :  Primary Next Hop Index
    258  * Returns:
    259  *        BCM_E_XXX
    260  */
    261 
    262 int
    263 bcm_kt2_failover_prot_nhi_cleanup  (int unit, int nh_index)
    264 {
    265     initial_prot_nhi_table_entry_t    prot_nhi_entry;
    266     initial_prot_nhi_table_1_entry_t  prot_nhi_1_entry;
    267     int rv;
    268 
    269     rv = soc_mem_read(unit, INITIAL_PROT_NHI_TABLEm,
    270                              MEM_BLOCK_ANY, nh_index, &prot_nhi_entry);
    271 
    272     if (rv < 0){
    273         return BCM_E_NOT_FOUND;
    274     }
    275 
    276     sal_memset(&prot_nhi_entry, 0, sizeof(initial_prot_nhi_table_entry_t));
    277 
    278     rv = soc_mem_write(unit, INITIAL_PROT_NHI_TABLEm,
    279                        MEM_BLOCK_ALL, nh_index, &prot_nhi_entry);
    280 
    281     if (rv < 0){
    282         return rv;
    283     }
    284 
    285      rv = soc_mem_read(unit, INITIAL_PROT_NHI_TABLE_1m,
    286                              MEM_BLOCK_ANY, nh_index, &prot_nhi_1_entry);
    287 
    288     if (rv < 0){
    289         return BCM_E_NOT_FOUND;
    290     }
    291 
    292     sal_memset(&prot_nhi_1_entry, 0, sizeof(initial_prot_nhi_table_1_entry_t));
    293 
    294     rv = soc_mem_write(unit, INITIAL_PROT_NHI_TABLE_1m,
    295                        MEM_BLOCK_ALL, nh_index, &prot_nhi_1_entry);
    296 
    297     return rv;
    298 
    299 }
    300 
    301 #endif /* defined(BCM_KATANA2_SUPPORT) &&  defined(INCLUDE_L3) */