Diff for /embedaddon/quagga/bgpd/bgp_fsm.c between versions 1.1.1.3 and 1.1.1.4

version 1.1.1.3, 2013/07/21 23:54:37 version 1.1.1.4, 2016/11/02 10:09:10
Line 30  Software Foundation, Inc., 59 Temple Place - Suite 330 Line 30  Software Foundation, Inc., 59 Temple Place - Suite 330
 #include "stream.h"  #include "stream.h"
 #include "memory.h"  #include "memory.h"
 #include "plist.h"  #include "plist.h"
   #include "workqueue.h"
   #include "filter.h"
   
 #include "bgpd/bgpd.h"  #include "bgpd/bgpd.h"
 #include "bgpd/bgp_attr.h"  #include "bgpd/bgp_attr.h"
Line 43  Software Foundation, Inc., 59 Temple Place - Suite 330 Line 45  Software Foundation, Inc., 59 Temple Place - Suite 330
 #ifdef HAVE_SNMP  #ifdef HAVE_SNMP
 #include "bgpd/bgp_snmp.h"  #include "bgpd/bgp_snmp.h"
 #endif /* HAVE_SNMP */  #endif /* HAVE_SNMP */
 /* BGP FSM (finite state machine) has three types of functions.  Type  /* BGP FSM (finite state machine) has three types of functions.  Type
    one is thread functions.  Type two is event functions.  Type three     one is thread functions.  Type two is event functions.  Type three
    is FSM functions.  Timer functions are set by bgp_timer_set     is FSM functions.  Timer functions are set by bgp_timer_set
Line 65  static int bgp_start (struct peer *); Line 67  static int bgp_start (struct peer *);
 static int  static int
 bgp_start_jitter (int time)  bgp_start_jitter (int time)
 {  {
  return ((rand () % (time + 1)) - (time / 2));  return ((random () % (time + 1)) - (time / 2));
 }  }
   
 /* Check if suppress start/restart of sessions to peer. */  /* Check if suppress start/restart of sessions to peer. */
Line 100  bgp_timer_set (struct peer *peer) Line 102  bgp_timer_set (struct peer *peer)
       BGP_TIMER_OFF (peer->t_connect);        BGP_TIMER_OFF (peer->t_connect);
       BGP_TIMER_OFF (peer->t_holdtime);        BGP_TIMER_OFF (peer->t_holdtime);
       BGP_TIMER_OFF (peer->t_keepalive);        BGP_TIMER_OFF (peer->t_keepalive);
       BGP_TIMER_OFF (peer->t_asorig);  
       BGP_TIMER_OFF (peer->t_routeadv);        BGP_TIMER_OFF (peer->t_routeadv);
       break;        break;
   
Line 112  bgp_timer_set (struct peer *peer) Line 113  bgp_timer_set (struct peer *peer)
       BGP_TIMER_ON (peer->t_connect, bgp_connect_timer, peer->v_connect);        BGP_TIMER_ON (peer->t_connect, bgp_connect_timer, peer->v_connect);
       BGP_TIMER_OFF (peer->t_holdtime);        BGP_TIMER_OFF (peer->t_holdtime);
       BGP_TIMER_OFF (peer->t_keepalive);        BGP_TIMER_OFF (peer->t_keepalive);
       BGP_TIMER_OFF (peer->t_asorig);  
       BGP_TIMER_OFF (peer->t_routeadv);        BGP_TIMER_OFF (peer->t_routeadv);
       break;        break;
   
Line 132  bgp_timer_set (struct peer *peer) Line 132  bgp_timer_set (struct peer *peer)
         }          }
       BGP_TIMER_OFF (peer->t_holdtime);        BGP_TIMER_OFF (peer->t_holdtime);
       BGP_TIMER_OFF (peer->t_keepalive);        BGP_TIMER_OFF (peer->t_keepalive);
       BGP_TIMER_OFF (peer->t_asorig);  
       BGP_TIMER_OFF (peer->t_routeadv);        BGP_TIMER_OFF (peer->t_routeadv);
       break;        break;
   
Line 150  bgp_timer_set (struct peer *peer) Line 149  bgp_timer_set (struct peer *peer)
           BGP_TIMER_OFF (peer->t_holdtime);            BGP_TIMER_OFF (peer->t_holdtime);
         }          }
       BGP_TIMER_OFF (peer->t_keepalive);        BGP_TIMER_OFF (peer->t_keepalive);
       BGP_TIMER_OFF (peer->t_asorig);  
       BGP_TIMER_OFF (peer->t_routeadv);        BGP_TIMER_OFF (peer->t_routeadv);
       break;        break;
   
Line 173  bgp_timer_set (struct peer *peer) Line 171  bgp_timer_set (struct peer *peer)
           BGP_TIMER_ON (peer->t_keepalive, bgp_keepalive_timer,             BGP_TIMER_ON (peer->t_keepalive, bgp_keepalive_timer, 
                         peer->v_keepalive);                          peer->v_keepalive);
         }          }
       BGP_TIMER_OFF (peer->t_asorig);  
       BGP_TIMER_OFF (peer->t_routeadv);        BGP_TIMER_OFF (peer->t_routeadv);
       break;        break;
   
Line 197  bgp_timer_set (struct peer *peer) Line 194  bgp_timer_set (struct peer *peer)
           BGP_TIMER_ON (peer->t_keepalive, bgp_keepalive_timer,            BGP_TIMER_ON (peer->t_keepalive, bgp_keepalive_timer,
                         peer->v_keepalive);                          peer->v_keepalive);
         }          }
       BGP_TIMER_OFF (peer->t_asorig);  
       break;        break;
     case Deleted:      case Deleted:
       BGP_TIMER_OFF (peer->t_gr_restart);        BGP_TIMER_OFF (peer->t_gr_restart);
Line 208  bgp_timer_set (struct peer *peer) Line 204  bgp_timer_set (struct peer *peer)
       BGP_TIMER_OFF (peer->t_connect);        BGP_TIMER_OFF (peer->t_connect);
       BGP_TIMER_OFF (peer->t_holdtime);        BGP_TIMER_OFF (peer->t_holdtime);
       BGP_TIMER_OFF (peer->t_keepalive);        BGP_TIMER_OFF (peer->t_keepalive);
       BGP_TIMER_OFF (peer->t_asorig);  
       BGP_TIMER_OFF (peer->t_routeadv);        BGP_TIMER_OFF (peer->t_routeadv);
     }      }
 }  }
Line 406  bgp_fsm_change_status (struct peer *peer, int status) Line 401  bgp_fsm_change_status (struct peer *peer, int status)
    * (and must do so before actually changing into Deleted..     * (and must do so before actually changing into Deleted..
    */     */
   if (status >= Clearing)    if (status >= Clearing)
    bgp_clear_route_all (peer);    {
       bgp_clear_route_all (peer);
 
       /* If no route was queued for the clear-node processing, generate the
        * completion event here. This is needed because if there are no routes
        * to trigger the background clear-node thread, the event won't get
        * generated and the peer would be stuck in Clearing. Note that this
        * event is for the peer and helps the peer transition out of Clearing
        * state; it should not be generated per (AFI,SAFI). The event is
        * directly posted here without calling clear_node_complete() as we
        * shouldn't do an extra unlock. This event will get processed after
        * the state change that happens below, so peer will be in Clearing
        * (or Deleted).
        */
       if (!work_queue_is_scheduled (peer->clear_node_queue))
         BGP_EVENT_ADD (peer, Clearing_Completed);
     }
       
   /* Preserve old status and change into new status. */    /* Preserve old status and change into new status. */
   peer->ostatus = peer->status;    peer->ostatus = peer->status;
Line 505  bgp_stop (struct peer *peer) Line 516  bgp_stop (struct peer *peer)
   BGP_TIMER_OFF (peer->t_connect);    BGP_TIMER_OFF (peer->t_connect);
   BGP_TIMER_OFF (peer->t_holdtime);    BGP_TIMER_OFF (peer->t_holdtime);
   BGP_TIMER_OFF (peer->t_keepalive);    BGP_TIMER_OFF (peer->t_keepalive);
   BGP_TIMER_OFF (peer->t_asorig);  
   BGP_TIMER_OFF (peer->t_routeadv);    BGP_TIMER_OFF (peer->t_routeadv);
   
   /* Stream reset. */    /* Stream reset. */
Line 545  bgp_stop (struct peer *peer) Line 555  bgp_stop (struct peer *peer)
   
         /* ORF received prefix-filter pnt */          /* ORF received prefix-filter pnt */
         sprintf (orf_name, "%s.%d.%d", peer->host, afi, safi);          sprintf (orf_name, "%s.%d.%d", peer->host, afi, safi);
        prefix_bgp_orf_remove_all (orf_name);        prefix_bgp_orf_remove_all (afi, orf_name);
       }        }
   
   /* Reset keepalive and holdtime */    /* Reset keepalive and holdtime */
Line 592  bgp_stop_with_error (struct peer *peer) Line 602  bgp_stop_with_error (struct peer *peer)
   return 0;    return 0;
 }  }
   
   
   /* something went wrong, send notify and tear down */
   static int
   bgp_stop_with_notify (struct peer *peer, u_char code, u_char sub_code)
   {
     /* Send notify to remote peer */
     bgp_notify_send (peer, code, sub_code);
   
     /* Sweep if it is temporary peer. */
     if (CHECK_FLAG (peer->sflags, PEER_STATUS_ACCEPT_PEER))
       {
         zlog_info ("%s [Event] Accepting BGP peer is deleted", peer->host);
         peer_delete (peer);
         return -1;
       }
   
     /* Clear start timer value to default. */
     peer->v_start = BGP_INIT_START_TIMER;
   
     /* bgp_stop needs to be invoked while in Established state */
     bgp_stop(peer);
   
     return 0;
   }
   
   
 /* TCP connection open.  Next we send open message to remote peer. And  /* TCP connection open.  Next we send open message to remote peer. And
    add read thread for reading open message. */     add read thread for reading open message. */
 static int  static int
Line 740  bgp_fsm_keepalive_expire (struct peer *peer) Line 776  bgp_fsm_keepalive_expire (struct peer *peer)
   return 0;    return 0;
 }  }
   
   /* FSM error, unexpected event.  This is error of BGP connection. So cut the
      peer and change to Idle status. */
   static int
   bgp_fsm_event_error (struct peer *peer)
   {
     plog_err (peer->log, "%s [FSM] unexpected packet received in state %s",
               peer->host, LOOKUP (bgp_status_msg, peer->status));
   
     return bgp_stop_with_notify (peer, BGP_NOTIFY_FSM_ERR, 0);
   }
   
 /* Hold timer expire.  This is error of BGP connection. So cut the  /* Hold timer expire.  This is error of BGP connection. So cut the
    peer and change to Idle status. */     peer and change to Idle status. */
 static int  static int
 bgp_fsm_holdtime_expire (struct peer *peer)  bgp_fsm_holdtime_expire (struct peer *peer)
 {  {
   if (BGP_DEBUG (fsm, FSM))    if (BGP_DEBUG (fsm, FSM))
    zlog (peer->log, LOG_DEBUG, "%s [FSM] Hold timer expire", peer->host);    plog_debug (peer->log, "%s [FSM] Hold timer expire", peer->host);
   
  /* Send notify to remote peer. */  return bgp_stop_with_notify (peer, BGP_NOTIFY_HOLD_ERR, 0);
  bgp_notify_send (peer, BGP_NOTIFY_HOLD_ERR, 0); 
 
  /* Sweep if it is temporary peer. */ 
  if (CHECK_FLAG (peer->sflags, PEER_STATUS_ACCEPT_PEER)) 
    { 
      zlog_info ("%s [Event] Accepting BGP peer is deleted", peer->host); 
      peer_delete (peer); 
      return -1; 
    } 
 
  /* bgp_stop needs to be invoked while in Established state */ 
  bgp_stop(peer); 
 
  return 0; 
 }  }
   
 /* Status goes to Established.  Send keepalive packet then make first  /* Status goes to Established.  Send keepalive packet then make first
Line 905  bgp_ignore (struct peer *peer) Line 938  bgp_ignore (struct peer *peer)
     zlog (peer->log, LOG_DEBUG, "%s [FSM] bgp_ignore called", peer->host);      zlog (peer->log, LOG_DEBUG, "%s [FSM] bgp_ignore called", peer->host);
   return 0;    return 0;
 }  }
 /* Finite State Machine structure */  /* Finite State Machine structure */
 static const struct {  static const struct {
   int (*func) (struct peer *);    int (*func) (struct peer *);
Line 977  static const struct { Line 1010  static const struct {
     {bgp_fsm_holdtime_expire, Idle},    /* Hold_Timer_expired           */      {bgp_fsm_holdtime_expire, Idle},    /* Hold_Timer_expired           */
     {bgp_ignore,  Idle},        /* KeepAlive_timer_expired      */      {bgp_ignore,  Idle},        /* KeepAlive_timer_expired      */
     {bgp_fsm_open,    OpenConfirm},     /* Receive_OPEN_message         */      {bgp_fsm_open,    OpenConfirm},     /* Receive_OPEN_message         */
    {bgp_ignore,  Idle}, /* Receive_KEEPALIVE_message    */    {bgp_fsm_event_error, Idle}, /* Receive_KEEPALIVE_message    */
    {bgp_ignore,  Idle}, /* Receive_UPDATE_message       */    {bgp_fsm_event_error, Idle}, /* Receive_UPDATE_message       */
     {bgp_stop_with_error, Idle}, /* Receive_NOTIFICATION_message */      {bgp_stop_with_error, Idle}, /* Receive_NOTIFICATION_message */
     {bgp_ignore, Idle},         /* Clearing_Completed           */      {bgp_ignore, Idle},         /* Clearing_Completed           */
   },    },

Removed from v.1.1.1.3  
changed lines
  Added in v.1.1.1.4


FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>