]> git.proxmox.com Git - mirror_frr.git/blobdiff - bgpd/bgpd.h
Merge pull request #5717 from pguibert6WIND/flowspec_issue_redistribute
[mirror_frr.git] / bgpd / bgpd.h
index 7d815790097314b222a9cc461f4050df6141b655..3f33139ef2389a1d4c7a47582f70c9278e4b3f96 100644 (file)
@@ -65,6 +65,12 @@ enum { AS_UNSPECIFIED = 0,
        AS_EXTERNAL,
 };
 
+/* Zebra Gracaful Restart states */
+enum zebra_gr_mode {
+       ZEBRA_GR_DISABLE = 0,
+       ZEBRA_GR_ENABLE
+};
+
 /* Typedef BGP specific types.  */
 typedef uint32_t as_t;
 typedef uint16_t as16_t; /* we may still encounter 16 Bit asnums */
@@ -232,6 +238,52 @@ enum bgp_instance_type {
        BGP_INSTANCE_TYPE_VIEW
 };
 
+#define BGP_SEND_EOR(bgp, afi, safi)                           \
+       (!bgp_flag_check(bgp, BGP_FLAG_GR_DISABLE_EOR) &&       \
+       ((bgp->gr_info[afi][safi].t_select_deferral == NULL) || \
+        (bgp->gr_info[afi][safi].eor_required ==               \
+         bgp->gr_info[afi][safi].eor_received)))
+
+/* BGP GR Global ds */
+
+#define BGP_GLOBAL_GR_MODE 4
+#define BGP_GLOBAL_GR_EVENT_CMD 4
+
+/* Graceful restart selection deferral timer info */
+struct graceful_restart_info {
+       /* Count of EOR message expected */
+       uint32_t eor_required;
+       /* Count of EOR received */
+       uint32_t eor_received;
+       /* Deferral Timer */
+       struct thread *t_select_deferral;
+       /* Route list */
+       struct list *route_list;
+       /* Best route select */
+       struct thread *t_route_select;
+       /* AFI, SAFI enabled */
+       bool af_enabled[AFI_MAX][SAFI_MAX];
+       /* Route update completed */
+       bool route_sync[AFI_MAX][SAFI_MAX];
+};
+
+enum global_mode {
+       GLOBAL_HELPER = 0, /* This is the default mode */
+       GLOBAL_GR,
+       GLOBAL_DISABLE,
+       GLOBAL_INVALID
+};
+
+enum global_gr_command {
+       GLOBAL_GR_CMD = 0,
+       NO_GLOBAL_GR_CMD,
+       GLOBAL_DISABLE_CMD,
+       NO_GLOBAL_DISABLE_CMD
+};
+
+#define BGP_GR_SUCCESS 0
+#define BGP_GR_FAILURE 1
+
 /* BGP instance structure.  */
 struct bgp {
        /* AS number of this BGP instance.  */
@@ -356,7 +408,10 @@ struct bgp {
 #define BGP_FLAG_IMPORT_CHECK             (1 << 9)
 #define BGP_FLAG_NO_FAST_EXT_FAILOVER     (1 << 10)
 #define BGP_FLAG_LOG_NEIGHBOR_CHANGES     (1 << 11)
+
+/* This flag is set when we have full BGP Graceful-Restart mode enable */
 #define BGP_FLAG_GRACEFUL_RESTART         (1 << 12)
+
 #define BGP_FLAG_ASPATH_CONFED            (1 << 13)
 #define BGP_FLAG_ASPATH_MULTIPATH_RELAX   (1 << 14)
 #define BGP_FLAG_RR_ALLOW_OUTBOUND_POLICY (1 << 15)
@@ -367,6 +422,17 @@ struct bgp {
 #define BGP_FLAG_GR_PRESERVE_FWD          (1 << 20)
 #define BGP_FLAG_GRACEFUL_SHUTDOWN        (1 << 21)
 #define BGP_FLAG_DELETE_IN_PROGRESS       (1 << 22)
+#define BGP_FLAG_SELECT_DEFER_DISABLE     (1 << 23)
+#define BGP_FLAG_GR_DISABLE_EOR           (1 << 24)
+
+       enum global_mode GLOBAL_GR_FSM[BGP_GLOBAL_GR_MODE]
+                               [BGP_GLOBAL_GR_EVENT_CMD];
+       enum global_mode global_gr_present_state;
+
+       /* This variable stores the current Graceful Restart state of Zebra
+        * - ZEBRA_GR_ENABLE / ZEBRA_GR_DISABLE
+        */
+       enum zebra_gr_mode present_zebra_gr_state;
 
        /* BGP Per AF flags */
        uint16_t af_flags[AFI_MAX][SAFI_MAX];
@@ -462,7 +528,12 @@ struct bgp {
        /* BGP graceful restart */
        uint32_t restart_time;
        uint32_t stalepath_time;
+       uint32_t select_defer_time;
+       struct graceful_restart_info gr_info[AFI_MAX][SAFI_MAX];
+       uint32_t rib_stale_time;
 
+#define BGP_ROUTE_SELECT_DELAY 1
+#define BGP_MAX_BEST_ROUTE_SELECT 10000
        /* Maximum-paths configuration */
        struct bgp_maxpaths_cfg {
                uint16_t maxpaths_ebgp;
@@ -548,7 +619,6 @@ struct bgp {
 #define BGP_VRF_RD_CFGD                     (1 << 3)
 #define BGP_VRF_L3VNI_PREFIX_ROUTES_ONLY    (1 << 4)
 
-
        /* unique ID for auto derivation of RD for this vrf */
        uint16_t vrf_rd_id;
 
@@ -589,6 +659,13 @@ DECLARE_HOOK(bgp_inst_config_write,
                (struct bgp *bgp, struct vty *vty),
                (bgp, vty))
 
+       /* Thread callback information */
+       struct afi_safi_info {
+               afi_t afi;
+               safi_t safi;
+               struct bgp *bgp;
+       };
+
 #define BGP_ROUTE_ADV_HOLD(bgp) (bgp->main_peers_update_hold)
 
 #define IS_BGP_INST_KNOWN_TO_ZEBRA(bgp)                                        \
@@ -596,6 +673,9 @@ DECLARE_HOOK(bgp_inst_config_write,
         || (bgp->inst_type == BGP_INSTANCE_TYPE_VRF                           \
             && bgp->vrf_id != VRF_UNKNOWN))
 
+#define BGP_SELECT_DEFER_DISABLE(bgp)                 \
+       (bgp_flag_check(bgp, BGP_FLAG_SELECT_DEFER_DISABLE))
+
 /* BGP peer-group support. */
 struct peer_group {
        /* Name of the peer-group. */
@@ -726,6 +806,36 @@ struct peer_af {
        safi_t safi;
        int afid;
 };
+/* BGP GR per peer ds */
+
+#define BGP_PEER_GR_MODE 5
+#define BGP_PEER_GR_EVENT_CMD 6
+
+enum peer_mode {
+       PEER_HELPER = 0,
+       PEER_GR,
+       PEER_DISABLE,
+       PEER_INVALID,
+       PEER_GLOBAL_INHERIT /* This is the default mode */
+
+};
+
+enum peer_gr_command {
+       PEER_GR_CMD = 0,
+       NO_PEER_GR_CMD,
+       PEER_DISABLE_CMD,
+       NO_PEER_DISABLE_CMD,
+       PEER_HELPER_CMD,
+       NO_PEER_HELPER_CMD
+};
+
+typedef unsigned int  (*bgp_peer_gr_action_ptr)(struct peer *, int, int);
+
+struct bgp_peer_gr {
+       enum peer_mode next_state;
+       bgp_peer_gr_action_ptr action_fun;
+};
+
 
 /* BGP neighbor structure. */
 struct peer {
@@ -947,11 +1057,36 @@ struct peer {
 #define PEER_FLAG_LOCAL_AS                  (1 << 21) /* local-as */
 #define PEER_FLAG_UPDATE_SOURCE             (1 << 22) /* update-source */
 
+       /* BGP-GR Peer related  flags */
+#define PEER_FLAG_GRACEFUL_RESTART_HELPER   (1 << 23) /* Helper */
+#define PEER_FLAG_GRACEFUL_RESTART          (1 << 24) /* Graceful Restart */
+#define PEER_FLAG_GRACEFUL_RESTART_GLOBAL_INHERIT (1 << 25) /* Global-Inherit */
+
+       /*
+        *GR-Disabled mode means unset PEER_FLAG_GRACEFUL_RESTART
+        *& PEER_FLAG_GRACEFUL_RESTART_HELPER
+        *and PEER_FLAG_GRACEFUL_RESTART_GLOBAL_INHERIT
+        */
+
+       struct bgp_peer_gr PEER_GR_FSM[BGP_PEER_GR_MODE][BGP_PEER_GR_EVENT_CMD];
+       enum peer_mode peer_gr_present_state;
+       /* Non stop forwarding afi-safi count for BGP gr feature*/
+       uint8_t nsf_af_count;
+
+       uint8_t peer_gr_new_status_flag;
+#define PEER_GRACEFUL_RESTART_NEW_STATE_HELPER   (1 << 0)
+#define PEER_GRACEFUL_RESTART_NEW_STATE_RESTART  (1 << 1)
+#define PEER_GRACEFUL_RESTART_NEW_STATE_INHERIT  (1 << 2)
+
        /* outgoing message sent in CEASE_ADMIN_SHUTDOWN notify */
        char *tx_shutdown_message;
 
        /* NSF mode (graceful restart) */
        uint8_t nsf[AFI_MAX][SAFI_MAX];
+       /* EOR Send time */
+       time_t eor_stime[AFI_MAX][SAFI_MAX];
+       /* Last update packet sent time */
+       time_t pkt_stime[AFI_MAX][SAFI_MAX];
 
        /* Peer Per AF flags */
        /*
@@ -988,6 +1123,7 @@ struct peer {
 #define PEER_FLAG_WEIGHT                    (1 << 24) /* weight */
 #define PEER_FLAG_ALLOWAS_IN_ORIGIN         (1 << 25) /* allowas-in origin */
 #define PEER_FLAG_SEND_LARGE_COMMUNITY      (1 << 26) /* Send large Communities */
+#define PEER_FLAG_MAX_PREFIX_OUT            (1 << 27) /* outgoing maximum prefix */
 
        enum bgp_addpath_strat addpath_type[AFI_MAX][SAFI_MAX];
 
@@ -1120,9 +1256,6 @@ struct peer {
        /* timestamp when the last msg was written */
        _Atomic time_t last_update;
 
-       /* Send prefix count. */
-       unsigned long scount[AFI_MAX][SAFI_MAX];
-
        /* Notify data. */
        struct bgp_notify notify;
 
@@ -1173,6 +1306,9 @@ struct peer {
        uint16_t pmax_restart[AFI_MAX][SAFI_MAX];
 #define MAXIMUM_PREFIX_THRESHOLD_DEFAULT 75
 
+       /* Send prefix count. */
+       uint32_t pmax_out[AFI_MAX][SAFI_MAX];
+
        /* allowas-in. */
        char allowas_in[AFI_MAX][SAFI_MAX];
 
@@ -1455,6 +1591,8 @@ struct bgp_nlri {
 /* BGP graceful restart  */
 #define BGP_DEFAULT_RESTART_TIME               120
 #define BGP_DEFAULT_STALEPATH_TIME             360
+#define BGP_DEFAULT_SELECT_DEFERRAL_TIME       360
+#define BGP_DEFAULT_RIB_STALE_TIME             500
 
 /* BGP uptime string length.  */
 #define BGP_UPTIME_LEN 25
@@ -1520,6 +1658,11 @@ enum bgp_clear_type {
 #define BGP_ERR_INVALID_FOR_DIRECT_PEER         -34
 #define BGP_ERR_PEER_SAFI_CONFLICT              -35
 
+/* BGP GR ERRORS */
+#define BGP_ERR_GR_INVALID_CMD                  -36
+#define BGP_ERR_GR_OPERATION_FAILED             -37
+#define BGP_GR_NO_OPERATION                     -38
+
 /*
  * Enumeration of different policy kinds a peer can be configured with.
  */
@@ -1772,6 +1915,36 @@ extern int peer_af_delete(struct peer *, afi_t, safi_t);
 
 extern void bgp_close(void);
 extern void bgp_free(struct bgp *);
+void bgp_gr_apply_running_config(void);
+
+/* BGP GR */
+int bgp_global_gr_init(struct bgp *bgp);
+int bgp_peer_gr_init(struct peer *peer);
+
+
+#define BGP_GR_ROUTER_DETECT_AND_SEND_CAPABILITY_TO_ZEBRA( \
+               _bgp, _peer_list) \
+do { \
+       struct peer *peer_loop; \
+       bool gr_router_detected = false; \
+       struct listnode *node = {0}; \
+       struct listnode *nnode = {0}; \
+       for (ALL_LIST_ELEMENTS( \
+                               _peer_list, node, \
+                               nnode, peer_loop)) { \
+               if (CHECK_FLAG( \
+                               peer_loop->flags, \
+                               PEER_FLAG_GRACEFUL_RESTART)) \
+                       gr_router_detected = true; \
+       } \
+       if (gr_router_detected && \
+                       _bgp->present_zebra_gr_state == ZEBRA_GR_DISABLE) { \
+               bgp_zebra_send_capabilities(_bgp, false); \
+       } else if (!gr_router_detected && \
+                       _bgp->present_zebra_gr_state == ZEBRA_GR_ENABLE) { \
+               bgp_zebra_send_capabilities(_bgp, true); \
+       } \
+} while (0)
 
 static inline struct bgp *bgp_lock(struct bgp *bgp)
 {
@@ -1961,5 +2134,6 @@ extern struct peer *peer_lookup_in_view(struct vty *vty, struct bgp *bgp,
 
 /* Hooks */
 DECLARE_HOOK(peer_status_changed, (struct peer * peer), (peer))
+void peer_nsf_stop(struct peer *peer);
 
 #endif /* _QUAGGA_BGPD_H */