diff options
author | FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp> | 2014-12-31 14:37:56 +0900 |
---|---|---|
committer | FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp> | 2014-12-31 14:37:56 +0900 |
commit | 04f90d2087d3a0741527d5ee111f7a3900e0687b (patch) | |
tree | ebb0ce48c5606814c4f48b396a3e3c0697789839 | |
parent | bb7f960572bba5ce1ddbded69e8315667e87d4c4 (diff) |
server: handle peer not capable of four byte AS number
Signed-off-by: FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp>
-rw-r--r-- | packet/bgp.go | 5 | ||||
-rw-r--r-- | server/fsm.go | 1 | ||||
-rw-r--r-- | server/peer.go | 26 |
3 files changed, 30 insertions, 2 deletions
diff --git a/packet/bgp.go b/packet/bgp.go index 60502e1a..527ebb7a 100644 --- a/packet/bgp.go +++ b/packet/bgp.go @@ -68,6 +68,7 @@ type ParameterCapabilityInterface interface { DecodeFromBytes([]byte) error Serialize() ([]byte, error) Len() int + Code() BGPCapabilityCode } type DefaultParameterCapability struct { @@ -76,6 +77,10 @@ type DefaultParameterCapability struct { CapValue []byte } +func (c *DefaultParameterCapability) Code() BGPCapabilityCode { + return c.CapCode +} + func (c *DefaultParameterCapability) DecodeFromBytes(data []byte) error { c.CapCode = BGPCapabilityCode(data[0]) c.CapLen = data[1] diff --git a/server/fsm.go b/server/fsm.go index de64a7fa..e215450a 100644 --- a/server/fsm.go +++ b/server/fsm.go @@ -264,6 +264,7 @@ func (h *FSMHandler) opensent() bgp.FSMState { if ok { fsm.bgpMessageStateUpdate(m.Header.Type, true) if m.Header.Type == bgp.BGP_MSG_OPEN { + fsm.incoming <- m fsm.routerId = m.Body.(*bgp.BGPOpen).ID msg := bgp.NewBGPKeepAliveMessage() b, _ := msg.Serialize() diff --git a/server/peer.go b/server/peer.go index b8dd2781..8379d079 100644 --- a/server/peer.go +++ b/server/peer.go @@ -42,7 +42,8 @@ type Peer struct { // here but it's the simplest and works our first target. rib *table.TableManager // for now we support only the same afi as transport - rf bgp.RouteFamily + rf bgp.RouteFamily + capMap map[bgp.BGPCapabilityCode]bgp.ParameterCapabilityInterface } func NewPeer(g config.GlobalType, peer config.NeighborType, outEventCh chan *message) *Peer { @@ -54,6 +55,7 @@ func NewPeer(g config.GlobalType, peer config.NeighborType, outEventCh chan *mes outgoing: make(chan *bgp.BGPMessage, 4096), inEventCh: make(chan *message, 4096), outEventCh: outEventCh, + capMap: make(map[bgp.BGPCapabilityCode]bgp.ParameterCapabilityInterface), } p.fsm = NewFSM(&g, &peer, p.acceptedConnCh, p.incoming, p.outgoing) peer.BgpNeighborCommonState.State = uint32(bgp.BGP_FSM_IDLE) @@ -73,11 +75,25 @@ func (peer *Peer) handleBGPmessage(m *bgp.BGPMessage) { log.Debug(string(j)) switch m.Header.Type { + case bgp.BGP_MSG_OPEN: + body := m.Body.(*bgp.BGPOpen) + for _, p := range body.OptParams { + paramCap, y := p.(*bgp.OptionParameterCapability) + if !y { + continue + } + for _, c := range paramCap.Capability { + peer.capMap[c.Code()] = c + } + } + case bgp.BGP_MSG_ROUTE_REFRESH: pathList := peer.adjRib.GetOutPathList(peer.rf) peer.sendMessages(peer.path2update(pathList)) case bgp.BGP_MSG_UPDATE: peer.peerConfig.BgpNeighborCommonState.UpdateRecvTime = time.Now() + body := m.Body.(*bgp.BGPUpdate) + table.UpdatePathAttrs4ByteAs(body) msg := table.NewProcessMessage(m, peer.fsm.peerInfo) pathList := msg.ToPathList() if len(pathList) == 0 { @@ -90,12 +106,18 @@ func (peer *Peer) handleBGPmessage(m *bgp.BGPMessage) { func (peer *Peer) sendMessages(msgs []*bgp.BGPMessage) { for _, m := range msgs { + if m.Header.Type == bgp.BGP_MSG_UPDATE { + _, y := peer.capMap[bgp.BGP_CAP_FOUR_OCTET_AS_NUMBER] + if !y { + log.Debug("update BGPUpdate for 2byte AS peer, ", peer.peerConfig.NeighborAddress.String()) + table.UpdatePathAttrs2ByteAs(m.Body.(*bgp.BGPUpdate)) + } + } peer.outgoing <- m } } func (peer *Peer) path2update(pathList []table.Path) []*bgp.BGPMessage { - // TODO: 4bytes and 2bytes conversion. msgs := make([]*bgp.BGPMessage, 0) var pMsg *bgp.BGPMessage for _, p := range pathList { |