Source: ../../bgp/peer.hh
|
|
|
|
// -*- c-basic-offset: 4; tab-width: 8; indent-tabs-mode: t -*-
// Copyright (c) 2001-2005 International Computer Science Institute
//
// Permission is hereby granted, free of charge, to any person obtaining a
// copy of this software and associated documentation files (the "Software")
// to deal in the Software without restriction, subject to the conditions
// listed in the XORP LICENSE file. These conditions include: you must
// preserve this copyright notice, and you cannot mention the copyright
// holders in advertising related to the Software without their permission.
// The Software is provided WITHOUT ANY WARRANTY, EXPRESS OR IMPLIED. This
// notice is a summary of the XORP LICENSE file; the license in that file is
// legally binding.
// $XORP: xorp/bgp/peer.hh,v 1.22 2005/04/09 00:31:40 atanu Exp $
#ifndef __BGP_PEER_HH__
#define __BGP_PEER_HH__
#include <sys/types.h>
#include "socket.hh"
#include "local_data.hh"
#include "peer_data.hh"
enum FSMState {
STATEIDLE = 1,
STATECONNECT = 2,
STATEACTIVE = 3,
STATEOPENSENT = 4,
STATEOPENCONFIRM = 5,
STATEESTABLISHED = 6,
STATESTOPPED = 7 // This state is not in the protocol specification.
// After sending a notify it is necessary to
// close the connection. Data transmission/reception
// is asynchronous, but the close is currently
// synchronous. Thus the stopped state allows
// us to wait for the notify to be sent to TCP,
// before closing the connection.
};
enum FSMEvent {
EVENTBGPSTART = 1,
EVENTBGPSTOP = 2,
EVENTBGPTRANOPEN = 3,
EVENTBGPTRANCLOSED = 4,
EVENTBGPCONNOPENFAIL = 5,
EVENTBGPTRANFATALERR = 6,
EVENTCONNTIMEEXP = 7,
EVENTHOLDTIMEEXP = 8,
EVENTKEEPALIVEEXP = 9,
EVENTRECOPENMESS = 10,
EVENTRECKEEPALIVEMESS = 11,
EVENTRECUPDATEMESS = 12,
EVENTRECNOTMESS = 13
};
enum PeerOutputState {
PEER_OUTPUT_OK = 1,
PEER_OUTPUT_BUSY = 2,
PEER_OUTPUT_FAIL = 3
};
#define OPENMSGOK 0
#define UPDATEMSGOK 0
class BGPMain;
class PeerHandler;
class BGPPeer {
public:
BGPPeer(LocalData *ld, BGPPeerData *pd, SocketClient *sock, BGPMain *m);
virtual ~BGPPeer();
void connected(int s);
int get_sock();
/**
* state machine handlers for the various BGP events
*/
void event_start(); // EVENTBGPSTART
void event_stop(bool restart=false);// EVENTBGPSTOP
void event_open(); // EVENTBGPTRANOPEN
void event_open(const int sock); // EVENTBGPTRANOPEN
void event_closed(); // EVENTBGPTRANCLOSED
void event_openfail(); // EVENTBGPCONNOPENFAIL
void event_tranfatal(); // EVENTBGPTRANFATALERR
void event_connexp(); // EVENTCONNTIMEEXP
void event_holdexp(); // EVENTHOLDTIMEEXP
void event_keepexp(); // EVENTKEEPALIVEEXP
void event_openmess(const OpenPacket& p); // EVENTRECOPENMESS
void event_keepmess(); // EVENTRECKEEPALIVEMESS
void event_recvupdate(const UpdatePacket& p); // EVENTRECUPDATEMESS
void event_recvnotify(const NotificationPacket& p); // EVENTRECNOTMESS
void notify_peer_of_error(const int error, const int subcode,
const uint8_t*data = 0, const size_t len = 0);
FSMState state() { return _state; }
void clear_all_timers();
void start_connect_retry_timer();
void clear_connect_retry_timer();
void restart_connect_retry_timer();
void start_keepalive_timer();
void clear_keepalive_timer();
void start_hold_timer();
void clear_hold_timer();
void restart_hold_timer();
void start_stopped_timer();
void clear_stopped_timer();
bool get_message(BGPPacket::Status status, const uint8_t *buf, size_t len);
PeerOutputState send_message(const BGPPacket& p);
void send_message_complete(SocketClient::Event, const uint8_t *buf);
inline string str() const { return _peername; }
bool is_connected() const { return _SocketClient->is_connected(); }
bool still_reading() const { return _SocketClient->still_reading(); }
LocalData* _localdata;
BGPMain* main() { return _mainprocess; }
const BGPPeerData* peerdata() const { return _peerdata; }
bool ibgp() const { return peerdata()->get_internal_peer(); }
/**
* send the netreachability message, return send result.
*/
bool send_netreachability(const BGPUpdateAttrib &n);
/*
** Virtual so that it can be subclassed in the plumbing test code.
*/
virtual PeerOutputState send_update_message(const UpdatePacket& p);
uint32_t get_established_transitions() const {
return _established_transitions;
}
uint32_t get_established_time() const;
void get_msg_stats(uint32_t& in_updates,
uint32_t& out_updates,
uint32_t& in_msgs,
uint32_t& out_msgs,
uint16_t& last_error,
uint32_t& in_update_elapsed) const;
protected:
private:
friend class BGPPeerList;
void connect_to_peer(SocketClient::ConnectCallback cb) {
_SocketClient->connect(cb);
}
void connect_to_peer_complete(bool success) {
if (success)
event_open(); // Event = EVENTBGPTRANOPEN
else
event_openfail(); // Event = EVENTBGPCONNOPENFAIL
}
void send_notification(const NotificationPacket& p, bool restart = true);
void send_notification_complete(SocketClient::Event, const uint8_t *buf,
bool restart);
void flush_transmit_queue() { _SocketClient->flush_transmit_queue(); }
void stop_reader() { _SocketClient->stop_reader(); }
SocketClient *_SocketClient;
bool _output_queue_was_busy;
FSMState _state;
BGPPeerData* _peerdata;
BGPMain* _mainprocess;
PeerHandler *_handler;
string _peername;
XorpTimer _timer_connect_retry;
XorpTimer _timer_hold_time;
XorpTimer _timer_keep_alive;
// counters needed for the BGP MIB
uint32_t _in_updates;
uint32_t _out_updates;
uint32_t _in_total_messages;
uint32_t _out_total_messages;
uint8_t _last_error[2];
uint32_t _established_transitions;
TimeVal _established_time;
TimeVal _in_update_time;
/**
* This timer is to break us out of the stopped state.
*/
XorpTimer _timer_stopped;
void hook_stopped();
void check_open_packet(const OpenPacket *p) throw (CorruptMessage);
NotificationPacket* check_update_packet(const UpdatePacket *p);
/**
* Called the first time that we go to the established state.
*/
bool established();
bool release_resources();
/**
* move to the desired state, plus does some additional
* work to clean up existing state and possibly retrying to
* open/connect if restart = true
*/
void set_state(FSMState s, bool restart = false);
static const char *pretty_print_state(FSMState s);
bool remote_ip_ge_than(const BGPPeer& peer);
private:
friend class BGPMain;
bool _current_state;
void set_current_peer_state(bool state) {_current_state = state;}
bool get_current_peer_state() {return _current_state;}
bool _next_state;
void set_next_peer_state(bool state) {_next_state = state;}
bool get_next_peer_state() {return _next_state;}
bool _activated;
void set_activate_state(bool state) {_activated = state;}
bool get_activate_state() {return _activated;}
};
#endif // __BGP_PEER_HH__
Generated by: pavlin on possum.icir.org on Wed Apr 13 21:53:16 2005, using kdoc $.