BGPSpeaker: Support IPv6 Flow Spec update messages
Signed-off-by: Satoshi Fujimoto <satoshi.fujimoto7@gmail.com> Signed-off-by: FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp>
This commit is contained in:
parent
4d9d444df1
commit
7e6c648ba1
|
@ -27,7 +27,9 @@ from ryu.lib.packet.bgp import EvpnEthernetSegmentNLRI
|
|||
from ryu.lib.packet.bgp import EvpnIpPrefixNLRI
|
||||
from ryu.lib.packet.bgp import BGPPathAttributePmsiTunnel
|
||||
from ryu.lib.packet.bgp import FlowSpecIPv4NLRI
|
||||
from ryu.lib.packet.bgp import FlowSpecIPv6NLRI
|
||||
from ryu.lib.packet.bgp import FlowSpecVPNv4NLRI
|
||||
from ryu.lib.packet.bgp import FlowSpecVPNv6NLRI
|
||||
from ryu.lib.packet.bgp import BGPFlowSpecTrafficRateCommunity
|
||||
from ryu.lib.packet.bgp import BGPFlowSpecTrafficActionCommunity
|
||||
from ryu.lib.packet.bgp import BGPFlowSpecRedirectCommunity
|
||||
|
@ -103,10 +105,14 @@ SUPPORTED_EVPN_ROUTE_TYPES = [
|
|||
|
||||
# Constants used in API calls for Flow Specification
|
||||
FLOWSPEC_FAMILY_IPV4 = FlowSpecIPv4NLRI.FLOWSPEC_FAMILY
|
||||
FLOWSPEC_FAMILY_IPV6 = FlowSpecIPv6NLRI.FLOWSPEC_FAMILY
|
||||
FLOWSPEC_FAMILY_VPNV4 = FlowSpecVPNv4NLRI.FLOWSPEC_FAMILY
|
||||
FLOWSPEC_FAMILY_VPNV6 = FlowSpecVPNv6NLRI.FLOWSPEC_FAMILY
|
||||
SUPPORTED_FLOWSPEC_FAMILIES = (
|
||||
FLOWSPEC_FAMILY_IPV4,
|
||||
FLOWSPEC_FAMILY_IPV6,
|
||||
FLOWSPEC_FAMILY_VPNV4,
|
||||
FLOWSPEC_FAMILY_VPNV6,
|
||||
)
|
||||
|
||||
# Constants for the Traffic Filtering Actions of Flow Specification
|
||||
|
|
|
@ -37,7 +37,9 @@ from ryu.lib.packet.bgp import RF_IPv4_VPN
|
|||
from ryu.lib.packet.bgp import RF_IPv6_VPN
|
||||
from ryu.lib.packet.bgp import RF_L2_EVPN
|
||||
from ryu.lib.packet.bgp import RF_IPv4_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_IPv6_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_VPNv4_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_VPNv6_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_RTC_UC
|
||||
from ryu.services.protocols.bgp.utils.circlist import CircularListType
|
||||
from ryu.services.protocols.bgp.utils.evtlet import LoopingCall
|
||||
|
@ -59,7 +61,9 @@ SUPPORTED_GLOBAL_RF = {
|
|||
RF_IPv6_VPN,
|
||||
RF_L2_EVPN,
|
||||
RF_IPv4_FLOWSPEC,
|
||||
RF_IPv6_FLOWSPEC,
|
||||
RF_VPNv4_FLOWSPEC,
|
||||
RF_VPNv6_FLOWSPEC,
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -4,6 +4,7 @@ from ryu.services.protocols.bgp.bgpspeaker import RF_VPN_V4
|
|||
from ryu.services.protocols.bgp.bgpspeaker import RF_VPN_V6
|
||||
from ryu.services.protocols.bgp.bgpspeaker import RF_L2_EVPN
|
||||
from ryu.services.protocols.bgp.bgpspeaker import RF_VPNV4_FLOWSPEC
|
||||
from ryu.services.protocols.bgp.bgpspeaker import RF_VPNV6_FLOWSPEC
|
||||
from ryu.services.protocols.bgp.bgpspeaker import EVPN_MAX_ET
|
||||
from ryu.services.protocols.bgp.bgpspeaker import ESI_TYPE_LACP
|
||||
from ryu.services.protocols.bgp.bgpspeaker import ESI_TYPE_MAC_BASED
|
||||
|
@ -14,7 +15,9 @@ from ryu.services.protocols.bgp.bgpspeaker import EVPN_MULTICAST_ETAG_ROUTE
|
|||
from ryu.services.protocols.bgp.bgpspeaker import EVPN_ETH_SEGMENT
|
||||
from ryu.services.protocols.bgp.bgpspeaker import EVPN_IP_PREFIX_ROUTE
|
||||
from ryu.services.protocols.bgp.bgpspeaker import FLOWSPEC_FAMILY_IPV4
|
||||
from ryu.services.protocols.bgp.bgpspeaker import FLOWSPEC_FAMILY_IPV6
|
||||
from ryu.services.protocols.bgp.bgpspeaker import FLOWSPEC_FAMILY_VPNV4
|
||||
from ryu.services.protocols.bgp.bgpspeaker import FLOWSPEC_FAMILY_VPNV6
|
||||
from ryu.services.protocols.bgp.bgpspeaker import FLOWSPEC_TA_SAMPLE
|
||||
from ryu.services.protocols.bgp.bgpspeaker import FLOWSPEC_TA_TERMINAL
|
||||
from ryu.services.protocols.bgp.bgpspeaker import REDUNDANCY_MODE_SINGLE_ACTIVE
|
||||
|
@ -54,7 +57,9 @@ BGP = {
|
|||
'address': '172.17.0.4',
|
||||
'remote_as': 65001,
|
||||
'enable_ipv4fs': True,
|
||||
'enable_ipv6fs': True,
|
||||
'enable_vpnv4fs': True,
|
||||
'enable_vpnv6fs': True,
|
||||
},
|
||||
],
|
||||
|
||||
|
@ -83,13 +88,20 @@ BGP = {
|
|||
'export_rts': ['65001:200'],
|
||||
'route_family': RF_L2_EVPN,
|
||||
},
|
||||
# Example of VRF for FlowSpec
|
||||
# Example of VRF for IPv4 FlowSpec
|
||||
{
|
||||
'route_dist': '65001:250',
|
||||
'import_rts': ['65001:250'],
|
||||
'export_rts': ['65001:250'],
|
||||
'route_family': RF_VPNV4_FLOWSPEC,
|
||||
},
|
||||
# Example of VRF for IPv6 FlowSpec
|
||||
{
|
||||
'route_dist': '65001:300',
|
||||
'import_rts': ['65001:300'],
|
||||
'export_rts': ['65001:300'],
|
||||
'route_family': RF_VPNV6_FLOWSPEC,
|
||||
},
|
||||
],
|
||||
|
||||
# List of BGP routes.
|
||||
|
@ -236,6 +248,77 @@ BGP = {
|
|||
}
|
||||
},
|
||||
},
|
||||
# Example of Flow Specification IPv6 prefix
|
||||
{
|
||||
'flowspec_family': FLOWSPEC_FAMILY_IPV6,
|
||||
'rules': {
|
||||
'dst_prefix': '2001::1/128/32',
|
||||
'src_prefix': '3001::2/128',
|
||||
'next_header': 6,
|
||||
'port': '80 | 8000',
|
||||
'dst_port': '>9000 & <9050',
|
||||
'src_port': '>=8500 & <=9000',
|
||||
'icmp_type': 0,
|
||||
'icmp_code': 6,
|
||||
'tcp_flags': 'SYN+ACK & !=URGENT',
|
||||
'packet_len': 1000,
|
||||
'dscp': '22 | 24',
|
||||
'fragment': 'LF | ==FF',
|
||||
'flow_label': 100,
|
||||
},
|
||||
'actions': {
|
||||
'traffic_rate': {
|
||||
'as_number': 0,
|
||||
'rate_info': 100.0,
|
||||
},
|
||||
'traffic_action': {
|
||||
'action': FLOWSPEC_TA_SAMPLE | FLOWSPEC_TA_TERMINAL,
|
||||
},
|
||||
'redirect': {
|
||||
'as_number': 10,
|
||||
'local_administrator': 100,
|
||||
},
|
||||
'traffic_marking': {
|
||||
'dscp': 24,
|
||||
}
|
||||
},
|
||||
},
|
||||
# Example of Flow Specification VPNv6 prefix
|
||||
{
|
||||
'flowspec_family': FLOWSPEC_FAMILY_VPNV6,
|
||||
'route_dist': '65001:300',
|
||||
'rules': {
|
||||
'dst_prefix': '2001::1/128/32',
|
||||
'src_prefix': '3001::2/128',
|
||||
'next_header': 6,
|
||||
'port': '80 | 8000',
|
||||
'dst_port': '>9000 & <9050',
|
||||
'src_port': '>=8500 & <=9000',
|
||||
'icmp_type': 0,
|
||||
'icmp_code': 6,
|
||||
'tcp_flags': 'SYN+ACK & !=URGENT',
|
||||
'packet_len': 1000,
|
||||
'dscp': '22 | 24',
|
||||
'fragment': 'LF | ==FF',
|
||||
'flow_label': 100,
|
||||
},
|
||||
'actions': {
|
||||
'traffic_rate': {
|
||||
'as_number': 0,
|
||||
'rate_info': 100.0,
|
||||
},
|
||||
'traffic_action': {
|
||||
'action': FLOWSPEC_TA_SAMPLE | FLOWSPEC_TA_TERMINAL,
|
||||
},
|
||||
'redirect': {
|
||||
'as_number': 10,
|
||||
'local_administrator': 100,
|
||||
},
|
||||
'traffic_marking': {
|
||||
'dscp': 24,
|
||||
}
|
||||
},
|
||||
},
|
||||
],
|
||||
}
|
||||
|
||||
|
|
|
@ -58,6 +58,8 @@ from ryu.services.protocols.bgp.api.prefix import (
|
|||
FLOWSPEC_FAMILY,
|
||||
FLOWSPEC_FAMILY_IPV4,
|
||||
FLOWSPEC_FAMILY_VPNV4,
|
||||
FLOWSPEC_FAMILY_IPV6,
|
||||
FLOWSPEC_FAMILY_VPNV6,
|
||||
FLOWSPEC_RULES,
|
||||
FLOWSPEC_ACTIONS)
|
||||
from ryu.services.protocols.bgp.rtconf.common import LOCAL_AS
|
||||
|
@ -82,18 +84,24 @@ from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_VPNV4
|
|||
from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_VPNV6
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_EVPN
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_IPV4FS
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_IPV6FS
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_VPNV4FS
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_VPNV6FS
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_ENHANCED_REFRESH
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_FOUR_OCTET_AS_NUMBER
|
||||
from ryu.services.protocols.bgp.rtconf.base import MULTI_EXIT_DISC
|
||||
from ryu.services.protocols.bgp.rtconf.base import SITE_OF_ORIGINS
|
||||
from ryu.services.protocols.bgp.rtconf.neighbors import DEFAULT_CAP_MBGP_IPV4
|
||||
from ryu.services.protocols.bgp.rtconf.neighbors import DEFAULT_CAP_MBGP_IPV6
|
||||
from ryu.services.protocols.bgp.rtconf.neighbors import DEFAULT_CAP_MBGP_VPNV4
|
||||
from ryu.services.protocols.bgp.rtconf.neighbors import DEFAULT_CAP_MBGP_VPNV6
|
||||
from ryu.services.protocols.bgp.rtconf.neighbors import DEFAULT_CAP_MBGP_EVPN
|
||||
from ryu.services.protocols.bgp.rtconf.neighbors import DEFAULT_CAP_MBGP_IPV4FS
|
||||
from ryu.services.protocols.bgp.rtconf.neighbors import DEFAULT_CAP_MBGP_VPNV4FS
|
||||
from ryu.services.protocols.bgp.rtconf.neighbors import (
|
||||
DEFAULT_CAP_MBGP_IPV4,
|
||||
DEFAULT_CAP_MBGP_IPV6,
|
||||
DEFAULT_CAP_MBGP_VPNV4,
|
||||
DEFAULT_CAP_MBGP_VPNV6,
|
||||
DEFAULT_CAP_MBGP_EVPN,
|
||||
DEFAULT_CAP_MBGP_IPV4FS,
|
||||
DEFAULT_CAP_MBGP_IPV6FS,
|
||||
DEFAULT_CAP_MBGP_VPNV4FS,
|
||||
DEFAULT_CAP_MBGP_VPNV6FS,
|
||||
)
|
||||
from ryu.services.protocols.bgp.rtconf.neighbors import (
|
||||
DEFAULT_CAP_ENHANCED_REFRESH, DEFAULT_CAP_FOUR_OCTET_AS_NUMBER)
|
||||
from ryu.services.protocols.bgp.rtconf.neighbors import DEFAULT_CONNECT_MODE
|
||||
|
@ -122,6 +130,7 @@ RF_VPN_V4 = vrfs.VRF_RF_IPV4
|
|||
RF_VPN_V6 = vrfs.VRF_RF_IPV6
|
||||
RF_L2_EVPN = vrfs.VRF_RF_L2_EVPN
|
||||
RF_VPNV4_FLOWSPEC = vrfs.VRF_RF_IPV4_FLOWSPEC
|
||||
RF_VPNV6_FLOWSPEC = vrfs.VRF_RF_IPV6_FLOWSPEC
|
||||
|
||||
# Constants for the Traffic Filtering Actions of Flow Specification.
|
||||
FLOWSPEC_TA_SAMPLE = BGPFlowSpecTrafficActionCommunity.SAMPLE
|
||||
|
@ -354,7 +363,9 @@ class BGPSpeaker(object):
|
|||
enable_vpnv6=DEFAULT_CAP_MBGP_VPNV6,
|
||||
enable_evpn=DEFAULT_CAP_MBGP_EVPN,
|
||||
enable_ipv4fs=DEFAULT_CAP_MBGP_IPV4FS,
|
||||
enable_ipv6fs=DEFAULT_CAP_MBGP_IPV6FS,
|
||||
enable_vpnv4fs=DEFAULT_CAP_MBGP_VPNV4FS,
|
||||
enable_vpnv6fs=DEFAULT_CAP_MBGP_VPNV6FS,
|
||||
enable_enhanced_refresh=DEFAULT_CAP_ENHANCED_REFRESH,
|
||||
enable_four_octet_as_number=DEFAULT_CAP_FOUR_OCTET_AS_NUMBER,
|
||||
next_hop=None, password=None, multi_exit_disc=None,
|
||||
|
@ -394,9 +405,15 @@ class BGPSpeaker(object):
|
|||
``enable_ipv4fs`` enables IPv4 Flow Specification address family
|
||||
for this neighbor.
|
||||
|
||||
``enable_ipv6fs`` enables IPv6 Flow Specification address family
|
||||
for this neighbor.
|
||||
|
||||
``enable_vpnv4fs`` enables VPNv4 Flow Specification address family
|
||||
for this neighbor.
|
||||
|
||||
``enable_vpnv6fs`` enables VPNv6 Flow Specification address family
|
||||
for this neighbor.
|
||||
|
||||
``enable_enhanced_refresh`` enables Enhanced Route Refresh for this
|
||||
neighbor.
|
||||
|
||||
|
@ -457,7 +474,9 @@ class BGPSpeaker(object):
|
|||
CAP_MBGP_VPNV6: enable_vpnv6,
|
||||
CAP_MBGP_EVPN: enable_evpn,
|
||||
CAP_MBGP_IPV4FS: enable_ipv4fs,
|
||||
CAP_MBGP_IPV6FS: enable_ipv6fs,
|
||||
CAP_MBGP_VPNV4FS: enable_vpnv4fs,
|
||||
CAP_MBGP_VPNV6FS: enable_vpnv6fs,
|
||||
}
|
||||
|
||||
if multi_exit_disc:
|
||||
|
@ -821,7 +840,9 @@ class BGPSpeaker(object):
|
|||
This parameter must be one of the following.
|
||||
|
||||
- FLOWSPEC_FAMILY_IPV4 = 'ipv4fs'
|
||||
- FLOWSPEC_FAMILY_IPV6 = 'ipv6fs'
|
||||
- FLOWSPEC_FAMILY_VPNV4 = 'vpnv4fs'
|
||||
- FLOWSPEC_FAMILY_VPNV6 = 'vpnv6fs'
|
||||
|
||||
``rules`` specifies NLRIs of Flow Specification as
|
||||
a dictionary type value.
|
||||
|
@ -829,13 +850,16 @@ class BGPSpeaker(object):
|
|||
see `from_user()` method of the following classes.
|
||||
|
||||
- :py:mod:`ryu.lib.packet.bgp.FlowSpecIPv4NLRI`
|
||||
- :py:mod:`ryu.lib.packet.bgp.FlowSpecIPv6NLRI`
|
||||
- :py:mod:`ryu.lib.packet.bgp.FlowSpecVPNv4NLRI`
|
||||
- :py:mod:`ryu.lib.packet.bgp.FlowSpecVPNv6NLRI`
|
||||
|
||||
``route_dist`` specifies a route distinguisher value.
|
||||
This parameter is required only if flowspec_family is one of the
|
||||
following address family.
|
||||
|
||||
- FLOWSPEC_FAMILY_VPNV4 = 'vpnv4fs'
|
||||
- FLOWSPEC_FAMILY_VPNV6 = 'vpnv6fs'
|
||||
|
||||
``actions`` specifies Traffic Filtering Actions of
|
||||
Flow Specification as a dictionary type value.
|
||||
|
@ -903,7 +927,7 @@ class BGPSpeaker(object):
|
|||
FLOWSPEC_ACTIONS: actions or {},
|
||||
}
|
||||
|
||||
if flowspec_family == FLOWSPEC_FAMILY_VPNV4:
|
||||
if flowspec_family in [FLOWSPEC_FAMILY_VPNV4, FLOWSPEC_FAMILY_VPNV6]:
|
||||
func_name = 'flowspec.add_local'
|
||||
kwargs.update({ROUTE_DISTINGUISHER: route_dist})
|
||||
|
||||
|
@ -927,7 +951,7 @@ class BGPSpeaker(object):
|
|||
FLOWSPEC_RULES: rules,
|
||||
}
|
||||
|
||||
if flowspec_family == FLOWSPEC_FAMILY_VPNV4:
|
||||
if flowspec_family in [FLOWSPEC_FAMILY_VPNV4, FLOWSPEC_FAMILY_VPNV6]:
|
||||
func_name = 'flowspec.del_local'
|
||||
kwargs.update({ROUTE_DISTINGUISHER: route_dist})
|
||||
|
||||
|
@ -953,6 +977,7 @@ class BGPSpeaker(object):
|
|||
- RF_VPN_V6 = 'ipv6'
|
||||
- RF_L2_EVPN = 'evpn'
|
||||
- RF_VPNV4_FLOWSPEC = 'ipv4fs'
|
||||
- RF_VPNV6_FLOWSPEC = 'ipv6fs'
|
||||
|
||||
``multi_exit_disc`` specifies multi exit discriminator (MED) value.
|
||||
It must be an integer.
|
||||
|
|
|
@ -19,12 +19,18 @@ from ryu.services.protocols.bgp.info_base.ipv4fs import IPv4FlowSpecPath
|
|||
from ryu.services.protocols.bgp.info_base.ipv4fs import IPv4FlowSpecTable
|
||||
from ryu.services.protocols.bgp.info_base.vpnv4fs import VPNv4FlowSpecTable
|
||||
from ryu.services.protocols.bgp.info_base.vrf4fs import Vrf4FlowSpecTable
|
||||
from ryu.services.protocols.bgp.info_base.ipv6fs import IPv6FlowSpecPath
|
||||
from ryu.services.protocols.bgp.info_base.ipv6fs import IPv6FlowSpecTable
|
||||
from ryu.services.protocols.bgp.info_base.vpnv6fs import VPNv6FlowSpecTable
|
||||
from ryu.services.protocols.bgp.info_base.vrf6fs import Vrf6FlowSpecTable
|
||||
from ryu.services.protocols.bgp.rtconf.vrfs import VRF_RF_IPV4
|
||||
from ryu.services.protocols.bgp.rtconf.vrfs import VRF_RF_IPV6
|
||||
from ryu.services.protocols.bgp.rtconf.vrfs import VRF_RF_L2_EVPN
|
||||
from ryu.services.protocols.bgp.rtconf.vrfs import VRF_RF_IPV4_FLOWSPEC
|
||||
from ryu.services.protocols.bgp.rtconf.vrfs import VRF_RF_IPV6_FLOWSPEC
|
||||
from ryu.services.protocols.bgp.rtconf.vrfs import SUPPORTED_VRF_RF
|
||||
from ryu.services.protocols.bgp.utils.bgp import create_v4flowspec_actions
|
||||
from ryu.services.protocols.bgp.utils.bgp import create_v6flowspec_actions
|
||||
|
||||
from ryu.lib import type_desc
|
||||
from ryu.lib.packet.bgp import RF_IPv4_UC
|
||||
|
@ -33,7 +39,9 @@ from ryu.lib.packet.bgp import RF_IPv4_VPN
|
|||
from ryu.lib.packet.bgp import RF_IPv6_VPN
|
||||
from ryu.lib.packet.bgp import RF_L2_EVPN
|
||||
from ryu.lib.packet.bgp import RF_IPv4_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_IPv6_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_VPNv4_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_VPNv6_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_RTC_UC
|
||||
from ryu.lib.packet.bgp import BGPPathAttributeOrigin
|
||||
from ryu.lib.packet.bgp import BGPPathAttributeAsPath
|
||||
|
@ -50,6 +58,7 @@ from ryu.lib.packet.bgp import EvpnInclusiveMulticastEthernetTagNLRI
|
|||
from ryu.lib.packet.bgp import IPAddrPrefix
|
||||
from ryu.lib.packet.bgp import IP6AddrPrefix
|
||||
from ryu.lib.packet.bgp import FlowSpecIPv4NLRI
|
||||
from ryu.lib.packet.bgp import FlowSpecIPv6NLRI
|
||||
|
||||
from ryu.services.protocols.bgp.utils.validation import is_valid_ipv4
|
||||
from ryu.services.protocols.bgp.utils.validation import is_valid_ipv4_prefix
|
||||
|
@ -132,6 +141,8 @@ class TableCoreManager(object):
|
|||
vpn_table = self.get_evpn_table()
|
||||
elif vrf_table.route_family == Vrf4FlowSpecTable.ROUTE_FAMILY:
|
||||
vpn_table = self.get_vpnv4fs_table()
|
||||
elif vrf_table.route_family == Vrf6FlowSpecTable.ROUTE_FAMILY:
|
||||
vpn_table = self.get_vpnv6fs_table()
|
||||
else:
|
||||
raise ValueError('Invalid VRF table route family: %s' %
|
||||
vrf_table.route_family)
|
||||
|
@ -200,8 +211,12 @@ class TableCoreManager(object):
|
|||
global_table = self.get_evpn_table()
|
||||
elif route_family == RF_IPv4_FLOWSPEC:
|
||||
global_table = self.get_ipv4fs_table()
|
||||
elif route_family == RF_IPv6_FLOWSPEC:
|
||||
global_table = self.get_ipv6fs_table()
|
||||
elif route_family == RF_VPNv4_FLOWSPEC:
|
||||
global_table = self.get_vpnv4fs_table()
|
||||
elif route_family == RF_VPNv6_FLOWSPEC:
|
||||
global_table = self.get_vpnv6fs_table()
|
||||
elif route_family == RF_RTC_UC:
|
||||
global_table = self.get_rtc_table()
|
||||
|
||||
|
@ -327,6 +342,21 @@ class TableCoreManager(object):
|
|||
|
||||
return ipv4fs_table
|
||||
|
||||
def get_ipv6fs_table(self):
|
||||
"""Returns global IPv6 Flow Specification table.
|
||||
|
||||
Creates the table if it does not exist.
|
||||
"""
|
||||
ipv6fs_table = self._global_tables.get(RF_IPv6_FLOWSPEC)
|
||||
# Lazy initialization of the table.
|
||||
if not ipv6fs_table:
|
||||
ipv6fs_table = IPv6FlowSpecTable(self._core_service,
|
||||
self._signal_bus)
|
||||
self._global_tables[RF_IPv6_FLOWSPEC] = ipv6fs_table
|
||||
self._tables[(None, RF_IPv6_FLOWSPEC)] = ipv6fs_table
|
||||
|
||||
return ipv6fs_table
|
||||
|
||||
def get_vpnv4fs_table(self):
|
||||
"""Returns global VPNv4 Flow Specification table.
|
||||
|
||||
|
@ -342,6 +372,21 @@ class TableCoreManager(object):
|
|||
|
||||
return vpnv4fs_table
|
||||
|
||||
def get_vpnv6fs_table(self):
|
||||
"""Returns global VPNv6 Flow Specification table.
|
||||
|
||||
Creates the table if it does not exist.
|
||||
"""
|
||||
vpnv6fs_table = self._global_tables.get(RF_VPNv6_FLOWSPEC)
|
||||
# Lazy initialization of the table.
|
||||
if not vpnv6fs_table:
|
||||
vpnv6fs_table = VPNv6FlowSpecTable(self._core_service,
|
||||
self._signal_bus)
|
||||
self._global_tables[RF_VPNv6_FLOWSPEC] = vpnv6fs_table
|
||||
self._tables[(None, RF_VPNv6_FLOWSPEC)] = vpnv6fs_table
|
||||
|
||||
return vpnv6fs_table
|
||||
|
||||
def get_nexthop_label(self, label_key):
|
||||
return self._next_hop_label.get(label_key, None)
|
||||
|
||||
|
@ -423,6 +468,8 @@ class TableCoreManager(object):
|
|||
vrf_table = VrfEvpnTable
|
||||
elif route_family == VRF_RF_IPV4_FLOWSPEC:
|
||||
vrf_table = Vrf4FlowSpecTable
|
||||
elif route_family == VRF_RF_IPV6_FLOWSPEC:
|
||||
vrf_table = Vrf6FlowSpecTable
|
||||
else:
|
||||
raise ValueError('Unsupported route family for VRF: %s' %
|
||||
route_family)
|
||||
|
@ -508,6 +555,8 @@ class TableCoreManager(object):
|
|||
route_family = RF_L2_EVPN
|
||||
elif vpn_path.route_family == RF_VPNv4_FLOWSPEC:
|
||||
route_family = RF_IPv4_FLOWSPEC
|
||||
elif vpn_path.route_family == RF_VPNv6_FLOWSPEC:
|
||||
route_family = RF_IPv6_FLOWSPEC
|
||||
else:
|
||||
raise ValueError('Unsupported route family for VRF: %s' %
|
||||
vpn_path.route_family)
|
||||
|
@ -650,7 +699,10 @@ class TableCoreManager(object):
|
|||
If `is_withdraw` is True, remove a BGP route from the VRF table.
|
||||
"""
|
||||
from ryu.services.protocols.bgp.core import BgpCoreError
|
||||
from ryu.services.protocols.bgp.api.prefix import FLOWSPEC_FAMILY_VPNV4
|
||||
from ryu.services.protocols.bgp.api.prefix import (
|
||||
FLOWSPEC_FAMILY_VPNV4,
|
||||
FLOWSPEC_FAMILY_VPNV6,
|
||||
)
|
||||
|
||||
if flowspec_family == FLOWSPEC_FAMILY_VPNV4:
|
||||
vrf_table = self._tables.get((route_dist, VRF_RF_IPV4_FLOWSPEC))
|
||||
|
@ -659,6 +711,13 @@ class TableCoreManager(object):
|
|||
communities = create_v4flowspec_actions(actions)
|
||||
except ValueError as e:
|
||||
raise BgpCoreError(desc=str(e))
|
||||
elif flowspec_family == FLOWSPEC_FAMILY_VPNV6:
|
||||
vrf_table = self._tables.get((route_dist, VRF_RF_IPV6_FLOWSPEC))
|
||||
prefix = FlowSpecIPv6NLRI.from_user(**rules)
|
||||
try:
|
||||
communities = create_v6flowspec_actions(actions)
|
||||
except ValueError as e:
|
||||
raise BgpCoreError(desc=str(e))
|
||||
else:
|
||||
raise BgpCoreError(
|
||||
desc='Unsupported flowspec_family %s' % flowspec_family)
|
||||
|
@ -732,7 +791,10 @@ class TableCoreManager(object):
|
|||
"""
|
||||
|
||||
from ryu.services.protocols.bgp.core import BgpCoreError
|
||||
from ryu.services.protocols.bgp.api.prefix import FLOWSPEC_FAMILY_IPV4
|
||||
from ryu.services.protocols.bgp.api.prefix import (
|
||||
FLOWSPEC_FAMILY_IPV4,
|
||||
FLOWSPEC_FAMILY_IPV6,
|
||||
)
|
||||
|
||||
src_ver_num = 1
|
||||
peer = None
|
||||
|
@ -754,6 +816,19 @@ class TableCoreManager(object):
|
|||
except ValueError as e:
|
||||
raise BgpCoreError(desc=str(e))
|
||||
|
||||
if communities:
|
||||
pathattrs[BGP_ATTR_TYPE_EXTENDED_COMMUNITIES] = (
|
||||
BGPPathAttributeExtendedCommunities(
|
||||
communities=communities))
|
||||
elif flowspec_family == FLOWSPEC_FAMILY_IPV6:
|
||||
_nlri = FlowSpecIPv6NLRI.from_user(**rules)
|
||||
p = IPv6FlowSpecPath
|
||||
|
||||
try:
|
||||
communities = create_v6flowspec_actions(actions)
|
||||
except ValueError as e:
|
||||
raise BgpCoreError(desc=str(e))
|
||||
|
||||
if communities:
|
||||
pathattrs[BGP_ATTR_TYPE_EXTENDED_COMMUNITIES] = (
|
||||
BGPPathAttributeExtendedCommunities(
|
||||
|
|
|
@ -97,11 +97,15 @@ class FlexinetOutgoingRoute(object):
|
|||
from ryu.services.protocols.bgp.info_base.vrf4 import Vrf4Path
|
||||
from ryu.services.protocols.bgp.info_base.vrf6 import Vrf6Path
|
||||
from ryu.services.protocols.bgp.info_base.vrfevpn import VrfEvpnPath
|
||||
from ryu.services.protocols.bgp.info_base.vrf4fs import Vrf4FlowSpecPath
|
||||
from ryu.services.protocols.bgp.info_base.vrf4fs import (
|
||||
Vrf4FlowSpecPath)
|
||||
from ryu.services.protocols.bgp.info_base.vrf6fs import (
|
||||
Vrf6FlowSpecPath)
|
||||
assert path.route_family in (Vrf4Path.ROUTE_FAMILY,
|
||||
Vrf6Path.ROUTE_FAMILY,
|
||||
VrfEvpnPath.ROUTE_FAMILY,
|
||||
Vrf4FlowSpecPath.ROUTE_FAMILY)
|
||||
Vrf4FlowSpecPath.ROUTE_FAMILY,
|
||||
Vrf6FlowSpecPath.ROUTE_FAMILY)
|
||||
|
||||
self.sink = None
|
||||
self._path = path
|
||||
|
|
|
@ -47,7 +47,9 @@ CAP_MBGP_VPNV4 = 'cap_mbgp_vpnv4'
|
|||
CAP_MBGP_VPNV6 = 'cap_mbgp_vpnv6'
|
||||
CAP_MBGP_EVPN = 'cap_mbgp_evpn'
|
||||
CAP_MBGP_IPV4FS = 'cap_mbgp_ipv4fs'
|
||||
CAP_MBGP_IPV6FS = 'cap_mbgp_ipv6fs'
|
||||
CAP_MBGP_VPNV4FS = 'cap_mbgp_vpnv4fs'
|
||||
CAP_MBGP_VPNV6FS = 'cap_mbgp_vpnv6fs'
|
||||
CAP_RTC = 'cap_rtc'
|
||||
RTC_AS = 'rtc_as'
|
||||
HOLD_TIME = 'hold_time'
|
||||
|
@ -659,6 +661,15 @@ def validate_cap_mbgp_ipv4fs(cmv4fs):
|
|||
return cmv4fs
|
||||
|
||||
|
||||
@validate(name=CAP_MBGP_IPV6FS)
|
||||
def validate_cap_mbgp_ipv6fs(cmv6fs):
|
||||
if not isinstance(cmv6fs, bool):
|
||||
raise ConfigTypeError(desc='Invalid MP-BGP '
|
||||
'IPv6 Flow Specification capability '
|
||||
'settings: %s. Boolean value expected' % cmv6fs)
|
||||
return cmv6fs
|
||||
|
||||
|
||||
@validate(name=CAP_MBGP_VPNV4FS)
|
||||
def validate_cap_mbgp_vpnv4fs(cmv4fs):
|
||||
if not isinstance(cmv4fs, bool):
|
||||
|
@ -668,6 +679,15 @@ def validate_cap_mbgp_vpnv4fs(cmv4fs):
|
|||
return cmv4fs
|
||||
|
||||
|
||||
@validate(name=CAP_MBGP_VPNV6FS)
|
||||
def validate_cap_mbgp_vpnv66fs(cmv6fs):
|
||||
if not isinstance(cmv6fs, bool):
|
||||
raise ConfigTypeError(desc='Invalid MP-BGP '
|
||||
'VPNv6 Flow Specification capability '
|
||||
'settings: %s. Boolean value expected' % cmv6fs)
|
||||
return cmv6fs
|
||||
|
||||
|
||||
@validate(name=CAP_RTC)
|
||||
def validate_cap_rtc(cap_rtc):
|
||||
if not isinstance(cap_rtc, bool):
|
||||
|
|
|
@ -28,7 +28,9 @@ from ryu.lib.packet.bgp import RF_IPv4_VPN
|
|||
from ryu.lib.packet.bgp import RF_IPv6_VPN
|
||||
from ryu.lib.packet.bgp import RF_L2_EVPN
|
||||
from ryu.lib.packet.bgp import RF_IPv4_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_IPv6_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_VPNv4_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_VPNv6_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_RTC_UC
|
||||
from ryu.lib.packet.bgp import BGPOptParamCapabilityFourOctetAsNumber
|
||||
from ryu.lib.packet.bgp import BGPOptParamCapabilityEnhancedRouteRefresh
|
||||
|
@ -51,7 +53,9 @@ from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_VPNV4
|
|||
from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_VPNV6
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_EVPN
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_IPV4FS
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_IPV6FS
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_VPNV4FS
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_MBGP_VPNV6FS
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_REFRESH
|
||||
from ryu.services.protocols.bgp.rtconf.base import CAP_RTC
|
||||
from ryu.services.protocols.bgp.rtconf.base import compute_optional_conf
|
||||
|
@ -110,7 +114,9 @@ DEFAULT_CAP_MBGP_VPNV4 = False
|
|||
DEFAULT_CAP_MBGP_VPNV6 = False
|
||||
DEFAULT_CAP_MBGP_EVPN = False
|
||||
DEFAULT_CAP_MBGP_IPV4FS = False
|
||||
DEFAULT_CAP_MBGP_IPV6FS = False
|
||||
DEFAULT_CAP_MBGP_VPNV4FS = False
|
||||
DEFAULT_CAP_MBGP_VPNV6FS = False
|
||||
DEFAULT_HOLD_TIME = 40
|
||||
DEFAULT_ENABLED = True
|
||||
DEFAULT_CAP_RTC = False
|
||||
|
@ -325,6 +331,7 @@ class NeighborConf(ConfWithId, ConfWithStats):
|
|||
CAP_MBGP_VPNV4, CAP_MBGP_VPNV6,
|
||||
CAP_RTC, CAP_MBGP_EVPN,
|
||||
CAP_MBGP_IPV4FS, CAP_MBGP_VPNV4FS,
|
||||
CAP_MBGP_IPV6FS, CAP_MBGP_VPNV6FS,
|
||||
RTC_AS, HOLD_TIME,
|
||||
ENABLED, MULTI_EXIT_DISC, MAX_PREFIXES,
|
||||
ADVERTISE_PEER_AS, SITE_OF_ORIGINS,
|
||||
|
@ -359,8 +366,12 @@ class NeighborConf(ConfWithId, ConfWithStats):
|
|||
CAP_MBGP_VPNV6, DEFAULT_CAP_MBGP_VPNV6, **kwargs)
|
||||
self._settings[CAP_MBGP_IPV4FS] = compute_optional_conf(
|
||||
CAP_MBGP_IPV4FS, DEFAULT_CAP_MBGP_IPV4FS, **kwargs)
|
||||
self._settings[CAP_MBGP_IPV6FS] = compute_optional_conf(
|
||||
CAP_MBGP_IPV6FS, DEFAULT_CAP_MBGP_IPV6FS, **kwargs)
|
||||
self._settings[CAP_MBGP_VPNV4FS] = compute_optional_conf(
|
||||
CAP_MBGP_VPNV4FS, DEFAULT_CAP_MBGP_VPNV4FS, **kwargs)
|
||||
self._settings[CAP_MBGP_VPNV6FS] = compute_optional_conf(
|
||||
CAP_MBGP_VPNV6FS, DEFAULT_CAP_MBGP_VPNV6FS, **kwargs)
|
||||
self._settings[HOLD_TIME] = compute_optional_conf(
|
||||
HOLD_TIME, DEFAULT_HOLD_TIME, **kwargs)
|
||||
self._settings[ENABLED] = compute_optional_conf(
|
||||
|
@ -534,10 +545,18 @@ class NeighborConf(ConfWithId, ConfWithStats):
|
|||
def cap_mbgp_ipv4fs(self):
|
||||
return self._settings[CAP_MBGP_IPV4FS]
|
||||
|
||||
@property
|
||||
def cap_mbgp_ipv6fs(self):
|
||||
return self._settings[CAP_MBGP_IPV6FS]
|
||||
|
||||
@property
|
||||
def cap_mbgp_vpnv4fs(self):
|
||||
return self._settings[CAP_MBGP_VPNV4FS]
|
||||
|
||||
@property
|
||||
def cap_mbgp_vpnv6fs(self):
|
||||
return self._settings[CAP_MBGP_VPNV6FS]
|
||||
|
||||
@property
|
||||
def cap_rtc(self):
|
||||
return self._settings[CAP_RTC]
|
||||
|
@ -667,11 +686,21 @@ class NeighborConf(ConfWithId, ConfWithStats):
|
|||
BGPOptParamCapabilityMultiprotocol(
|
||||
RF_IPv4_FLOWSPEC.afi, RF_IPv4_FLOWSPEC.safi))
|
||||
|
||||
if self.cap_mbgp_ipv6fs:
|
||||
mbgp_caps.append(
|
||||
BGPOptParamCapabilityMultiprotocol(
|
||||
RF_IPv6_FLOWSPEC.afi, RF_IPv6_FLOWSPEC.safi))
|
||||
|
||||
if self.cap_mbgp_vpnv4fs:
|
||||
mbgp_caps.append(
|
||||
BGPOptParamCapabilityMultiprotocol(
|
||||
RF_VPNv4_FLOWSPEC.afi, RF_VPNv4_FLOWSPEC.safi))
|
||||
|
||||
if self.cap_mbgp_vpnv6fs:
|
||||
mbgp_caps.append(
|
||||
BGPOptParamCapabilityMultiprotocol(
|
||||
RF_VPNv6_FLOWSPEC.afi, RF_VPNv6_FLOWSPEC.safi))
|
||||
|
||||
if mbgp_caps:
|
||||
capabilities[BGP_CAP_MULTIPROTOCOL] = mbgp_caps
|
||||
|
||||
|
|
|
@ -24,6 +24,7 @@ from ryu.lib.packet.bgp import RF_IPv4_UC
|
|||
from ryu.lib.packet.bgp import RF_IPv6_UC
|
||||
from ryu.lib.packet.bgp import RF_L2_EVPN
|
||||
from ryu.lib.packet.bgp import RF_IPv4_FLOWSPEC
|
||||
from ryu.lib.packet.bgp import RF_IPv6_FLOWSPEC
|
||||
|
||||
from ryu.services.protocols.bgp.utils import validation
|
||||
from ryu.services.protocols.bgp.base import get_validator
|
||||
|
@ -61,11 +62,13 @@ VRF_RF_IPV4 = 'ipv4'
|
|||
VRF_RF_IPV6 = 'ipv6'
|
||||
VRF_RF_L2_EVPN = 'evpn'
|
||||
VRF_RF_IPV4_FLOWSPEC = 'ipv4fs'
|
||||
VRF_RF_IPV6_FLOWSPEC = 'ipv6fs'
|
||||
SUPPORTED_VRF_RF = (
|
||||
VRF_RF_IPV4,
|
||||
VRF_RF_IPV6,
|
||||
VRF_RF_L2_EVPN,
|
||||
VRF_RF_IPV4_FLOWSPEC,
|
||||
VRF_RF_IPV6_FLOWSPEC,
|
||||
)
|
||||
|
||||
|
||||
|
@ -235,6 +238,8 @@ class VrfConf(ConfWithId, ConfWithStats):
|
|||
return RF_L2_EVPN
|
||||
elif vrf_rf == VRF_RF_IPV4_FLOWSPEC:
|
||||
return RF_IPv4_FLOWSPEC
|
||||
elif vrf_rf == VRF_RF_IPV6_FLOWSPEC:
|
||||
return RF_IPv6_FLOWSPEC
|
||||
else:
|
||||
raise ValueError('Unsupported VRF route family given %s' % vrf_rf)
|
||||
|
||||
|
@ -248,6 +253,8 @@ class VrfConf(ConfWithId, ConfWithStats):
|
|||
return VRF_RF_L2_EVPN
|
||||
elif route_family == RF_IPv4_FLOWSPEC:
|
||||
return VRF_RF_IPV4_FLOWSPEC
|
||||
elif route_family == RF_IPv6_FLOWSPEC:
|
||||
return VRF_RF_IPV6_FLOWSPEC
|
||||
else:
|
||||
raise ValueError('No supported mapping for route family '
|
||||
'to vrf_route_family exists for %s' %
|
||||
|
|
|
@ -29,7 +29,9 @@ from ryu.lib.packet.bgp import (
|
|||
RF_IPv6_VPN,
|
||||
RF_L2_EVPN,
|
||||
RF_IPv4_FLOWSPEC,
|
||||
RF_IPv6_FLOWSPEC,
|
||||
RF_VPNv4_FLOWSPEC,
|
||||
RF_VPNv6_FLOWSPEC,
|
||||
RF_RTC_UC,
|
||||
RouteTargetMembershipNLRI,
|
||||
BGP_ATTR_TYPE_MULTI_EXIT_DISC,
|
||||
|
@ -55,7 +57,9 @@ from ryu.services.protocols.bgp.info_base.vpnv4 import Vpnv4Path
|
|||
from ryu.services.protocols.bgp.info_base.vpnv6 import Vpnv6Path
|
||||
from ryu.services.protocols.bgp.info_base.evpn import EvpnPath
|
||||
from ryu.services.protocols.bgp.info_base.ipv4fs import IPv4FlowSpecPath
|
||||
from ryu.services.protocols.bgp.info_base.ipv6fs import IPv6FlowSpecPath
|
||||
from ryu.services.protocols.bgp.info_base.vpnv4fs import VPNv4FlowSpecPath
|
||||
from ryu.services.protocols.bgp.info_base.vpnv6fs import VPNv6FlowSpecPath
|
||||
|
||||
|
||||
LOG = logging.getLogger('utils.bgp')
|
||||
|
@ -67,7 +71,9 @@ _ROUTE_FAMILY_TO_PATH_MAP = {RF_IPv4_UC: Ipv4Path,
|
|||
RF_IPv6_VPN: Vpnv6Path,
|
||||
RF_L2_EVPN: EvpnPath,
|
||||
RF_IPv4_FLOWSPEC: IPv4FlowSpecPath,
|
||||
RF_IPv6_FLOWSPEC: IPv6FlowSpecPath,
|
||||
RF_VPNv4_FLOWSPEC: VPNv4FlowSpecPath,
|
||||
RF_VPNv6_FLOWSPEC: VPNv6FlowSpecPath,
|
||||
RF_RTC_UC: RtcPath}
|
||||
|
||||
|
||||
|
@ -215,6 +221,35 @@ def create_v4flowspec_actions(actions=None):
|
|||
FLOWSPEC_ACTION_TRAFFIC_MARKING: BGPFlowSpecTrafficMarkingCommunity,
|
||||
}
|
||||
|
||||
return _create_actions(actions, action_types)
|
||||
|
||||
|
||||
def create_v6flowspec_actions(actions=None):
|
||||
"""
|
||||
Create list of traffic filtering actions
|
||||
for Ipv6 Flow Specification and VPNv6 Flow Specification.
|
||||
|
||||
"FLOWSPEC_ACTION_REDIRECT_IPV6" is not implemented yet.
|
||||
"""
|
||||
from ryu.services.protocols.bgp.api.prefix import (
|
||||
FLOWSPEC_ACTION_TRAFFIC_RATE,
|
||||
FLOWSPEC_ACTION_TRAFFIC_ACTION,
|
||||
FLOWSPEC_ACTION_REDIRECT,
|
||||
FLOWSPEC_ACTION_TRAFFIC_MARKING,
|
||||
)
|
||||
|
||||
# Supported action type for IPv6 and VPNv6.
|
||||
action_types = {
|
||||
FLOWSPEC_ACTION_TRAFFIC_RATE: BGPFlowSpecTrafficRateCommunity,
|
||||
FLOWSPEC_ACTION_TRAFFIC_ACTION: BGPFlowSpecTrafficActionCommunity,
|
||||
FLOWSPEC_ACTION_REDIRECT: BGPFlowSpecRedirectCommunity,
|
||||
FLOWSPEC_ACTION_TRAFFIC_MARKING: BGPFlowSpecTrafficMarkingCommunity,
|
||||
}
|
||||
|
||||
return _create_actions(actions, action_types)
|
||||
|
||||
|
||||
def _create_actions(actions, action_types):
|
||||
communities = []
|
||||
|
||||
if actions is None:
|
||||
|
|
Loading…
Reference in New Issue