diff options
Diffstat (limited to 'packet/bgp/bgp.go')
-rw-r--r-- | packet/bgp/bgp.go | 63 |
1 files changed, 45 insertions, 18 deletions
diff --git a/packet/bgp/bgp.go b/packet/bgp/bgp.go index 034a2bcb..a32ce069 100644 --- a/packet/bgp/bgp.go +++ b/packet/bgp/bgp.go @@ -590,52 +590,79 @@ func (m BGPAddPathMode) String() string { } } -type CapAddPath struct { - DefaultParameterCapability +type CapAddPathTuple struct { RouteFamily RouteFamily Mode BGPAddPathMode } +func (t *CapAddPathTuple) MarshalJSON() ([]byte, error) { + return json.Marshal(struct { + RouteFamily RouteFamily `json:"family"` + Mode uint8 `json:"mode"` + }{ + RouteFamily: t.RouteFamily, + Mode: uint8(t.Mode), + }) +} + +func NewCapAddPathTuple(family RouteFamily, mode BGPAddPathMode) *CapAddPathTuple { + return &CapAddPathTuple{ + RouteFamily: family, + Mode: mode, + } +} + +type CapAddPath struct { + DefaultParameterCapability + Tuples []*CapAddPathTuple +} + func (c *CapAddPath) DecodeFromBytes(data []byte) error { c.DefaultParameterCapability.DecodeFromBytes(data) data = data[2:] if len(data) < 4 { return NewMessageError(BGP_ERROR_OPEN_MESSAGE_ERROR, BGP_ERROR_SUB_UNSUPPORTED_CAPABILITY, nil, "Not all CapabilityAddPath bytes available") } - c.RouteFamily = AfiSafiToRouteFamily(binary.BigEndian.Uint16(data[:2]), data[2]) - c.Mode = BGPAddPathMode(data[3]) + c.Tuples = []*CapAddPathTuple{} + for len(data) >= 4 { + t := &CapAddPathTuple{ + RouteFamily: AfiSafiToRouteFamily(binary.BigEndian.Uint16(data[:2]), data[2]), + Mode: BGPAddPathMode(data[3]), + } + c.Tuples = append(c.Tuples, t) + data = data[4:] + } return nil } func (c *CapAddPath) Serialize() ([]byte, error) { - buf := make([]byte, 4) - afi, safi := RouteFamilyToAfiSafi(c.RouteFamily) - binary.BigEndian.PutUint16(buf, afi) - buf[2] = safi - buf[3] = byte(c.Mode) + buf := make([]byte, len(c.Tuples)*4) + for i, t := range c.Tuples { + afi, safi := RouteFamilyToAfiSafi(t.RouteFamily) + binary.BigEndian.PutUint16(buf[i*4:i*4+2], afi) + buf[i*4+2] = safi + buf[i*4+3] = byte(t.Mode) + } c.DefaultParameterCapability.CapValue = buf return c.DefaultParameterCapability.Serialize() } func (c *CapAddPath) MarshalJSON() ([]byte, error) { return json.Marshal(struct { - Code BGPCapabilityCode `json:"code"` - Value RouteFamily `json:"value"` - Mode BGPAddPathMode `json:"mode"` + Code BGPCapabilityCode `json:"code"` + Tuples []*CapAddPathTuple `json:"tuples"` }{ - Code: c.Code(), - Value: c.RouteFamily, - Mode: c.Mode, + Code: c.Code(), + Tuples: c.Tuples, }) } -func NewCapAddPath(rf RouteFamily, mode BGPAddPathMode) *CapAddPath { +func NewCapAddPath(tuples []*CapAddPathTuple) *CapAddPath { return &CapAddPath{ DefaultParameterCapability: DefaultParameterCapability{ CapCode: BGP_CAP_ADD_PATH, }, - RouteFamily: rf, - Mode: mode, + Tuples: tuples, } } |