blob: 129f220c3145526d2d4f586853abd013c95d762c [file] [log] [blame]
Klement Sekera31da2e32018-06-24 22:49:55 +02001import unittest
Klement Sekera611864f2018-09-26 11:19:00 +02002import socket
Neale Ranns80f6fd52019-04-16 02:41:34 +00003import struct
Klement Sekera31da2e32018-06-24 22:49:55 +02004
Neale Ranns53f526b2019-02-25 14:32:02 +00005from scapy.layers.inet import IP, ICMP, TCP, UDP
Damjan Mariona829b132019-04-24 23:39:16 +02006from scapy.layers.ipsec import SecurityAssociation, ESP
snaramre5d4b8912019-12-13 23:39:35 +00007from scapy.layers.l2 import Ether
Paul Vinciguerra582eac52020-04-03 12:18:40 -04008from scapy.packet import raw, Raw
Neale Ranns02950402019-12-20 00:54:57 +00009from scapy.layers.inet6 import IPv6, ICMPv6EchoRequest, IPv6ExtHdrHopByHop, \
10 IPv6ExtHdrFragment, IPv6ExtHdrDestOpt
11
Klement Sekera31da2e32018-06-24 22:49:55 +020012
13from framework import VppTestCase, VppTestRunner
Neale Ranns14046982019-07-29 14:49:52 +000014from util import ppp, reassemble4, fragment_rfc791, fragment_rfc8200
Neale Ranns17dcec02019-01-09 21:22:20 -080015from vpp_papi import VppEnum
Klement Sekera31da2e32018-06-24 22:49:55 +020016
17
Paul Vinciguerrae061dad2020-12-04 14:57:51 -050018class IPsecIPv4Params:
Neale Ranns17dcec02019-01-09 21:22:20 -080019
Klement Sekera611864f2018-09-26 11:19:00 +020020 addr_type = socket.AF_INET
21 addr_any = "0.0.0.0"
22 addr_bcast = "255.255.255.255"
23 addr_len = 32
24 is_ipv6 = 0
Klement Sekera611864f2018-09-26 11:19:00 +020025
Neale Ranns17dcec02019-01-09 21:22:20 -080026 def __init__(self):
27 self.remote_tun_if_host = '1.1.1.1'
Neale Ranns987aea82019-03-27 13:40:35 +000028 self.remote_tun_if_host6 = '1111::1'
Klement Sekera611864f2018-09-26 11:19:00 +020029
Neale Ranns28287212019-12-16 00:53:11 +000030 self.scapy_tun_sa_id = 100
Neale Ranns17dcec02019-01-09 21:22:20 -080031 self.scapy_tun_spi = 1001
Neale Ranns28287212019-12-16 00:53:11 +000032 self.vpp_tun_sa_id = 200
Neale Ranns17dcec02019-01-09 21:22:20 -080033 self.vpp_tun_spi = 1000
Klement Sekera611864f2018-09-26 11:19:00 +020034
Neale Ranns28287212019-12-16 00:53:11 +000035 self.scapy_tra_sa_id = 300
Neale Ranns17dcec02019-01-09 21:22:20 -080036 self.scapy_tra_spi = 2001
Neale Ranns28287212019-12-16 00:53:11 +000037 self.vpp_tra_sa_id = 400
Neale Ranns17dcec02019-01-09 21:22:20 -080038 self.vpp_tra_spi = 2000
Klement Sekera611864f2018-09-26 11:19:00 +020039
Neale Ranns17dcec02019-01-09 21:22:20 -080040 self.auth_algo_vpp_id = (VppEnum.vl_api_ipsec_integ_alg_t.
41 IPSEC_API_INTEG_ALG_SHA1_96)
42 self.auth_algo = 'HMAC-SHA1-96' # scapy name
Ole Troan64e978b2019-10-17 21:40:36 +020043 self.auth_key = b'C91KUR9GYMm5GfkEvNjX'
Neale Ranns17dcec02019-01-09 21:22:20 -080044
45 self.crypt_algo_vpp_id = (VppEnum.vl_api_ipsec_crypto_alg_t.
46 IPSEC_API_CRYPTO_ALG_AES_CBC_128)
47 self.crypt_algo = 'AES-CBC' # scapy name
Ole Troan64e978b2019-10-17 21:40:36 +020048 self.crypt_key = b'JPjyOWBeVEQiMe7h'
Neale Ranns80f6fd52019-04-16 02:41:34 +000049 self.salt = 0
Neale Ranns53f526b2019-02-25 14:32:02 +000050 self.flags = 0
51 self.nat_header = None
Neale Ranns041add72020-01-02 04:06:10 +000052 self.tun_flags = (VppEnum.vl_api_tunnel_encap_decap_flags_t.
53 TUNNEL_API_ENCAP_DECAP_FLAG_NONE)
54 self.dscp = 0
Klement Sekera611864f2018-09-26 11:19:00 +020055
56
Paul Vinciguerrae061dad2020-12-04 14:57:51 -050057class IPsecIPv6Params:
Neale Ranns17dcec02019-01-09 21:22:20 -080058
Klement Sekera611864f2018-09-26 11:19:00 +020059 addr_type = socket.AF_INET6
60 addr_any = "0::0"
61 addr_bcast = "ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff"
62 addr_len = 128
63 is_ipv6 = 1
Klement Sekera611864f2018-09-26 11:19:00 +020064
Neale Ranns17dcec02019-01-09 21:22:20 -080065 def __init__(self):
66 self.remote_tun_if_host = '1111:1111:1111:1111:1111:1111:1111:1111'
Neale Ranns987aea82019-03-27 13:40:35 +000067 self.remote_tun_if_host4 = '1.1.1.1'
Klement Sekera611864f2018-09-26 11:19:00 +020068
Neale Ranns28287212019-12-16 00:53:11 +000069 self.scapy_tun_sa_id = 500
Neale Ranns17dcec02019-01-09 21:22:20 -080070 self.scapy_tun_spi = 3001
Neale Ranns28287212019-12-16 00:53:11 +000071 self.vpp_tun_sa_id = 600
Neale Ranns17dcec02019-01-09 21:22:20 -080072 self.vpp_tun_spi = 3000
Klement Sekera611864f2018-09-26 11:19:00 +020073
Neale Ranns28287212019-12-16 00:53:11 +000074 self.scapy_tra_sa_id = 700
Neale Ranns17dcec02019-01-09 21:22:20 -080075 self.scapy_tra_spi = 4001
Neale Ranns28287212019-12-16 00:53:11 +000076 self.vpp_tra_sa_id = 800
Neale Ranns17dcec02019-01-09 21:22:20 -080077 self.vpp_tra_spi = 4000
Klement Sekera611864f2018-09-26 11:19:00 +020078
Neale Ranns17dcec02019-01-09 21:22:20 -080079 self.auth_algo_vpp_id = (VppEnum.vl_api_ipsec_integ_alg_t.
Neale Ranns1091c4a2019-04-08 14:48:23 +000080 IPSEC_API_INTEG_ALG_SHA1_96)
81 self.auth_algo = 'HMAC-SHA1-96' # scapy name
Ole Troan64e978b2019-10-17 21:40:36 +020082 self.auth_key = b'C91KUR9GYMm5GfkEvNjX'
Neale Ranns17dcec02019-01-09 21:22:20 -080083
84 self.crypt_algo_vpp_id = (VppEnum.vl_api_ipsec_crypto_alg_t.
Neale Ranns4f33c802019-04-10 12:39:10 +000085 IPSEC_API_CRYPTO_ALG_AES_CBC_128)
Neale Ranns17dcec02019-01-09 21:22:20 -080086 self.crypt_algo = 'AES-CBC' # scapy name
Ole Troan64e978b2019-10-17 21:40:36 +020087 self.crypt_key = b'JPjyOWBeVEQiMe7h'
Neale Ranns80f6fd52019-04-16 02:41:34 +000088 self.salt = 0
Neale Ranns53f526b2019-02-25 14:32:02 +000089 self.flags = 0
90 self.nat_header = None
Neale Ranns041add72020-01-02 04:06:10 +000091 self.tun_flags = (VppEnum.vl_api_tunnel_encap_decap_flags_t.
92 TUNNEL_API_ENCAP_DECAP_FLAG_NONE)
93 self.dscp = 0
Klement Sekera611864f2018-09-26 11:19:00 +020094
95
Neale Ranns12989b52019-09-26 16:20:19 +000096def mk_scapy_crypt_key(p):
Neale Ranns6afaae12019-07-17 15:07:14 +000097 if p.crypt_algo == "AES-GCM":
98 return p.crypt_key + struct.pack("!I", p.salt)
99 else:
100 return p.crypt_key
101
102
Neale Ranns2ac885c2019-03-20 18:24:43 +0000103def config_tun_params(p, encryption_type, tun_if):
104 ip_class_by_addr_type = {socket.AF_INET: IP, socket.AF_INET6: IPv6}
snaramre5d4b8912019-12-13 23:39:35 +0000105 esn_en = bool(p.flags & (VppEnum.vl_api_ipsec_sad_flags_t.
106 IPSEC_API_SAD_FLAG_USE_ESN))
Neale Rannsf3a66222020-01-02 05:04:00 +0000107 p.tun_dst = tun_if.remote_addr[p.addr_type]
108 p.tun_src = tun_if.local_addr[p.addr_type]
Neale Ranns12989b52019-09-26 16:20:19 +0000109 crypt_key = mk_scapy_crypt_key(p)
Neale Ranns2ac885c2019-03-20 18:24:43 +0000110 p.scapy_tun_sa = SecurityAssociation(
111 encryption_type, spi=p.vpp_tun_spi,
Neale Ranns80f6fd52019-04-16 02:41:34 +0000112 crypt_algo=p.crypt_algo,
113 crypt_key=crypt_key,
Neale Ranns2ac885c2019-03-20 18:24:43 +0000114 auth_algo=p.auth_algo, auth_key=p.auth_key,
115 tunnel_header=ip_class_by_addr_type[p.addr_type](
Neale Rannsf3a66222020-01-02 05:04:00 +0000116 src=p.tun_dst,
117 dst=p.tun_src),
Neale Ranns3833ffd2019-03-21 14:34:09 +0000118 nat_t_header=p.nat_header,
snaramre5d4b8912019-12-13 23:39:35 +0000119 esn_en=esn_en)
Neale Ranns2ac885c2019-03-20 18:24:43 +0000120 p.vpp_tun_sa = SecurityAssociation(
121 encryption_type, spi=p.scapy_tun_spi,
Neale Ranns80f6fd52019-04-16 02:41:34 +0000122 crypt_algo=p.crypt_algo,
123 crypt_key=crypt_key,
Neale Ranns2ac885c2019-03-20 18:24:43 +0000124 auth_algo=p.auth_algo, auth_key=p.auth_key,
125 tunnel_header=ip_class_by_addr_type[p.addr_type](
Neale Rannsf3a66222020-01-02 05:04:00 +0000126 dst=p.tun_dst,
127 src=p.tun_src),
Neale Ranns3833ffd2019-03-21 14:34:09 +0000128 nat_t_header=p.nat_header,
snaramre5d4b8912019-12-13 23:39:35 +0000129 esn_en=esn_en)
Neale Ranns2ac885c2019-03-20 18:24:43 +0000130
131
132def config_tra_params(p, encryption_type):
snaramre5d4b8912019-12-13 23:39:35 +0000133 esn_en = bool(p.flags & (VppEnum.vl_api_ipsec_sad_flags_t.
134 IPSEC_API_SAD_FLAG_USE_ESN))
Neale Ranns12989b52019-09-26 16:20:19 +0000135 crypt_key = mk_scapy_crypt_key(p)
Neale Ranns2ac885c2019-03-20 18:24:43 +0000136 p.scapy_tra_sa = SecurityAssociation(
137 encryption_type,
138 spi=p.vpp_tra_spi,
139 crypt_algo=p.crypt_algo,
Neale Ranns80f6fd52019-04-16 02:41:34 +0000140 crypt_key=crypt_key,
Neale Ranns2ac885c2019-03-20 18:24:43 +0000141 auth_algo=p.auth_algo,
142 auth_key=p.auth_key,
Neale Ranns3833ffd2019-03-21 14:34:09 +0000143 nat_t_header=p.nat_header,
snaramre5d4b8912019-12-13 23:39:35 +0000144 esn_en=esn_en)
Neale Ranns2ac885c2019-03-20 18:24:43 +0000145 p.vpp_tra_sa = SecurityAssociation(
146 encryption_type,
147 spi=p.scapy_tra_spi,
148 crypt_algo=p.crypt_algo,
Neale Ranns80f6fd52019-04-16 02:41:34 +0000149 crypt_key=crypt_key,
Neale Ranns2ac885c2019-03-20 18:24:43 +0000150 auth_algo=p.auth_algo,
151 auth_key=p.auth_key,
Neale Ranns3833ffd2019-03-21 14:34:09 +0000152 nat_t_header=p.nat_header,
snaramre5d4b8912019-12-13 23:39:35 +0000153 esn_en=esn_en)
Neale Ranns2ac885c2019-03-20 18:24:43 +0000154
155
Klement Sekera31da2e32018-06-24 22:49:55 +0200156class TemplateIpsec(VppTestCase):
157 """
158 TRANSPORT MODE:
159
160 ------ encrypt ---
161 |tra_if| <-------> |VPP|
162 ------ decrypt ---
163
164 TUNNEL MODE:
165
166 ------ encrypt --- plain ---
167 |tun_if| <------- |VPP| <------ |pg1|
168 ------ --- ---
169
170 ------ decrypt --- plain ---
171 |tun_if| -------> |VPP| ------> |pg1|
172 ------ --- ---
173 """
Neale Ranns4f33c802019-04-10 12:39:10 +0000174 tun_spd_id = 1
175 tra_spd_id = 2
Klement Sekera31da2e32018-06-24 22:49:55 +0200176
Neale Ranns8e4a89b2019-01-23 08:16:17 -0800177 def ipsec_select_backend(self):
Klement Sekerab4d30532018-11-08 13:00:02 +0100178 """ empty method to be overloaded when necessary """
179 pass
180
Paul Vinciguerra7f9b7f92019-03-12 19:23:27 -0700181 @classmethod
182 def setUpClass(cls):
183 super(TemplateIpsec, cls).setUpClass()
184
185 @classmethod
186 def tearDownClass(cls):
187 super(TemplateIpsec, cls).tearDownClass()
188
Neale Ranns3833ffd2019-03-21 14:34:09 +0000189 def setup_params(self):
Neale Ranns041add72020-01-02 04:06:10 +0000190 if not hasattr(self, 'ipv4_params'):
191 self.ipv4_params = IPsecIPv4Params()
192 if not hasattr(self, 'ipv6_params'):
193 self.ipv6_params = IPsecIPv6Params()
Neale Ranns8e4a89b2019-01-23 08:16:17 -0800194 self.params = {self.ipv4_params.addr_type: self.ipv4_params,
195 self.ipv6_params.addr_type: self.ipv6_params}
196
Neale Ranns4f33c802019-04-10 12:39:10 +0000197 def config_interfaces(self):
Neale Ranns8e4a89b2019-01-23 08:16:17 -0800198 self.create_pg_interfaces(range(3))
199 self.interfaces = list(self.pg_interfaces)
200 for i in self.interfaces:
Klement Sekera31da2e32018-06-24 22:49:55 +0200201 i.admin_up()
202 i.config_ip4()
203 i.resolve_arp()
Klement Sekera611864f2018-09-26 11:19:00 +0200204 i.config_ip6()
205 i.resolve_ndp()
Neale Ranns4f33c802019-04-10 12:39:10 +0000206
207 def setUp(self):
208 super(TemplateIpsec, self).setUp()
209
210 self.setup_params()
211
212 self.vpp_esp_protocol = (VppEnum.vl_api_ipsec_proto_t.
213 IPSEC_API_PROTO_ESP)
214 self.vpp_ah_protocol = (VppEnum.vl_api_ipsec_proto_t.
215 IPSEC_API_PROTO_AH)
216
217 self.config_interfaces()
Paul Vinciguerra90cf21b2019-03-13 09:23:05 -0700218
Neale Ranns8e4a89b2019-01-23 08:16:17 -0800219 self.ipsec_select_backend()
Klement Sekera31da2e32018-06-24 22:49:55 +0200220
Neale Ranns4f33c802019-04-10 12:39:10 +0000221 def unconfig_interfaces(self):
Neale Ranns8e4a89b2019-01-23 08:16:17 -0800222 for i in self.interfaces:
223 i.admin_down()
224 i.unconfig_ip4()
225 i.unconfig_ip6()
226
Neale Ranns4f33c802019-04-10 12:39:10 +0000227 def tearDown(self):
228 super(TemplateIpsec, self).tearDown()
229
230 self.unconfig_interfaces()
231
Paul Vinciguerra90cf21b2019-03-13 09:23:05 -0700232 def show_commands_at_teardown(self):
233 self.logger.info(self.vapi.cli("show hardware"))
Klement Sekera31da2e32018-06-24 22:49:55 +0200234
Neale Ranns28287212019-12-16 00:53:11 +0000235 def gen_encrypt_pkts(self, p, sa, sw_intf, src, dst, count=1,
Neale Rannsd7603d92019-03-28 08:56:10 +0000236 payload_size=54):
Klement Sekera31da2e32018-06-24 22:49:55 +0200237 return [Ether(src=sw_intf.remote_mac, dst=sw_intf.local_mac) /
Neale Rannsd7603d92019-03-28 08:56:10 +0000238 sa.encrypt(IP(src=src, dst=dst) /
Ole Troan8b76c232019-10-21 20:55:13 +0200239 ICMP() / Raw(b'X' * payload_size))
Klement Sekera31da2e32018-06-24 22:49:55 +0200240 for i in range(count)]
241
Neale Ranns28287212019-12-16 00:53:11 +0000242 def gen_encrypt_pkts6(self, p, sa, sw_intf, src, dst, count=1,
Neale Rannsd7603d92019-03-28 08:56:10 +0000243 payload_size=54):
Klement Sekera611864f2018-09-26 11:19:00 +0200244 return [Ether(src=sw_intf.remote_mac, dst=sw_intf.local_mac) /
245 sa.encrypt(IPv6(src=src, dst=dst) /
Neale Rannsd7603d92019-03-28 08:56:10 +0000246 ICMPv6EchoRequest(id=0, seq=1,
247 data='X' * payload_size))
Klement Sekera611864f2018-09-26 11:19:00 +0200248 for i in range(count)]
249
Neale Rannsd7603d92019-03-28 08:56:10 +0000250 def gen_pkts(self, sw_intf, src, dst, count=1, payload_size=54):
Klement Sekera31da2e32018-06-24 22:49:55 +0200251 return [Ether(src=sw_intf.remote_mac, dst=sw_intf.local_mac) /
Ole Troan8b76c232019-10-21 20:55:13 +0200252 IP(src=src, dst=dst) / ICMP() / Raw(b'X' * payload_size)
Klement Sekera31da2e32018-06-24 22:49:55 +0200253 for i in range(count)]
254
Neale Rannsd7603d92019-03-28 08:56:10 +0000255 def gen_pkts6(self, sw_intf, src, dst, count=1, payload_size=54):
Klement Sekera611864f2018-09-26 11:19:00 +0200256 return [Ether(src=sw_intf.remote_mac, dst=sw_intf.local_mac) /
257 IPv6(src=src, dst=dst) /
Neale Rannsd7603d92019-03-28 08:56:10 +0000258 ICMPv6EchoRequest(id=0, seq=1, data='X' * payload_size)
Klement Sekera611864f2018-09-26 11:19:00 +0200259 for i in range(count)]
260
Klement Sekera31da2e32018-06-24 22:49:55 +0200261
Neale Ranns4f33c802019-04-10 12:39:10 +0000262class IpsecTcp(object):
263 def verify_tcp_checksum(self):
Klement Sekera31da2e32018-06-24 22:49:55 +0200264 self.vapi.cli("test http server")
Klement Sekera611864f2018-09-26 11:19:00 +0200265 p = self.params[socket.AF_INET]
Klement Sekera31da2e32018-06-24 22:49:55 +0200266 send = (Ether(src=self.tun_if.remote_mac, dst=self.tun_if.local_mac) /
Neale Ranns2ac885c2019-03-20 18:24:43 +0000267 p.scapy_tun_sa.encrypt(IP(src=p.remote_tun_if_host,
268 dst=self.tun_if.local_ip4) /
269 TCP(flags='S', dport=80)))
Klement Sekera31da2e32018-06-24 22:49:55 +0200270 self.logger.debug(ppp("Sending packet:", send))
Klement Sekera611864f2018-09-26 11:19:00 +0200271 recv = self.send_and_expect(self.tun_if, [send], self.tun_if)
Klement Sekera31da2e32018-06-24 22:49:55 +0200272 recv = recv[0]
Neale Ranns2ac885c2019-03-20 18:24:43 +0000273 decrypted = p.vpp_tun_sa.decrypt(recv[IP])
Klement Sekera31da2e32018-06-24 22:49:55 +0200274 self.assert_packet_checksums_valid(decrypted)
275
276
Neale Ranns4f33c802019-04-10 12:39:10 +0000277class IpsecTcpTests(IpsecTcp):
278 def test_tcp_checksum(self):
279 """ verify checksum correctness for vpp generated packets """
280 self.verify_tcp_checksum()
281
282
283class IpsecTra4(object):
284 """ verify methods for Transport v4 """
Neale Ranns6afaae12019-07-17 15:07:14 +0000285 def verify_tra_anti_replay(self):
Neale Rannsde847272018-11-28 01:38:34 -0800286 p = self.params[socket.AF_INET]
snaramre5d4b8912019-12-13 23:39:35 +0000287 esn_en = p.vpp_tra_sa.esn_en
Neale Rannsde847272018-11-28 01:38:34 -0800288
Neale Ranns6afaae12019-07-17 15:07:14 +0000289 seq_cycle_node_name = ('/err/%s/sequence number cycled' %
290 self.tra4_encrypt_node_name)
291 replay_node_name = ('/err/%s/SA replayed packet' %
292 self.tra4_decrypt_node_name)
293 if ESP == self.encryption_type and p.crypt_algo == "AES-GCM":
294 hash_failed_node_name = ('/err/%s/ESP decryption failed' %
295 self.tra4_decrypt_node_name)
296 else:
297 hash_failed_node_name = ('/err/%s/Integrity check failed' %
298 self.tra4_decrypt_node_name)
299 replay_count = self.statistics.get_err_counter(replay_node_name)
300 hash_failed_count = self.statistics.get_err_counter(
301 hash_failed_node_name)
302 seq_cycle_count = self.statistics.get_err_counter(seq_cycle_node_name)
Neale Rannsde847272018-11-28 01:38:34 -0800303
Neale Ranns6afaae12019-07-17 15:07:14 +0000304 if ESP == self.encryption_type:
305 undersize_node_name = ('/err/%s/undersized packet' %
306 self.tra4_decrypt_node_name)
307 undersize_count = self.statistics.get_err_counter(
308 undersize_node_name)
309
310 #
311 # send packets with seq numbers 1->34
312 # this means the window size is still in Case B (see RFC4303
313 # Appendix A)
314 #
315 # for reasons i haven't investigated Scapy won't create a packet with
316 # seq_num=0
317 #
318 pkts = [(Ether(src=self.tra_if.remote_mac,
319 dst=self.tra_if.local_mac) /
320 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
321 dst=self.tra_if.local_ip4) /
322 ICMP(),
323 seq_num=seq))
324 for seq in range(1, 34)]
325 recv_pkts = self.send_and_expect(self.tra_if, pkts, self.tra_if)
326
327 # replayed packets are dropped
328 self.send_and_assert_no_replies(self.tra_if, pkts)
329 replay_count += len(pkts)
330 self.assert_error_counter_equal(replay_node_name, replay_count)
331
332 #
Neale Ranns3b9374f2019-08-01 04:45:15 -0700333 # now send a batch of packets all with the same sequence number
334 # the first packet in the batch is legitimate, the rest bogus
335 #
336 pkts = (Ether(src=self.tra_if.remote_mac,
337 dst=self.tra_if.local_mac) /
338 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
339 dst=self.tra_if.local_ip4) /
340 ICMP(),
341 seq_num=35))
342 recv_pkts = self.send_and_expect(self.tra_if, pkts * 8,
343 self.tra_if, n_rx=1)
344 replay_count += 7
345 self.assert_error_counter_equal(replay_node_name, replay_count)
346
347 #
Neale Ranns6afaae12019-07-17 15:07:14 +0000348 # now move the window over to 257 (more than one byte) and into Case A
349 #
Neale Rannsde847272018-11-28 01:38:34 -0800350 pkt = (Ether(src=self.tra_if.remote_mac,
351 dst=self.tra_if.local_mac) /
352 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
353 dst=self.tra_if.local_ip4) /
354 ICMP(),
Neale Ranns6afaae12019-07-17 15:07:14 +0000355 seq_num=257))
Neale Rannsde847272018-11-28 01:38:34 -0800356 recv_pkts = self.send_and_expect(self.tra_if, [pkt], self.tra_if)
357
Neale Ranns3833ffd2019-03-21 14:34:09 +0000358 # replayed packets are dropped
359 self.send_and_assert_no_replies(self.tra_if, pkt * 3)
Neale Ranns6afaae12019-07-17 15:07:14 +0000360 replay_count += 3
361 self.assert_error_counter_equal(replay_node_name, replay_count)
Neale Ranns3833ffd2019-03-21 14:34:09 +0000362
Neale Rannsde847272018-11-28 01:38:34 -0800363 # the window size is 64 packets
364 # in window are still accepted
365 pkt = (Ether(src=self.tra_if.remote_mac,
366 dst=self.tra_if.local_mac) /
367 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
368 dst=self.tra_if.local_ip4) /
369 ICMP(),
Neale Ranns6afaae12019-07-17 15:07:14 +0000370 seq_num=200))
Neale Rannsde847272018-11-28 01:38:34 -0800371 recv_pkts = self.send_and_expect(self.tra_if, [pkt], self.tra_if)
372
Neale Rannsde847272018-11-28 01:38:34 -0800373 # a packet that does not decrypt does not move the window forward
374 bogus_sa = SecurityAssociation(self.encryption_type,
Damjan Mariona829b132019-04-24 23:39:16 +0200375 p.vpp_tra_spi,
376 crypt_algo=p.crypt_algo,
Neale Ranns12989b52019-09-26 16:20:19 +0000377 crypt_key=mk_scapy_crypt_key(p)[::-1],
Damjan Mariona829b132019-04-24 23:39:16 +0200378 auth_algo=p.auth_algo,
379 auth_key=p.auth_key[::-1])
Neale Rannsde847272018-11-28 01:38:34 -0800380 pkt = (Ether(src=self.tra_if.remote_mac,
381 dst=self.tra_if.local_mac) /
382 bogus_sa.encrypt(IP(src=self.tra_if.remote_ip4,
383 dst=self.tra_if.local_ip4) /
384 ICMP(),
385 seq_num=350))
386 self.send_and_assert_no_replies(self.tra_if, pkt * 17)
387
Neale Ranns6afaae12019-07-17 15:07:14 +0000388 hash_failed_count += 17
389 self.assert_error_counter_equal(hash_failed_node_name,
390 hash_failed_count)
Neale Rannsde847272018-11-28 01:38:34 -0800391
Damjan Mariona829b132019-04-24 23:39:16 +0200392 # a malformed 'runt' packet
393 # created by a mis-constructed SA
Neale Ranns2cdcd0c2019-08-27 12:26:14 +0000394 if (ESP == self.encryption_type and p.crypt_algo != "NULL"):
Damjan Mariona829b132019-04-24 23:39:16 +0200395 bogus_sa = SecurityAssociation(self.encryption_type,
396 p.vpp_tra_spi)
397 pkt = (Ether(src=self.tra_if.remote_mac,
398 dst=self.tra_if.local_mac) /
399 bogus_sa.encrypt(IP(src=self.tra_if.remote_ip4,
400 dst=self.tra_if.local_ip4) /
401 ICMP(),
402 seq_num=350))
403 self.send_and_assert_no_replies(self.tra_if, pkt * 17)
404
Neale Ranns6afaae12019-07-17 15:07:14 +0000405 undersize_count += 17
406 self.assert_error_counter_equal(undersize_node_name,
407 undersize_count)
Damjan Mariona829b132019-04-24 23:39:16 +0200408
Neale Rannsde847272018-11-28 01:38:34 -0800409 # which we can determine since this packet is still in the window
410 pkt = (Ether(src=self.tra_if.remote_mac,
411 dst=self.tra_if.local_mac) /
412 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
413 dst=self.tra_if.local_ip4) /
414 ICMP(),
415 seq_num=234))
Klement Sekera14d7e902018-12-10 13:46:09 +0100416 self.send_and_expect(self.tra_if, [pkt], self.tra_if)
Neale Rannsde847272018-11-28 01:38:34 -0800417
Neale Ranns6afaae12019-07-17 15:07:14 +0000418 #
Neale Ranns3833ffd2019-03-21 14:34:09 +0000419 # out of window are dropped
Neale Ranns6afaae12019-07-17 15:07:14 +0000420 # this is Case B. So VPP will consider this to be a high seq num wrap
421 # and so the decrypt attempt will fail
422 #
Neale Ranns3833ffd2019-03-21 14:34:09 +0000423 pkt = (Ether(src=self.tra_if.remote_mac,
424 dst=self.tra_if.local_mac) /
425 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
426 dst=self.tra_if.local_ip4) /
427 ICMP(),
428 seq_num=17))
429 self.send_and_assert_no_replies(self.tra_if, pkt * 17)
Neale Ranns00a44202019-03-21 16:36:28 +0000430
snaramre5d4b8912019-12-13 23:39:35 +0000431 if esn_en:
Neale Ranns3833ffd2019-03-21 14:34:09 +0000432 # an out of window error with ESN looks like a high sequence
433 # wrap. but since it isn't then the verify will fail.
Neale Ranns6afaae12019-07-17 15:07:14 +0000434 hash_failed_count += 17
435 self.assert_error_counter_equal(hash_failed_node_name,
436 hash_failed_count)
Neale Ranns3833ffd2019-03-21 14:34:09 +0000437
438 else:
Neale Ranns6afaae12019-07-17 15:07:14 +0000439 replay_count += 17
440 self.assert_error_counter_equal(replay_node_name,
441 replay_count)
Neale Ranns3833ffd2019-03-21 14:34:09 +0000442
Neale Ranns6afaae12019-07-17 15:07:14 +0000443 # valid packet moves the window over to 258
Neale Ranns00a44202019-03-21 16:36:28 +0000444 pkt = (Ether(src=self.tra_if.remote_mac,
445 dst=self.tra_if.local_mac) /
446 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
447 dst=self.tra_if.local_ip4) /
448 ICMP(),
Neale Ranns6afaae12019-07-17 15:07:14 +0000449 seq_num=258))
Neale Ranns3833ffd2019-03-21 14:34:09 +0000450 rx = self.send_and_expect(self.tra_if, [pkt], self.tra_if)
451 decrypted = p.vpp_tra_sa.decrypt(rx[0][IP])
452
Neale Ranns6afaae12019-07-17 15:07:14 +0000453 #
454 # move VPP's SA TX seq-num to just before the seq-number wrap.
455 # then fire in a packet that VPP should drop on TX because it
456 # causes the TX seq number to wrap; unless we're using extened sequence
457 # numbers.
458 #
Neale Ranns3833ffd2019-03-21 14:34:09 +0000459 self.vapi.cli("test ipsec sa %d seq 0xffffffff" % p.scapy_tra_sa_id)
Neale Ranns6afaae12019-07-17 15:07:14 +0000460 self.logger.info(self.vapi.ppcli("show ipsec sa 0"))
461 self.logger.info(self.vapi.ppcli("show ipsec sa 1"))
Neale Ranns3833ffd2019-03-21 14:34:09 +0000462
Neale Ranns6afaae12019-07-17 15:07:14 +0000463 pkts = [(Ether(src=self.tra_if.remote_mac,
464 dst=self.tra_if.local_mac) /
465 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
466 dst=self.tra_if.local_ip4) /
467 ICMP(),
468 seq_num=seq))
469 for seq in range(259, 280)]
Neale Ranns3833ffd2019-03-21 14:34:09 +0000470
snaramre5d4b8912019-12-13 23:39:35 +0000471 if esn_en:
Neale Ranns6afaae12019-07-17 15:07:14 +0000472 rxs = self.send_and_expect(self.tra_if, pkts, self.tra_if)
Neale Ranns3833ffd2019-03-21 14:34:09 +0000473
Neale Ranns6afaae12019-07-17 15:07:14 +0000474 #
475 # in order for scapy to decrypt its SA's high order number needs
476 # to wrap
477 #
478 p.vpp_tra_sa.seq_num = 0x100000000
479 for rx in rxs:
480 decrypted = p.vpp_tra_sa.decrypt(rx[0][IP])
481
482 #
483 # wrap scapy's TX high sequence number. VPP is in case B, so it
484 # will consider this a high seq wrap also.
485 # The low seq num we set it to will place VPP's RX window in Case A
486 #
Neale Ranns3833ffd2019-03-21 14:34:09 +0000487 p.scapy_tra_sa.seq_num = 0x100000005
488 pkt = (Ether(src=self.tra_if.remote_mac,
489 dst=self.tra_if.local_mac) /
490 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
491 dst=self.tra_if.local_ip4) /
492 ICMP(),
493 seq_num=0x100000005))
494 rx = self.send_and_expect(self.tra_if, [pkt], self.tra_if)
Neale Ranns3833ffd2019-03-21 14:34:09 +0000495 decrypted = p.vpp_tra_sa.decrypt(rx[0][IP])
Neale Ranns6afaae12019-07-17 15:07:14 +0000496
497 #
498 # A packet that has seq num between (2^32-64) and 5 is within
499 # the window
500 #
501 p.scapy_tra_sa.seq_num = 0xfffffffd
502 pkt = (Ether(src=self.tra_if.remote_mac,
503 dst=self.tra_if.local_mac) /
504 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
505 dst=self.tra_if.local_ip4) /
506 ICMP(),
507 seq_num=0xfffffffd))
508 rx = self.send_and_expect(self.tra_if, [pkt], self.tra_if)
509 decrypted = p.vpp_tra_sa.decrypt(rx[0][IP])
510
511 #
512 # While in case A we cannot wrap the high sequence number again
513 # becuase VPP will consider this packet to be one that moves the
514 # window forward
515 #
516 pkt = (Ether(src=self.tra_if.remote_mac,
517 dst=self.tra_if.local_mac) /
518 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
519 dst=self.tra_if.local_ip4) /
520 ICMP(),
521 seq_num=0x200000999))
522 self.send_and_assert_no_replies(self.tra_if, [pkt], self.tra_if)
523
524 hash_failed_count += 1
525 self.assert_error_counter_equal(hash_failed_node_name,
526 hash_failed_count)
527
528 #
529 # but if we move the wondow forward to case B, then we can wrap
530 # again
531 #
532 p.scapy_tra_sa.seq_num = 0x100000555
533 pkt = (Ether(src=self.tra_if.remote_mac,
534 dst=self.tra_if.local_mac) /
535 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
536 dst=self.tra_if.local_ip4) /
537 ICMP(),
538 seq_num=0x100000555))
539 rx = self.send_and_expect(self.tra_if, [pkt], self.tra_if)
540 decrypted = p.vpp_tra_sa.decrypt(rx[0][IP])
541
542 p.scapy_tra_sa.seq_num = 0x200000444
543 pkt = (Ether(src=self.tra_if.remote_mac,
544 dst=self.tra_if.local_mac) /
545 p.scapy_tra_sa.encrypt(IP(src=self.tra_if.remote_ip4,
546 dst=self.tra_if.local_ip4) /
547 ICMP(),
548 seq_num=0x200000444))
549 rx = self.send_and_expect(self.tra_if, [pkt], self.tra_if)
550 decrypted = p.vpp_tra_sa.decrypt(rx[0][IP])
551
Neale Ranns3833ffd2019-03-21 14:34:09 +0000552 else:
Neale Ranns6afaae12019-07-17 15:07:14 +0000553 #
554 # without ESN TX sequence numbers can't wrap and packets are
555 # dropped from here on out.
556 #
557 self.send_and_assert_no_replies(self.tra_if, pkts)
558 seq_cycle_count += len(pkts)
559 self.assert_error_counter_equal(seq_cycle_node_name,
560 seq_cycle_count)
Neale Ranns00a44202019-03-21 16:36:28 +0000561
Neale Rannsde847272018-11-28 01:38:34 -0800562 # move the security-associations seq number on to the last we used
Neale Ranns00a44202019-03-21 16:36:28 +0000563 self.vapi.cli("test ipsec sa %d seq 0x15f" % p.scapy_tra_sa_id)
Neale Rannsde847272018-11-28 01:38:34 -0800564 p.scapy_tra_sa.seq_num = 351
565 p.vpp_tra_sa.seq_num = 351
566
Filip Tehlarefcad1a2020-02-04 09:36:04 +0000567 def verify_tra_basic4(self, count=1, payload_size=54):
Klement Sekera31da2e32018-06-24 22:49:55 +0200568 """ ipsec v4 transport basic test """
Klement Sekera10d066e2018-11-13 11:12:57 +0100569 self.vapi.cli("clear errors")
Neale Ranns6afaae12019-07-17 15:07:14 +0000570 self.vapi.cli("clear ipsec sa")
Klement Sekera31da2e32018-06-24 22:49:55 +0200571 try:
Klement Sekera611864f2018-09-26 11:19:00 +0200572 p = self.params[socket.AF_INET]
Neale Ranns28287212019-12-16 00:53:11 +0000573 send_pkts = self.gen_encrypt_pkts(p, p.scapy_tra_sa, self.tra_if,
Klement Sekera31da2e32018-06-24 22:49:55 +0200574 src=self.tra_if.remote_ip4,
575 dst=self.tra_if.local_ip4,
Filip Tehlarefcad1a2020-02-04 09:36:04 +0000576 count=count,
577 payload_size=payload_size)
Klement Sekera31da2e32018-06-24 22:49:55 +0200578 recv_pkts = self.send_and_expect(self.tra_if, send_pkts,
Klement Sekera611864f2018-09-26 11:19:00 +0200579 self.tra_if)
Neale Rannsde847272018-11-28 01:38:34 -0800580 for rx in recv_pkts:
Neale Ranns1b582b82019-04-18 19:49:13 -0700581 self.assertEqual(len(rx) - len(Ether()), rx[IP].len)
582 self.assert_packet_checksums_valid(rx)
Klement Sekera611864f2018-09-26 11:19:00 +0200583 try:
Neale Rannsde847272018-11-28 01:38:34 -0800584 decrypted = p.vpp_tra_sa.decrypt(rx[IP])
Klement Sekera611864f2018-09-26 11:19:00 +0200585 self.assert_packet_checksums_valid(decrypted)
586 except:
Neale Rannsde847272018-11-28 01:38:34 -0800587 self.logger.debug(ppp("Unexpected packet:", rx))
Klement Sekera611864f2018-09-26 11:19:00 +0200588 raise
Klement Sekera31da2e32018-06-24 22:49:55 +0200589 finally:
590 self.logger.info(self.vapi.ppcli("show error"))
Paul Vinciguerra9673e3e2019-05-10 20:41:08 -0400591 self.logger.info(self.vapi.ppcli("show ipsec all"))
Klement Sekera31da2e32018-06-24 22:49:55 +0200592
Neale Rannseba31ec2019-02-17 18:04:27 +0000593 pkts = p.tra_sa_in.get_stats()['packets']
594 self.assertEqual(pkts, count,
595 "incorrect SA in counts: expected %d != %d" %
596 (count, pkts))
597 pkts = p.tra_sa_out.get_stats()['packets']
598 self.assertEqual(pkts, count,
599 "incorrect SA out counts: expected %d != %d" %
600 (count, pkts))
601
Klement Sekera10d066e2018-11-13 11:12:57 +0100602 self.assert_packet_counter_equal(self.tra4_encrypt_node_name, count)
603 self.assert_packet_counter_equal(self.tra4_decrypt_node_name, count)
604
Neale Ranns4f33c802019-04-10 12:39:10 +0000605
606class IpsecTra4Tests(IpsecTra4):
607 """ UT test methods for Transport v4 """
608 def test_tra_anti_replay(self):
Paul Vinciguerra6e20e032019-12-27 00:19:23 -0500609 """ ipsec v4 transport anti-replay test """
Neale Ranns6afaae12019-07-17 15:07:14 +0000610 self.verify_tra_anti_replay()
Neale Ranns4f33c802019-04-10 12:39:10 +0000611
612 def test_tra_basic(self, count=1):
613 """ ipsec v4 transport basic test """
614 self.verify_tra_basic4(count=1)
615
Klement Sekera31da2e32018-06-24 22:49:55 +0200616 def test_tra_burst(self):
617 """ ipsec v4 transport burst test """
Neale Ranns4f33c802019-04-10 12:39:10 +0000618 self.verify_tra_basic4(count=257)
Klement Sekera611864f2018-09-26 11:19:00 +0200619
Neale Ranns53f526b2019-02-25 14:32:02 +0000620
Neale Ranns4f33c802019-04-10 12:39:10 +0000621class IpsecTra6(object):
622 """ verify methods for Transport v6 """
Filip Tehlarefcad1a2020-02-04 09:36:04 +0000623 def verify_tra_basic6(self, count=1, payload_size=54):
Klement Sekera10d066e2018-11-13 11:12:57 +0100624 self.vapi.cli("clear errors")
Filip Tehlarefcad1a2020-02-04 09:36:04 +0000625 self.vapi.cli("clear ipsec sa")
Klement Sekera31da2e32018-06-24 22:49:55 +0200626 try:
Klement Sekera611864f2018-09-26 11:19:00 +0200627 p = self.params[socket.AF_INET6]
Neale Ranns28287212019-12-16 00:53:11 +0000628 send_pkts = self.gen_encrypt_pkts6(p, p.scapy_tra_sa, self.tra_if,
Klement Sekera611864f2018-09-26 11:19:00 +0200629 src=self.tra_if.remote_ip6,
630 dst=self.tra_if.local_ip6,
Filip Tehlarefcad1a2020-02-04 09:36:04 +0000631 count=count,
632 payload_size=payload_size)
Klement Sekera611864f2018-09-26 11:19:00 +0200633 recv_pkts = self.send_and_expect(self.tra_if, send_pkts,
634 self.tra_if)
Neale Rannsde847272018-11-28 01:38:34 -0800635 for rx in recv_pkts:
Neale Rannsd207fd72019-04-18 17:18:12 -0700636 self.assertEqual(len(rx) - len(Ether()) - len(IPv6()),
637 rx[IPv6].plen)
Klement Sekera611864f2018-09-26 11:19:00 +0200638 try:
Neale Rannsde847272018-11-28 01:38:34 -0800639 decrypted = p.vpp_tra_sa.decrypt(rx[IPv6])
Klement Sekera611864f2018-09-26 11:19:00 +0200640 self.assert_packet_checksums_valid(decrypted)
641 except:
Neale Rannsde847272018-11-28 01:38:34 -0800642 self.logger.debug(ppp("Unexpected packet:", rx))
Klement Sekera611864f2018-09-26 11:19:00 +0200643 raise
Klement Sekera31da2e32018-06-24 22:49:55 +0200644 finally:
645 self.logger.info(self.vapi.ppcli("show error"))
Paul Vinciguerra9673e3e2019-05-10 20:41:08 -0400646 self.logger.info(self.vapi.ppcli("show ipsec all"))
Klement Sekera31da2e32018-06-24 22:49:55 +0200647
Neale Rannseba31ec2019-02-17 18:04:27 +0000648 pkts = p.tra_sa_in.get_stats()['packets']
649 self.assertEqual(pkts, count,
650 "incorrect SA in counts: expected %d != %d" %
651 (count, pkts))
652 pkts = p.tra_sa_out.get_stats()['packets']
653 self.assertEqual(pkts, count,
654 "incorrect SA out counts: expected %d != %d" %
655 (count, pkts))
Klement Sekera10d066e2018-11-13 11:12:57 +0100656 self.assert_packet_counter_equal(self.tra6_encrypt_node_name, count)
657 self.assert_packet_counter_equal(self.tra6_decrypt_node_name, count)
658
Neale Ranns02950402019-12-20 00:54:57 +0000659 def gen_encrypt_pkts_ext_hdrs6(self, sa, sw_intf, src, dst, count=1,
660 payload_size=54):
661 return [Ether(src=sw_intf.remote_mac, dst=sw_intf.local_mac) /
662 sa.encrypt(IPv6(src=src, dst=dst) /
663 ICMPv6EchoRequest(id=0, seq=1,
664 data='X' * payload_size))
665 for i in range(count)]
666
667 def gen_pkts_ext_hdrs6(self, sw_intf, src, dst, count=1, payload_size=54):
668 return [Ether(src=sw_intf.remote_mac, dst=sw_intf.local_mac) /
669 IPv6(src=src, dst=dst) /
670 IPv6ExtHdrHopByHop() /
671 IPv6ExtHdrFragment(id=2, offset=200) /
672 Raw(b'\xff' * 200)
673 for i in range(count)]
674
675 def verify_tra_encrypted6(self, p, sa, rxs):
676 decrypted = []
677 for rx in rxs:
678 self.assert_packet_checksums_valid(rx)
679 try:
680 decrypt_pkt = p.vpp_tra_sa.decrypt(rx[IPv6])
681 decrypted.append(decrypt_pkt)
682 self.assert_equal(decrypt_pkt.src, self.tra_if.local_ip6)
683 self.assert_equal(decrypt_pkt.dst, self.tra_if.remote_ip6)
684 except:
685 self.logger.debug(ppp("Unexpected packet:", rx))
686 try:
687 self.logger.debug(ppp("Decrypted packet:", decrypt_pkt))
688 except:
689 pass
690 raise
691 return decrypted
692
693 def verify_tra_66_ext_hdrs(self, p):
694 count = 63
695
696 #
697 # check we can decrypt with options
698 #
699 tx = self.gen_encrypt_pkts_ext_hdrs6(p.scapy_tra_sa, self.tra_if,
700 src=self.tra_if.remote_ip6,
701 dst=self.tra_if.local_ip6,
702 count=count)
703 self.send_and_expect(self.tra_if, tx, self.tra_if)
704
705 #
706 # injecting a packet from ourselves to be routed of box is a hack
707 # but it matches an outbout policy, alors je ne regrette rien
708 #
709
710 # one extension before ESP
711 tx = (Ether(src=self.pg2.remote_mac, dst=self.pg2.local_mac) /
712 IPv6(src=self.tra_if.local_ip6,
713 dst=self.tra_if.remote_ip6) /
714 IPv6ExtHdrFragment(id=2, offset=200) /
715 Raw(b'\xff' * 200))
716
717 rxs = self.send_and_expect(self.pg2, [tx], self.tra_if)
718 dcs = self.verify_tra_encrypted6(p, p.vpp_tra_sa, rxs)
719
720 for dc in dcs:
721 # for reasons i'm not going to investigate scapy does not
722 # created the correct headers after decrypt. but reparsing
723 # the ipv6 packet fixes it
724 dc = IPv6(raw(dc[IPv6]))
725 self.assert_equal(dc[IPv6ExtHdrFragment].id, 2)
726
727 # two extensions before ESP
728 tx = (Ether(src=self.pg2.remote_mac, dst=self.pg2.local_mac) /
729 IPv6(src=self.tra_if.local_ip6,
730 dst=self.tra_if.remote_ip6) /
731 IPv6ExtHdrHopByHop() /
732 IPv6ExtHdrFragment(id=2, offset=200) /
733 Raw(b'\xff' * 200))
734
735 rxs = self.send_and_expect(self.pg2, [tx], self.tra_if)
736 dcs = self.verify_tra_encrypted6(p, p.vpp_tra_sa, rxs)
737
738 for dc in dcs:
739 dc = IPv6(raw(dc[IPv6]))
740 self.assertTrue(dc[IPv6ExtHdrHopByHop])
741 self.assert_equal(dc[IPv6ExtHdrFragment].id, 2)
742
743 # two extensions before ESP, one after
744 tx = (Ether(src=self.pg2.remote_mac, dst=self.pg2.local_mac) /
745 IPv6(src=self.tra_if.local_ip6,
746 dst=self.tra_if.remote_ip6) /
747 IPv6ExtHdrHopByHop() /
748 IPv6ExtHdrFragment(id=2, offset=200) /
749 IPv6ExtHdrDestOpt() /
750 Raw(b'\xff' * 200))
751
752 rxs = self.send_and_expect(self.pg2, [tx], self.tra_if)
753 dcs = self.verify_tra_encrypted6(p, p.vpp_tra_sa, rxs)
754
755 for dc in dcs:
756 dc = IPv6(raw(dc[IPv6]))
757 self.assertTrue(dc[IPv6ExtHdrDestOpt])
758 self.assertTrue(dc[IPv6ExtHdrHopByHop])
759 self.assert_equal(dc[IPv6ExtHdrFragment].id, 2)
760
Neale Ranns4f33c802019-04-10 12:39:10 +0000761
762class IpsecTra6Tests(IpsecTra6):
763 """ UT test methods for Transport v6 """
764 def test_tra_basic6(self):
765 """ ipsec v6 transport basic test """
766 self.verify_tra_basic6(count=1)
767
Klement Sekera611864f2018-09-26 11:19:00 +0200768 def test_tra_burst6(self):
769 """ ipsec v6 transport burst test """
Neale Ranns4f33c802019-04-10 12:39:10 +0000770 self.verify_tra_basic6(count=257)
Klement Sekera31da2e32018-06-24 22:49:55 +0200771
Klement Sekera611864f2018-09-26 11:19:00 +0200772
Neale Ranns02950402019-12-20 00:54:57 +0000773class IpsecTra6ExtTests(IpsecTra6):
774 def test_tra_ext_hdrs_66(self):
775 """ ipsec 6o6 tra extension headers test """
776 self.verify_tra_66_ext_hdrs(self.params[socket.AF_INET6])
777
778
Neale Ranns53f526b2019-02-25 14:32:02 +0000779class IpsecTra46Tests(IpsecTra4Tests, IpsecTra6Tests):
Neale Ranns4f33c802019-04-10 12:39:10 +0000780 """ UT test methods for Transport v6 and v4"""
Neale Ranns53f526b2019-02-25 14:32:02 +0000781 pass
782
783
Neale Ranns2ac885c2019-03-20 18:24:43 +0000784class IpsecTun4(object):
Neale Ranns4f33c802019-04-10 12:39:10 +0000785 """ verify methods for Tunnel v4 """
Neale Ranns4a56f4e2019-12-23 04:10:25 +0000786 def verify_counters4(self, p, count, n_frags=None, worker=None):
Klement Sekera6aa58b72019-05-16 14:34:55 +0200787 if not n_frags:
788 n_frags = count
Neale Ranns987aea82019-03-27 13:40:35 +0000789 if (hasattr(p, "spd_policy_in_any")):
Neale Ranns4a56f4e2019-12-23 04:10:25 +0000790 pkts = p.spd_policy_in_any.get_stats(worker)['packets']
Neale Ranns987aea82019-03-27 13:40:35 +0000791 self.assertEqual(pkts, count,
792 "incorrect SPD any policy: expected %d != %d" %
793 (count, pkts))
794
795 if (hasattr(p, "tun_sa_in")):
Neale Ranns4a56f4e2019-12-23 04:10:25 +0000796 pkts = p.tun_sa_in.get_stats(worker)['packets']
Neale Ranns987aea82019-03-27 13:40:35 +0000797 self.assertEqual(pkts, count,
798 "incorrect SA in counts: expected %d != %d" %
799 (count, pkts))
Neale Ranns4a56f4e2019-12-23 04:10:25 +0000800 pkts = p.tun_sa_out.get_stats(worker)['packets']
Neale Ranns987aea82019-03-27 13:40:35 +0000801 self.assertEqual(pkts, count,
802 "incorrect SA out counts: expected %d != %d" %
803 (count, pkts))
804
Klement Sekera6aa58b72019-05-16 14:34:55 +0200805 self.assert_packet_counter_equal(self.tun4_encrypt_node_name, n_frags)
Neale Ranns987aea82019-03-27 13:40:35 +0000806 self.assert_packet_counter_equal(self.tun4_decrypt_node_name, count)
807
Neale Rannsf05e7322019-03-29 20:23:58 +0000808 def verify_decrypted(self, p, rxs):
809 for rx in rxs:
810 self.assert_equal(rx[IP].src, p.remote_tun_if_host)
811 self.assert_equal(rx[IP].dst, self.pg1.remote_ip4)
812 self.assert_packet_checksums_valid(rx)
813
Christian Hoppsfb7e7ed2019-11-03 07:02:15 -0500814 def verify_esp_padding(self, sa, esp_payload, decrypt_pkt):
815 align = sa.crypt_algo.block_size
816 if align < 4:
817 align = 4
818 exp_len = (len(decrypt_pkt) + 2 + (align - 1)) & ~(align - 1)
819 exp_len += sa.crypt_algo.iv_size
820 exp_len += sa.crypt_algo.icv_size or sa.auth_algo.icv_size
821 self.assertEqual(exp_len, len(esp_payload))
822
Neale Rannsf05e7322019-03-29 20:23:58 +0000823 def verify_encrypted(self, p, sa, rxs):
824 decrypt_pkts = []
825 for rx in rxs:
Neale Ranns41afb332019-07-16 06:19:35 -0700826 if p.nat_header:
827 self.assertEqual(rx[UDP].dport, 4500)
Neale Ranns1b582b82019-04-18 19:49:13 -0700828 self.assert_packet_checksums_valid(rx)
829 self.assertEqual(len(rx) - len(Ether()), rx[IP].len)
Neale Rannsf05e7322019-03-29 20:23:58 +0000830 try:
Christian Hoppsfb7e7ed2019-11-03 07:02:15 -0500831 rx_ip = rx[IP]
832 decrypt_pkt = p.vpp_tun_sa.decrypt(rx_ip)
Neale Rannsf05e7322019-03-29 20:23:58 +0000833 if not decrypt_pkt.haslayer(IP):
834 decrypt_pkt = IP(decrypt_pkt[Raw].load)
Christian Hoppsfb7e7ed2019-11-03 07:02:15 -0500835 if rx_ip.proto == socket.IPPROTO_ESP:
836 self.verify_esp_padding(sa, rx_ip[ESP].data, decrypt_pkt)
Neale Rannsf05e7322019-03-29 20:23:58 +0000837 decrypt_pkts.append(decrypt_pkt)
838 self.assert_equal(decrypt_pkt.src, self.pg1.remote_ip4)
839 self.assert_equal(decrypt_pkt.dst, p.remote_tun_if_host)
840 except:
841 self.logger.debug(ppp("Unexpected packet:", rx))
842 try:
843 self.logger.debug(ppp("Decrypted packet:", decrypt_pkt))
844 except:
845 pass
846 raise
847 pkts = reassemble4(decrypt_pkts)
848 for pkt in pkts:
849 self.assert_packet_checksums_valid(pkt)
850
Neale Rannsd7603d92019-03-28 08:56:10 +0000851 def verify_tun_44(self, p, count=1, payload_size=64, n_rx=None):
Klement Sekera10d066e2018-11-13 11:12:57 +0100852 self.vapi.cli("clear errors")
Neale Ranns02950402019-12-20 00:54:57 +0000853 self.vapi.cli("clear ipsec counters")
Neale Ranns28287212019-12-16 00:53:11 +0000854 self.vapi.cli("clear ipsec sa")
Neale Rannsd7603d92019-03-28 08:56:10 +0000855 if not n_rx:
856 n_rx = count
Klement Sekera31da2e32018-06-24 22:49:55 +0200857 try:
Neale Ranns28287212019-12-16 00:53:11 +0000858 send_pkts = self.gen_encrypt_pkts(p, p.scapy_tun_sa, self.tun_if,
Klement Sekera611864f2018-09-26 11:19:00 +0200859 src=p.remote_tun_if_host,
Klement Sekera31da2e32018-06-24 22:49:55 +0200860 dst=self.pg1.remote_ip4,
Filip Tehlarefcad1a2020-02-04 09:36:04 +0000861 count=count,
862 payload_size=payload_size)
Klement Sekera611864f2018-09-26 11:19:00 +0200863 recv_pkts = self.send_and_expect(self.tun_if, send_pkts, self.pg1)
Neale Rannsf05e7322019-03-29 20:23:58 +0000864 self.verify_decrypted(p, recv_pkts)
865
Klement Sekera31da2e32018-06-24 22:49:55 +0200866 send_pkts = self.gen_pkts(self.pg1, src=self.pg1.remote_ip4,
Neale Rannsd7603d92019-03-28 08:56:10 +0000867 dst=p.remote_tun_if_host, count=count,
868 payload_size=payload_size)
869 recv_pkts = self.send_and_expect(self.pg1, send_pkts,
870 self.tun_if, n_rx)
Neale Rannsf05e7322019-03-29 20:23:58 +0000871 self.verify_encrypted(p, p.vpp_tun_sa, recv_pkts)
872
Neale Rannsf3a66222020-01-02 05:04:00 +0000873 for rx in recv_pkts:
874 self.assertEqual(rx[IP].src, p.tun_src)
875 self.assertEqual(rx[IP].dst, p.tun_dst)
876
Klement Sekera31da2e32018-06-24 22:49:55 +0200877 finally:
878 self.logger.info(self.vapi.ppcli("show error"))
Paul Vinciguerra9673e3e2019-05-10 20:41:08 -0400879 self.logger.info(self.vapi.ppcli("show ipsec all"))
Klement Sekera31da2e32018-06-24 22:49:55 +0200880
Neale Ranns02950402019-12-20 00:54:57 +0000881 self.logger.info(self.vapi.ppcli("show ipsec sa 0"))
882 self.logger.info(self.vapi.ppcli("show ipsec sa 4"))
Klement Sekera6aa58b72019-05-16 14:34:55 +0200883 self.verify_counters4(p, count, n_rx)
Neale Rannseba31ec2019-02-17 18:04:27 +0000884
Neale Ranns28287212019-12-16 00:53:11 +0000885 def verify_tun_dropped_44(self, p, count=1, payload_size=64, n_rx=None):
886 self.vapi.cli("clear errors")
887 if not n_rx:
888 n_rx = count
889 try:
890 send_pkts = self.gen_encrypt_pkts(p, p.scapy_tun_sa, self.tun_if,
891 src=p.remote_tun_if_host,
892 dst=self.pg1.remote_ip4,
893 count=count)
894 self.send_and_assert_no_replies(self.tun_if, send_pkts)
895
896 send_pkts = self.gen_pkts(self.pg1, src=self.pg1.remote_ip4,
897 dst=p.remote_tun_if_host, count=count,
898 payload_size=payload_size)
899 self.send_and_assert_no_replies(self.pg1, send_pkts)
900
901 finally:
902 self.logger.info(self.vapi.ppcli("show error"))
903 self.logger.info(self.vapi.ppcli("show ipsec all"))
904
Neale Ranns14046982019-07-29 14:49:52 +0000905 def verify_tun_reass_44(self, p):
906 self.vapi.cli("clear errors")
907 self.vapi.ip_reassembly_enable_disable(
908 sw_if_index=self.tun_if.sw_if_index, enable_ip4=True)
909
910 try:
Neale Ranns28287212019-12-16 00:53:11 +0000911 send_pkts = self.gen_encrypt_pkts(p, p.scapy_tun_sa, self.tun_if,
Neale Ranns14046982019-07-29 14:49:52 +0000912 src=p.remote_tun_if_host,
913 dst=self.pg1.remote_ip4,
914 payload_size=1900,
915 count=1)
916 send_pkts = fragment_rfc791(send_pkts[0], 1400)
917 recv_pkts = self.send_and_expect(self.tun_if, send_pkts,
918 self.pg1, n_rx=1)
919 self.verify_decrypted(p, recv_pkts)
920
921 send_pkts = self.gen_pkts(self.pg1, src=self.pg1.remote_ip4,
922 dst=p.remote_tun_if_host, count=1)
923 recv_pkts = self.send_and_expect(self.pg1, send_pkts,
924 self.tun_if)
925 self.verify_encrypted(p, p.vpp_tun_sa, recv_pkts)
926
927 finally:
928 self.logger.info(self.vapi.ppcli("show error"))
929 self.logger.info(self.vapi.ppcli("show ipsec all"))
930
931 self.verify_counters4(p, 1, 1)
932 self.vapi.ip_reassembly_enable_disable(
933 sw_if_index=self.tun_if.sw_if_index, enable_ip4=False)
934
Neale Ranns987aea82019-03-27 13:40:35 +0000935 def verify_tun_64(self, p, count=1):
936 self.vapi.cli("clear errors")
Neale Rannsdd4ccf22020-06-30 07:47:14 +0000937 self.vapi.cli("clear ipsec sa")
Neale Ranns987aea82019-03-27 13:40:35 +0000938 try:
Neale Ranns28287212019-12-16 00:53:11 +0000939 send_pkts = self.gen_encrypt_pkts6(p, p.scapy_tun_sa, self.tun_if,
Neale Ranns987aea82019-03-27 13:40:35 +0000940 src=p.remote_tun_if_host6,
941 dst=self.pg1.remote_ip6,
942 count=count)
943 recv_pkts = self.send_and_expect(self.tun_if, send_pkts, self.pg1)
944 for recv_pkt in recv_pkts:
945 self.assert_equal(recv_pkt[IPv6].src, p.remote_tun_if_host6)
946 self.assert_equal(recv_pkt[IPv6].dst, self.pg1.remote_ip6)
947 self.assert_packet_checksums_valid(recv_pkt)
948 send_pkts = self.gen_pkts6(self.pg1, src=self.pg1.remote_ip6,
949 dst=p.remote_tun_if_host6, count=count)
950 recv_pkts = self.send_and_expect(self.pg1, send_pkts, self.tun_if)
951 for recv_pkt in recv_pkts:
952 try:
953 decrypt_pkt = p.vpp_tun_sa.decrypt(recv_pkt[IP])
954 if not decrypt_pkt.haslayer(IPv6):
955 decrypt_pkt = IPv6(decrypt_pkt[Raw].load)
956 self.assert_equal(decrypt_pkt.src, self.pg1.remote_ip6)
957 self.assert_equal(decrypt_pkt.dst, p.remote_tun_if_host6)
958 self.assert_packet_checksums_valid(decrypt_pkt)
959 except:
960 self.logger.error(ppp("Unexpected packet:", recv_pkt))
961 try:
962 self.logger.debug(
963 ppp("Decrypted packet:", decrypt_pkt))
964 except:
965 pass
966 raise
967 finally:
968 self.logger.info(self.vapi.ppcli("show error"))
Paul Vinciguerra9673e3e2019-05-10 20:41:08 -0400969 self.logger.info(self.vapi.ppcli("show ipsec all"))
Neale Rannseba31ec2019-02-17 18:04:27 +0000970
Klement Sekera6aa58b72019-05-16 14:34:55 +0200971 self.verify_counters4(p, count)
Klement Sekera10d066e2018-11-13 11:12:57 +0100972
Neale Ranns41afb332019-07-16 06:19:35 -0700973 def verify_keepalive(self, p):
974 pkt = (Ether(src=self.tun_if.remote_mac, dst=self.tun_if.local_mac) /
975 IP(src=p.remote_tun_if_host, dst=self.tun_if.local_ip4) /
976 UDP(sport=333, dport=4500) /
Ole Troan8b76c232019-10-21 20:55:13 +0200977 Raw(b'\xff'))
Neale Ranns41afb332019-07-16 06:19:35 -0700978 self.send_and_assert_no_replies(self.tun_if, pkt*31)
979 self.assert_error_counter_equal(
980 '/err/%s/NAT Keepalive' % self.tun4_input_node, 31)
981
982 pkt = (Ether(src=self.tun_if.remote_mac, dst=self.tun_if.local_mac) /
983 IP(src=p.remote_tun_if_host, dst=self.tun_if.local_ip4) /
984 UDP(sport=333, dport=4500) /
Ole Troan8b76c232019-10-21 20:55:13 +0200985 Raw(b'\xfe'))
Neale Ranns41afb332019-07-16 06:19:35 -0700986 self.send_and_assert_no_replies(self.tun_if, pkt*31)
987 self.assert_error_counter_equal(
988 '/err/%s/Too Short' % self.tun4_input_node, 31)
989
Neale Ranns2ac885c2019-03-20 18:24:43 +0000990
991class IpsecTun4Tests(IpsecTun4):
Neale Ranns4f33c802019-04-10 12:39:10 +0000992 """ UT test methods for Tunnel v4 """
Neale Ranns2ac885c2019-03-20 18:24:43 +0000993 def test_tun_basic44(self):
994 """ ipsec 4o4 tunnel basic test """
995 self.verify_tun_44(self.params[socket.AF_INET], count=1)
Neale Ranns02950402019-12-20 00:54:57 +0000996 self.tun_if.admin_down()
997 self.tun_if.resolve_arp()
998 self.tun_if.admin_up()
999 self.verify_tun_44(self.params[socket.AF_INET], count=1)
Neale Ranns2ac885c2019-03-20 18:24:43 +00001000
Neale Ranns14046982019-07-29 14:49:52 +00001001 def test_tun_reass_basic44(self):
1002 """ ipsec 4o4 tunnel basic reassembly test """
1003 self.verify_tun_reass_44(self.params[socket.AF_INET])
1004
Klement Sekera611864f2018-09-26 11:19:00 +02001005 def test_tun_burst44(self):
Klement Sekera31da2e32018-06-24 22:49:55 +02001006 """ ipsec 4o4 tunnel burst test """
Neale Ranns02950402019-12-20 00:54:57 +00001007 self.verify_tun_44(self.params[socket.AF_INET], count=127)
1008
1009
Neale Ranns2ac885c2019-03-20 18:24:43 +00001010class IpsecTun6(object):
Neale Ranns4f33c802019-04-10 12:39:10 +00001011 """ verify methods for Tunnel v6 """
Neale Ranns4a56f4e2019-12-23 04:10:25 +00001012 def verify_counters6(self, p_in, p_out, count, worker=None):
Neale Rannsc87b66c2019-02-07 07:26:12 -08001013 if (hasattr(p_in, "tun_sa_in")):
Neale Ranns4a56f4e2019-12-23 04:10:25 +00001014 pkts = p_in.tun_sa_in.get_stats(worker)['packets']
Neale Ranns987aea82019-03-27 13:40:35 +00001015 self.assertEqual(pkts, count,
1016 "incorrect SA in counts: expected %d != %d" %
1017 (count, pkts))
Neale Rannsc87b66c2019-02-07 07:26:12 -08001018 if (hasattr(p_out, "tun_sa_out")):
Neale Ranns4a56f4e2019-12-23 04:10:25 +00001019 pkts = p_out.tun_sa_out.get_stats(worker)['packets']
Neale Ranns987aea82019-03-27 13:40:35 +00001020 self.assertEqual(pkts, count,
1021 "incorrect SA out counts: expected %d != %d" %
1022 (count, pkts))
1023 self.assert_packet_counter_equal(self.tun6_encrypt_node_name, count)
1024 self.assert_packet_counter_equal(self.tun6_decrypt_node_name, count)
1025
Neale Rannsc87b66c2019-02-07 07:26:12 -08001026 def verify_decrypted6(self, p, rxs):
1027 for rx in rxs:
1028 self.assert_equal(rx[IPv6].src, p.remote_tun_if_host)
1029 self.assert_equal(rx[IPv6].dst, self.pg1.remote_ip6)
1030 self.assert_packet_checksums_valid(rx)
1031
1032 def verify_encrypted6(self, p, sa, rxs):
1033 for rx in rxs:
1034 self.assert_packet_checksums_valid(rx)
1035 self.assertEqual(len(rx) - len(Ether()) - len(IPv6()),
1036 rx[IPv6].plen)
1037 try:
1038 decrypt_pkt = p.vpp_tun_sa.decrypt(rx[IPv6])
1039 if not decrypt_pkt.haslayer(IPv6):
1040 decrypt_pkt = IPv6(decrypt_pkt[Raw].load)
1041 self.assert_packet_checksums_valid(decrypt_pkt)
1042 self.assert_equal(decrypt_pkt.src, self.pg1.remote_ip6)
1043 self.assert_equal(decrypt_pkt.dst, p.remote_tun_if_host)
1044 except:
1045 self.logger.debug(ppp("Unexpected packet:", rx))
1046 try:
1047 self.logger.debug(ppp("Decrypted packet:", decrypt_pkt))
1048 except:
1049 pass
1050 raise
1051
1052 def verify_drop_tun_66(self, p_in, count=1, payload_size=64):
Klement Sekera10d066e2018-11-13 11:12:57 +01001053 self.vapi.cli("clear errors")
Neale Rannsc87b66c2019-02-07 07:26:12 -08001054 self.vapi.cli("clear ipsec sa")
1055
Neale Ranns28287212019-12-16 00:53:11 +00001056 send_pkts = self.gen_encrypt_pkts6(p_in, p_in.scapy_tun_sa,
1057 self.tun_if,
Neale Rannsc87b66c2019-02-07 07:26:12 -08001058 src=p_in.remote_tun_if_host,
1059 dst=self.pg1.remote_ip6,
1060 count=count)
1061 self.send_and_assert_no_replies(self.tun_if, send_pkts)
1062 self.logger.info(self.vapi.cli("sh punt stats"))
1063
1064 def verify_tun_66(self, p_in, p_out=None, count=1, payload_size=64):
1065 self.vapi.cli("clear errors")
1066 self.vapi.cli("clear ipsec sa")
1067 if not p_out:
1068 p_out = p_in
Klement Sekera31da2e32018-06-24 22:49:55 +02001069 try:
Neale Ranns28287212019-12-16 00:53:11 +00001070 send_pkts = self.gen_encrypt_pkts6(p_in, p_in.scapy_tun_sa,
1071 self.tun_if,
Neale Rannsc87b66c2019-02-07 07:26:12 -08001072 src=p_in.remote_tun_if_host,
Klement Sekera611864f2018-09-26 11:19:00 +02001073 dst=self.pg1.remote_ip6,
Filip Tehlarefcad1a2020-02-04 09:36:04 +00001074 count=count,
1075 payload_size=payload_size)
Klement Sekera611864f2018-09-26 11:19:00 +02001076 recv_pkts = self.send_and_expect(self.tun_if, send_pkts, self.pg1)
Neale Rannsc87b66c2019-02-07 07:26:12 -08001077 self.verify_decrypted6(p_in, recv_pkts)
1078
Klement Sekera611864f2018-09-26 11:19:00 +02001079 send_pkts = self.gen_pkts6(self.pg1, src=self.pg1.remote_ip6,
Neale Rannsc87b66c2019-02-07 07:26:12 -08001080 dst=p_out.remote_tun_if_host,
1081 count=count,
1082 payload_size=payload_size)
Neale Ranns4a56f4e2019-12-23 04:10:25 +00001083 recv_pkts = self.send_and_expect(self.pg1, send_pkts, self.tun_if)
Neale Rannsc87b66c2019-02-07 07:26:12 -08001084 self.verify_encrypted6(p_out, p_out.vpp_tun_sa, recv_pkts)
1085
Neale Rannsf3a66222020-01-02 05:04:00 +00001086 for rx in recv_pkts:
1087 self.assertEqual(rx[IPv6].src, p_out.tun_src)
1088 self.assertEqual(rx[IPv6].dst, p_out.tun_dst)
1089
Klement Sekera31da2e32018-06-24 22:49:55 +02001090 finally:
1091 self.logger.info(self.vapi.ppcli("show error"))
Paul Vinciguerra9673e3e2019-05-10 20:41:08 -04001092 self.logger.info(self.vapi.ppcli("show ipsec all"))
Neale Rannsc87b66c2019-02-07 07:26:12 -08001093 self.verify_counters6(p_in, p_out, count)
Klement Sekera31da2e32018-06-24 22:49:55 +02001094
Neale Ranns14046982019-07-29 14:49:52 +00001095 def verify_tun_reass_66(self, p):
1096 self.vapi.cli("clear errors")
1097 self.vapi.ip_reassembly_enable_disable(
1098 sw_if_index=self.tun_if.sw_if_index, enable_ip6=True)
1099
1100 try:
Neale Ranns28287212019-12-16 00:53:11 +00001101 send_pkts = self.gen_encrypt_pkts6(p, p.scapy_tun_sa, self.tun_if,
Neale Ranns14046982019-07-29 14:49:52 +00001102 src=p.remote_tun_if_host,
1103 dst=self.pg1.remote_ip6,
1104 count=1,
Neale Ranns02950402019-12-20 00:54:57 +00001105 payload_size=1850)
Neale Ranns14046982019-07-29 14:49:52 +00001106 send_pkts = fragment_rfc8200(send_pkts[0], 1, 1400, self.logger)
1107 recv_pkts = self.send_and_expect(self.tun_if, send_pkts,
1108 self.pg1, n_rx=1)
1109 self.verify_decrypted6(p, recv_pkts)
1110
1111 send_pkts = self.gen_pkts6(self.pg1, src=self.pg1.remote_ip6,
1112 dst=p.remote_tun_if_host,
1113 count=1,
1114 payload_size=64)
1115 recv_pkts = self.send_and_expect(self.pg1, send_pkts,
1116 self.tun_if)
1117 self.verify_encrypted6(p, p.vpp_tun_sa, recv_pkts)
1118 finally:
1119 self.logger.info(self.vapi.ppcli("show error"))
1120 self.logger.info(self.vapi.ppcli("show ipsec all"))
1121 self.verify_counters6(p, p, 1)
1122 self.vapi.ip_reassembly_enable_disable(
1123 sw_if_index=self.tun_if.sw_if_index, enable_ip6=False)
1124
Neale Ranns987aea82019-03-27 13:40:35 +00001125 def verify_tun_46(self, p, count=1):
1126 """ ipsec 4o6 tunnel basic test """
1127 self.vapi.cli("clear errors")
Neale Rannsdd4ccf22020-06-30 07:47:14 +00001128 self.vapi.cli("clear ipsec sa")
Neale Ranns987aea82019-03-27 13:40:35 +00001129 try:
Neale Ranns28287212019-12-16 00:53:11 +00001130 send_pkts = self.gen_encrypt_pkts(p, p.scapy_tun_sa, self.tun_if,
Neale Ranns987aea82019-03-27 13:40:35 +00001131 src=p.remote_tun_if_host4,
1132 dst=self.pg1.remote_ip4,
1133 count=count)
1134 recv_pkts = self.send_and_expect(self.tun_if, send_pkts, self.pg1)
1135 for recv_pkt in recv_pkts:
1136 self.assert_equal(recv_pkt[IP].src, p.remote_tun_if_host4)
1137 self.assert_equal(recv_pkt[IP].dst, self.pg1.remote_ip4)
1138 self.assert_packet_checksums_valid(recv_pkt)
1139 send_pkts = self.gen_pkts(self.pg1, src=self.pg1.remote_ip4,
1140 dst=p.remote_tun_if_host4,
1141 count=count)
1142 recv_pkts = self.send_and_expect(self.pg1, send_pkts, self.tun_if)
1143 for recv_pkt in recv_pkts:
1144 try:
1145 decrypt_pkt = p.vpp_tun_sa.decrypt(recv_pkt[IPv6])
1146 if not decrypt_pkt.haslayer(IP):
1147 decrypt_pkt = IP(decrypt_pkt[Raw].load)
1148 self.assert_equal(decrypt_pkt.src, self.pg1.remote_ip4)
1149 self.assert_equal(decrypt_pkt.dst, p.remote_tun_if_host4)
1150 self.assert_packet_checksums_valid(decrypt_pkt)
1151 except:
1152 self.logger.debug(ppp("Unexpected packet:", recv_pkt))
1153 try:
1154 self.logger.debug(ppp("Decrypted packet:",
1155 decrypt_pkt))
1156 except:
1157 pass
1158 raise
1159 finally:
1160 self.logger.info(self.vapi.ppcli("show error"))
Paul Vinciguerra9673e3e2019-05-10 20:41:08 -04001161 self.logger.info(self.vapi.ppcli("show ipsec all"))
Neale Rannsc87b66c2019-02-07 07:26:12 -08001162 self.verify_counters6(p, p, count)
Klement Sekera10d066e2018-11-13 11:12:57 +01001163
Neale Ranns2ac885c2019-03-20 18:24:43 +00001164
1165class IpsecTun6Tests(IpsecTun6):
Neale Ranns4f33c802019-04-10 12:39:10 +00001166 """ UT test methods for Tunnel v6 """
Neale Ranns2ac885c2019-03-20 18:24:43 +00001167
1168 def test_tun_basic66(self):
1169 """ ipsec 6o6 tunnel basic test """
1170 self.verify_tun_66(self.params[socket.AF_INET6], count=1)
1171
Neale Ranns14046982019-07-29 14:49:52 +00001172 def test_tun_reass_basic66(self):
1173 """ ipsec 6o6 tunnel basic reassembly test """
1174 self.verify_tun_reass_66(self.params[socket.AF_INET6])
1175
Klement Sekera611864f2018-09-26 11:19:00 +02001176 def test_tun_burst66(self):
1177 """ ipsec 6o6 tunnel burst test """
Neale Ranns2ac885c2019-03-20 18:24:43 +00001178 self.verify_tun_66(self.params[socket.AF_INET6], count=257)
Klement Sekera611864f2018-09-26 11:19:00 +02001179
1180
Neale Ranns4a56f4e2019-12-23 04:10:25 +00001181class IpsecTun6HandoffTests(IpsecTun6):
1182 """ UT test methods for Tunnel v6 with multiple workers """
1183 worker_config = "workers 2"
1184
1185 def test_tun_handoff_66(self):
1186 """ ipsec 6o6 tunnel worker hand-off test """
1187 N_PKTS = 15
1188 p = self.params[socket.AF_INET6]
1189
1190 # inject alternately on worker 0 and 1. all counts on the SA
1191 # should be against worker 0
1192 for worker in [0, 1, 0, 1]:
Neale Ranns28287212019-12-16 00:53:11 +00001193 send_pkts = self.gen_encrypt_pkts6(p, p.scapy_tun_sa, self.tun_if,
Neale Ranns4a56f4e2019-12-23 04:10:25 +00001194 src=p.remote_tun_if_host,
1195 dst=self.pg1.remote_ip6,
1196 count=N_PKTS)
1197 recv_pkts = self.send_and_expect(self.tun_if, send_pkts,
1198 self.pg1, worker=worker)
1199 self.verify_decrypted6(p, recv_pkts)
1200
1201 send_pkts = self.gen_pkts6(self.pg1, src=self.pg1.remote_ip6,
1202 dst=p.remote_tun_if_host,
1203 count=N_PKTS)
1204 recv_pkts = self.send_and_expect(self.pg1, send_pkts,
1205 self.tun_if, worker=worker)
1206 self.verify_encrypted6(p, p.vpp_tun_sa, recv_pkts)
1207
1208 # all counts against the first worker that was used
1209 self.verify_counters6(p, p, 4*N_PKTS, worker=0)
1210
1211
1212class IpsecTun4HandoffTests(IpsecTun4):
1213 """ UT test methods for Tunnel v4 with multiple workers """
1214 worker_config = "workers 2"
1215
1216 def test_tun_handooff_44(self):
1217 """ ipsec 4o4 tunnel worker hand-off test """
1218 N_PKTS = 15
1219 p = self.params[socket.AF_INET]
1220
1221 # inject alternately on worker 0 and 1. all counts on the SA
1222 # should be against worker 0
1223 for worker in [0, 1, 0, 1]:
Neale Ranns28287212019-12-16 00:53:11 +00001224 send_pkts = self.gen_encrypt_pkts(p, p.scapy_tun_sa, self.tun_if,
Neale Ranns4a56f4e2019-12-23 04:10:25 +00001225 src=p.remote_tun_if_host,
1226 dst=self.pg1.remote_ip4,
1227 count=N_PKTS)
1228 recv_pkts = self.send_and_expect(self.tun_if, send_pkts,
1229 self.pg1, worker=worker)
1230 self.verify_decrypted(p, recv_pkts)
1231
1232 send_pkts = self.gen_pkts(self.pg1, src=self.pg1.remote_ip4,
1233 dst=p.remote_tun_if_host,
1234 count=N_PKTS)
1235 recv_pkts = self.send_and_expect(self.pg1, send_pkts,
1236 self.tun_if, worker=worker)
1237 self.verify_encrypted(p, p.vpp_tun_sa, recv_pkts)
1238
1239 # all counts against the first worker that was used
1240 self.verify_counters4(p, 4*N_PKTS, worker=0)
1241
1242
Neale Ranns53f526b2019-02-25 14:32:02 +00001243class IpsecTun46Tests(IpsecTun4Tests, IpsecTun6Tests):
Neale Ranns4f33c802019-04-10 12:39:10 +00001244 """ UT test methods for Tunnel v6 & v4 """
Klement Sekera611864f2018-09-26 11:19:00 +02001245 pass
1246
Klement Sekera31da2e32018-06-24 22:49:55 +02001247
1248if __name__ == '__main__':
1249 unittest.main(testRunner=VppTestRunner)