rules = []
for r in self.rules:
rules.append(r.encode())
- self._test.vapi.gbp_contract_add_del(
+ r = self._test.vapi.gbp_contract_add_del(
1,
self.sclass,
self.dclass,
self.acl_index,
rules,
self.allowed_ethertypes)
+ self.stats_index = r.stats_index
self._test.registry.register(self, self._test.logger)
def remove_vpp_config(self):
return True
return False
+ def get_drop_stats(self):
+ c = self._test.statistics.get_counter("/net/gbp/contract/drop")
+ return c[0][self.stats_index]
+
+ def get_permit_stats(self):
+ c = self._test.statistics.get_counter("/net/gbp/contract/permit")
+ return c[0][self.stats_index]
+
class VppGbpVxlanTunnel(VppInterface):
"""
class TestGBP(VppTestCase):
""" GBP Test Case """
+ @property
+ def config_flags(self):
+ return VppEnum.vl_api_nat_config_flags_t
+
+ @classmethod
+ def setUpClass(cls):
+ super(TestGBP, cls).setUpClass()
+
+ @classmethod
+ def tearDownClass(cls):
+ super(TestGBP, cls).tearDownClass()
+
def setUp(self):
super(TestGBP, self).setUp()
self.router_mac.packed)
# The BVIs are NAT inside interfaces
+ flags = self.config_flags.NAT_IS_INSIDE
self.vapi.nat44_interface_add_del_feature(epg.bvi.sw_if_index,
- is_inside=1,
- is_add=1)
+ flags=flags)
self.vapi.nat66_add_del_interface(epg.bvi.sw_if_index,
- is_inside=1,
- is_add=1)
+ flags=flags)
if_ip4 = VppIpInterfaceAddress(self, epg.bvi, epg.bvi_ip4, 32)
if_ip6 = VppIpInterfaceAddress(self, epg.bvi, epg.bvi_ip6, 128)
recirc.epg.rd.t6).add_vpp_config()
self.vapi.nat44_interface_add_del_feature(
- recirc.recirc.sw_if_index,
- is_inside=0,
- is_add=1)
+ recirc.recirc.sw_if_index)
self.vapi.nat66_add_del_interface(
- recirc.recirc.sw_if_index,
- is_inside=0,
- is_add=1)
+ recirc.recirc.sw_if_index)
recirc.add_vpp_config()
for (ip, fip) in zip(ep.ips, ep.fips):
# Add static mappings for each EP from the 10/8 to 11/8 network
if ip.af == AF_INET:
+ flags = self.config_flags.NAT_IS_ADDR_ONLY
self.vapi.nat44_add_del_static_mapping(ip.bytes,
fip.bytes,
vrf_id=0,
- addr_only=1)
+ flags=flags)
else:
self.vapi.nat66_add_del_static_mapping(ip.bytes,
fip.bytes,
pkt_inter_epg_221_to_220 * 65,
eps[0].itf)
+ ds = c2.get_drop_stats()
+ self.assertEqual(ds['packets'], 0)
+ ps = c2.get_permit_stats()
+ self.assertEqual(ps['packets'], 65)
+
#
# the contract does not allow non-IP
#
#
for ep in eps:
# del static mappings for each EP from the 10/8 to 11/8 network
+ flags = self.config_flags.NAT_IS_ADDR_ONLY
self.vapi.nat44_add_del_static_mapping(ep.ip4.bytes,
ep.fip4.bytes,
vrf_id=0,
- addr_only=1,
- is_add=0)
+ is_add=0,
+ flags=flags)
self.vapi.nat66_add_del_static_mapping(ep.ip6.bytes,
ep.fip6.bytes,
vrf_id=0,
for epg in epgs:
# IP config on the BVI interfaces
if epg != epgs[0] and epg != epgs[3]:
+ flags = self.config_flags.NAT_IS_INSIDE
self.vapi.nat44_interface_add_del_feature(epg.bvi.sw_if_index,
- is_inside=1,
+ flags=flags,
is_add=0)
self.vapi.nat66_add_del_interface(epg.bvi.sw_if_index,
- is_inside=1,
+ flags=flags,
is_add=0)
for recirc in recircs:
self.vapi.nat44_interface_add_del_feature(
recirc.recirc.sw_if_index,
- is_inside=0,
is_add=0)
self.vapi.nat66_add_del_interface(
recirc.recirc.sw_if_index,
- is_inside=0,
is_add=0)
def wait_for_ep_timeout(self, sw_if_index=None, ip=None, mac=None,
def test_gbp_learn_l2(self):
""" GBP L2 Endpoint Learning """
+ self.vapi.cli("clear errors")
+
ep_flags = VppEnum.vl_api_gbp_endpoint_flags_t
learnt = [{'mac': '00:00:11:11:11:01',
'ip': '10.0.0.1',
self.send_and_assert_no_replies(self.pg2, p)
+ self.logger.info(self.vapi.cli("sh error"))
+ # self.assert_packet_counter_equal(
+ # '/err/gbp-policy-port/drop-no-contract', 1)
+
#
# we should not have learnt a new tunnel endpoint, since
# the EPG was not learnt.
self.pg2.remote_hosts[0].ip4,
99))
- # epg is not learnt, because the EPG is unknwon
+ # epg is not learnt, because the EPG is unknown
self.assertEqual(len(self.vapi.gbp_endpoint_dump()), 1)
#
vx_tun_l2_1.sw_if_index,
ip=l['ip']))
+ # self.assert_packet_counter_equal(
+ # '/err/gbp-policy-port/allow-intra-sclass', 2)
+
self.logger.info(self.vapi.cli("show gbp endpoint"))
self.logger.info(self.vapi.cli("show gbp vxlan"))
self.logger.info(self.vapi.cli("show ip mfib"))
vx_tun_l2_1.sw_if_index,
mac=l['mac']))
+ #
+ # repeat in the other EPG
+ # there's no contract between 220 and 330, but the sclass is set to 1
+ # so the packet is cleared for delivery
+ #
+ for l in learnt:
+ # a packet with an sclass from a known EPG
+ p = (Ether(src=self.pg2.remote_mac,
+ dst=self.pg2.local_mac) /
+ IP(src=self.pg2.remote_hosts[1].ip4,
+ dst=self.pg2.local_ip4) /
+ UDP(sport=1234, dport=48879) /
+ VXLAN(vni=99, gpid=1, flags=0x88) /
+ Ether(src=l['mac'], dst=ep.mac) /
+ IP(src=l['ip'], dst=ep.ip4.address) /
+ UDP(sport=1234, dport=1234) /
+ Raw('\xa5' * 100))
+
+ rx = self.send_and_expect(self.pg2, p*65, self.pg0)
+
+ self.assertTrue(find_gbp_endpoint(self,
+ vx_tun_l2_1.sw_if_index,
+ mac=l['mac']))
+
#
# static EP cannot reach the learnt EPs since there is no contract
# only test 1 EP as the others could timeout
for l in learnt:
self.wait_for_ep_timeout(vx_tun_l2_1.sw_if_index,
mac=l['mac'])
-
self.pg2.unconfig_ip4()
self.pg3.unconfig_ip4()
self.pg4.unconfig_ip4()
self.logger.info(self.vapi.cli("sh int"))
self.logger.info(self.vapi.cli("sh gbp vxlan"))
+ def test_gbp_bd_flags(self):
+ """ GBP BD FLAGS """
+
+ #
+ # IP tables
+ #
+ gt4 = VppIpTable(self, 1)
+ gt4.add_vpp_config()
+ gt6 = VppIpTable(self, 1, is_ip6=True)
+ gt6.add_vpp_config()
+
+ rd1 = VppGbpRouteDomain(self, 1, gt4, gt6)
+ rd1.add_vpp_config()
+
+ #
+ # Pg3 hosts the IP4 UU-flood VXLAN tunnel
+ # Pg4 hosts the IP6 UU-flood VXLAN tunnel
+ #
+ self.pg3.config_ip4()
+ self.pg3.resolve_arp()
+ self.pg4.config_ip4()
+ self.pg4.resolve_arp()
+
+ #
+ # Add a mcast destination VXLAN-GBP tunnel for B&M traffic
+ #
+ tun_bm = VppVxlanGbpTunnel(self, self.pg4.local_ip4,
+ "239.1.1.1", 88,
+ mcast_itf=self.pg4)
+ tun_bm.add_vpp_config()
+
+ #
+ # a GBP bridge domain with a BVI and a UU-flood interface
+ #
+ bd1 = VppBridgeDomain(self, 1)
+ bd1.add_vpp_config()
+
+ gbd1 = VppGbpBridgeDomain(self, bd1, self.loop0, self.pg3, tun_bm,
+ uu_drop=True, bm_drop=True)
+ gbd1.add_vpp_config()
+
+ self.logger.info(self.vapi.cli("sh bridge 1 detail"))
+ self.logger.info(self.vapi.cli("sh gbp bridge"))
+
+ # ... and has a /32 applied
+ ip_addr = VppIpInterfaceAddress(self, gbd1.bvi, "10.0.0.128", 32)
+ ip_addr.add_vpp_config()
+
+ #
+ # The Endpoint-group
+ #
+ epg_220 = VppGbpEndpointGroup(self, 220, 112, rd1, gbd1,
+ None, self.loop0,
+ "10.0.0.128",
+ "2001:10::128",
+ VppGbpEndpointRetention(2))
+ epg_220.add_vpp_config()
+
+ ep = VppGbpEndpoint(self, self.pg0,
+ epg_220, None,
+ "10.0.0.127", "11.0.0.127",
+ "2001:10::1", "3001::1")
+ ep.add_vpp_config()
+ #
+ # send UU/BM packet from the local EP with UU drop and BM drop enabled
+ # in bd
+ #
+ self.logger.info(self.vapi.cli("sh bridge 1 detail"))
+ self.logger.info(self.vapi.cli("sh gbp bridge"))
+ p_uu = (Ether(src=ep.mac, dst="00:11:11:11:11:11") /
+ IP(dst="10.0.0.133", src=ep.ip4.address) /
+ UDP(sport=1234, dport=1234) /
+ Raw('\xa5' * 100))
+ self.send_and_assert_no_replies(ep.itf, [p_uu])
+
+ p_bm = (Ether(src=ep.mac, dst="ff:ff:ff:ff:ff:ff") /
+ IP(dst="10.0.0.133", src=ep.ip4.address) /
+ UDP(sport=1234, dport=1234) /
+ Raw('\xa5' * 100))
+ self.send_and_assert_no_replies(ep.itf, [p_bm])
+
+ self.pg3.unconfig_ip4()
+ self.pg4.unconfig_ip4()
+
+ self.logger.info(self.vapi.cli("sh int"))
+
def test_gbp_learn_vlan_l2(self):
""" GBP L2 Endpoint w/ VLANs"""
self.assertEqual(inner[IP].src, "10.220.0.1")
self.assertEqual(inner[IP].dst, "10.222.0.1")
+ #
+ # ping from host in remote to local external subnets
+ # there's no contract for this, but sclass is 1.
+ #
+ p = (Ether(src=self.pg7.remote_mac, dst=self.pg7.local_mac) /
+ IP(src=self.pg7.remote_ip4, dst=self.pg7.local_ip4) /
+ UDP(sport=1234, dport=48879) /
+ VXLAN(vni=445, gpid=1, flags=0x88) /
+ Ether(src=self.pg0.remote_mac, dst=str(self.router_mac)) /
+ IP(src="10.222.0.1", dst="10.220.0.1") /
+ UDP(sport=1234, dport=1234) /
+ Raw('\xa5' * 100))
+
+ rxs = self.send_and_expect(self.pg7, p * 3, self.pg0)
+ self.assertFalse(find_gbp_endpoint(self, ip="10.222.0.1"))
+
#
# ping from host in remote to local external subnets
# there's no contract for this, but the A bit is set.