The BGP FSM is not currently correct enough for production use. Its core transition table roughly follows RFC 4271, but the surrounding event plumbing violates the specification in several important cases.
-
Process
ConnectRetryTimerExpiresevents. The timer is created and started, and the FSM defines transitions for its expiry, butSession::tick()never selects onconnect_retry_timer.tick(). -
Route TCP EOF and read errors through the FSM as
TcpConnectionFailsinstead of directly forcingState::Connect. In particular, a failure inEstablishedmust transition toIdleand perform the required cleanup and counter handling. -
Preserve the FSM's error transition. Invalid OPEN processing sets the state to
Idleand returns an error, butSession::tick()overwrites that state withConnect;Session::process()then terminates the session task. -
Do not forward an UPDATE to the application after the FSM has rejected it.
handle_msg()currently forwards the UPDATE even when, for example, an UPDATE inOpenSentcaused an FSM-error notification, disconnection, and a transition toIdle. -
Make
Command::Disconnectperform the appropriate FSM transition. Callingdisconnect()currently removes the connection and stops timers but can leave the state asEstablished. -
Stop, rather than start, the ConnectRetryTimer after successful TCP establishment in
Activewhen DelayOpen is disabled. -
Make
Timer::start()idempotent or prevent it from being called while the timer is running. Each call currently spawns a new task and overwrites the old stop handle, which can create orphan timers and duplicate events. -
Implement RFC 4271 section 6.8 connection-collision handling. Second TCP connections in
OpenSent,OpenConfirm, andEstablishedare currently ignored instead of being tracked until OPEN-based collision resolution. -
Validate ROUTE-REFRESH messages against the FSM state and negotiated capability instead of silently ignoring them in every state.
-
Add table-driven FSM tests covering every supported
(State, Event)pair, resulting state, timer effects, counters, emitted messages, connection lifecycle, and application-visible messages. The old transition tests insrc/bgp/fsm/session.rsare disabled inside a/* FIXME ... */block. The currentcargo test --all-featuressuite passes, but it does not validate the FSM transition matrix.
Reference: RFC 4271 section 8.