Merge "Install dependencies: bare-metal, standalone"
[yardstick.git] / yardstick / tests / unit / network_services / vnf_generic / vnf / test_cgnapt_vnf.py
1 # Copyright (c) 2016-2017 Intel Corporation
2 #
3 # Licensed under the Apache License, Version 2.0 (the "License");
4 # you may not use this file except in compliance with the License.
5 # You may obtain a copy of the License at
6 #
7 #      http://www.apache.org/licenses/LICENSE-2.0
8 #
9 # Unless required by applicable law or agreed to in writing, software
10 # distributed under the License is distributed on an "AS IS" BASIS,
11 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 # See the License for the specific language governing permissions and
13 # limitations under the License.
14 #
15
16 from copy import deepcopy
17 import os
18
19 import mock
20 import unittest
21
22
23 from yardstick.common import utils
24
25 from yardstick.tests.unit.network_services.vnf_generic.vnf.test_base import mock_ssh
26
27
28
29 from yardstick.network_services.vnf_generic.vnf.cgnapt_vnf import CgnaptApproxVnf, \
30     CgnaptApproxSetupEnvHelper
31 from yardstick.network_services.vnf_generic.vnf import cgnapt_vnf
32 from yardstick.network_services.nfvi.resource import ResourceProfile
33
34 TEST_FILE_YAML = 'nsb_test_case.yaml'
35 SSH_HELPER = 'yardstick.network_services.vnf_generic.vnf.sample_vnf.VnfSshHelper'
36
37
38 name = 'vnf__0'
39
40
41 class TestCgnaptApproxSetupEnvHelper(unittest.TestCase):
42
43     def test__generate_ip_from_pool(self):
44
45         ip = CgnaptApproxSetupEnvHelper._generate_ip_from_pool("1.2.3.4")
46         self.assertEqual(next(ip), '1.2.3.4')
47         self.assertEqual(next(ip), '1.2.4.4')
48         self.assertEqual(next(ip), '1.2.5.4')
49
50     def test__update_cgnat_script_file(self):
51
52         sample = """\
53 # See the License for the specific language governing permissions and
54 # limitations under the License.
55
56 link 0 down
57 link 0 config {port0_local_ip} {port0_prefixlen}
58 link 0 up
59 link 1 down
60 link 1 config {port1_local_ip} {port1_prefixlen}
61 link 1 up
62 """
63         header = "This is a header"
64
65         out = CgnaptApproxSetupEnvHelper._update_cgnat_script_file(header, sample.splitlines())
66         self.assertNotIn("This is a header", out)
67
68     def test__get_cgnapt_config(self):
69         vnfd_helper = mock.MagicMock()
70         vnfd_helper.port_pairs.uplink_ports = [{"name": 'a'}, {"name": "b"}, {"name": "c"}]
71
72         helper = CgnaptApproxSetupEnvHelper(vnfd_helper, mock.Mock(), mock.Mock())
73         result = helper._get_cgnapt_config()
74         self.assertIsNotNone(result)
75
76     def test_scale(self):
77         helper = CgnaptApproxSetupEnvHelper(mock.Mock(), mock.Mock(), mock.Mock())
78         with self.assertRaises(NotImplementedError):
79             helper.scale()
80
81     @mock.patch('yardstick.network_services.vnf_generic.vnf.sample_vnf.open')
82     @mock.patch.object(utils, 'find_relative_file')
83     @mock.patch('yardstick.network_services.vnf_generic.vnf.sample_vnf.MultiPortConfig')
84     @mock.patch.object(utils, 'open_relative_file')
85     def test_build_config(self, *args):
86         vnfd_helper = mock.Mock()
87         ssh_helper = mock.Mock()
88         scenario_helper = mock.Mock()
89         scenario_helper.vnf_cfg = {'lb_config': 'HW'}
90         scenario_helper.all_options = {}
91
92         cgnat_approx_setup_helper = CgnaptApproxSetupEnvHelper(vnfd_helper,
93                                                                ssh_helper,
94                                                                scenario_helper)
95
96         cgnat_approx_setup_helper.ssh_helper.provision_tool = mock.Mock(return_value='tool_path')
97         cgnat_approx_setup_helper.ssh_helper.all_ports = mock.Mock()
98         cgnat_approx_setup_helper.vnfd_helper.port_nums = mock.Mock(return_value=[0, 1])
99         expected = 'sudo tool_path -p 0x3 -f /tmp/cgnapt_config -s /tmp/cgnapt_script  --hwlb 3'
100         self.assertEqual(cgnat_approx_setup_helper.build_config(), expected)
101
102
103 @mock.patch("yardstick.network_services.vnf_generic.vnf.sample_vnf.Process")
104 class TestCgnaptApproxVnf(unittest.TestCase):
105     VNFD = {'vnfd:vnfd-catalog':
106             {'vnfd':
107              [{'short-name': 'VpeVnf',
108                'vdu':
109                [{'routing_table':
110                  [{'network': '152.16.100.20',
111                    'netmask': '255.255.255.0',
112                    'gateway': '152.16.100.20',
113                    'if': 'xe0'},
114                   {'network': '152.16.40.20',
115                    'netmask': '255.255.255.0',
116                    'gateway': '152.16.40.20',
117                    'if': 'xe1'}],
118                  'description': 'VPE approximation using DPDK',
119                  'name': 'vpevnf-baremetal',
120                  'nd_route_tbl':
121                  [{'network': '0064:ff9b:0:0:0:0:9810:6414',
122                    'netmask': '112',
123                    'gateway': '0064:ff9b:0:0:0:0:9810:6414',
124                    'if': 'xe0'},
125                   {'network': '0064:ff9b:0:0:0:0:9810:2814',
126                    'netmask': '112',
127                    'gateway': '0064:ff9b:0:0:0:0:9810:2814',
128                    'if': 'xe1'}],
129                  'id': 'vpevnf-baremetal',
130                  'external-interface':
131                  [{'virtual-interface':
132                    {'dst_mac': '00:00:00:00:00:04',
133                     'vpci': '0000:05:00.0',
134                     'local_ip': '152.16.100.19',
135                     'type': 'PCI-PASSTHROUGH',
136                     'netmask': '255.255.255.0',
137                     'dpdk_port_num': 0,
138                     'bandwidth': '10 Gbps',
139                     'driver': "i40e",
140                     'dst_ip': '152.16.100.20',
141                     'local_iface_name': 'xe0',
142                     'local_mac': '00:00:00:00:00:02'},
143                    'vnfd-connection-point-ref': 'xe0',
144                    'name': 'xe0'},
145                   {'virtual-interface':
146                    {'dst_mac': '00:00:00:00:00:03',
147                     'vpci': '0000:05:00.1',
148                     'local_ip': '152.16.40.19',
149                     'type': 'PCI-PASSTHROUGH',
150                     'driver': "i40e",
151                     'netmask': '255.255.255.0',
152                     'dpdk_port_num': 1,
153                     'bandwidth': '10 Gbps',
154                     'dst_ip': '152.16.40.20',
155                     'local_iface_name': 'xe1',
156                     'local_mac': '00:00:00:00:00:01'},
157                    'vnfd-connection-point-ref': 'xe1',
158                    'name': 'xe1'}]}],
159                'description': 'Vpe approximation using DPDK',
160                'mgmt-interface':
161                    {'vdu-id': 'vpevnf-baremetal',
162                     'host': '1.2.1.1',
163                     'password': 'r00t',
164                     'user': 'root',
165                     'ip': '1.2.1.1'},
166                'benchmark':
167                    {'kpi': ['packets_in', 'packets_fwd', 'packets_dropped']},
168                'connection-point': [{'type': 'VPORT', 'name': 'xe0'},
169                                     {'type': 'VPORT', 'name': 'xe1'}],
170                'id': 'CgnaptApproxVnf', 'name': 'VPEVnfSsh'}]}}
171
172     SCENARIO_CFG = {
173         'options': {
174             'packetsize': 64,
175             'traffic_type': 4,
176             'rfc2544': {
177                 'allowed_drop_rate': '0.8 - 1',
178             },
179             'vnf__0': {
180                 'napt': 'dynamic',
181                 'vnf_config': {
182                     'lb_config': 'SW',
183                     'lb_count': 1,
184                     'worker_config':
185                     '1C/1T',
186                     'worker_threads': 1,
187                 },
188             },
189             'flow': {'count': 1,
190                      'dst_ip': [{'tg__1': 'xe0'}],
191                      'public_ip': [''],
192                      'src_ip': [{'tg__0': 'xe0'}]},
193         },
194         'task_id': 'a70bdf4a-8e67-47a3-9dc1-273c14506eb7',
195         'task_path': '/tmp',
196         'tc': 'tc_ipv4_1Mflow_64B_packetsize',
197         'runner': {
198             'object': 'NetworkServiceTestCase',
199             'interval': 35,
200             'output_filename': '/tmp/yardstick.out',
201             'runner_id': 74476,
202             'duration': 400,
203             'type': 'Duration',
204         },
205         'traffic_profile': 'ipv4_throughput_acl.yaml',
206         'type': 'NSPerf',
207         'nodes': {
208             'tg__1': 'trafficgen_1.yardstick',
209             'tg__0': 'trafficgen_0.yardstick',
210             'vnf__0': 'vnf.yardstick',
211         },
212         'topology': 'vpe-tg-topology-baremetal.yaml',
213     }
214
215     context_cfg = {'nodes': {'tg__2':
216                              {'member-vnf-index': '3',
217                               'role': 'TrafficGen',
218                               'name': 'trafficgen_2.yardstick',
219                               'vnfd-id-ref': 'tg__2',
220                               'ip': '1.2.1.1',
221                               'interfaces':
222                               {'xe0': {'local_iface_name': 'ens513f0',
223                                        'vld_id': CgnaptApproxVnf.DOWNLINK,
224                                        'netmask': '255.255.255.0',
225                                        'local_ip': '152.16.40.20',
226                                        'dst_mac': '00:00:00:00:00:01',
227                                        'local_mac': '00:00:00:00:00:03',
228                                        'dst_ip': '152.16.40.19',
229                                        'driver': 'ixgbe',
230                                        'vpci': '0000:02:00.0',
231                                        'dpdk_port_num': 0},
232                                'xe1': {'local_iface_name': 'ens513f1',
233                                        'netmask': '255.255.255.0',
234                                        'network': '202.16.100.0',
235                                        'local_ip': '202.16.100.20',
236                                        'local_mac': '00:1e:67:d0:60:5d',
237                                        'driver': 'ixgbe',
238                                        'vpci': '0000:02:00.1',
239                                        'dpdk_port_num': 1}},
240                               'password': 'r00t',
241                               'VNF model': 'l3fwd_vnf.yaml',
242                               'user': 'root'},
243                              'tg__1':
244                              {'member-vnf-index': '1',
245                               'role': 'TrafficGen',
246                               'name': 'trafficgen_1.yardstick',
247                               'vnfd-id-ref': 'tg__1',
248                               'ip': '1.2.1.1',
249                               'interfaces':
250                               {'xe0': {'local_iface_name': 'ens785f0',
251                                        'vld_id': CgnaptApproxVnf.UPLINK,
252                                        'netmask': '255.255.255.0',
253                                        'local_ip': '152.16.100.20',
254                                        'dst_mac': '00:00:00:00:00:02',
255                                        'local_mac': '00:00:00:00:00:04',
256                                        'dst_ip': '152.16.100.19',
257                                        'driver': 'i40e',
258                                        'vpci': '0000:05:00.0',
259                                        'dpdk_port_num': 0},
260                                'xe1': {'local_iface_name': 'ens785f1',
261                                        'netmask': '255.255.255.0',
262                                        'local_ip': '152.16.100.21',
263                                        'local_mac': '00:00:00:00:00:01',
264                                        'driver': 'i40e',
265                                        'vpci': '0000:05:00.1',
266                                        'dpdk_port_num': 1}},
267                               'password': 'r00t',
268                               'VNF model': 'tg_rfc2544_tpl.yaml',
269                               'user': 'root'},
270                              'vnf__0':
271                              {'name': 'vnf.yardstick',
272                               'vnfd-id-ref': 'vnf__0',
273                               'ip': '1.2.1.1',
274                               'interfaces':
275                               {'xe0': {'local_iface_name': 'ens786f0',
276                                        'vld_id': CgnaptApproxVnf.UPLINK,
277                                        'netmask': '255.255.255.0',
278                                        'local_ip': '152.16.100.19',
279                                        'dst_mac': '00:00:00:00:00:04',
280                                        'local_mac': '00:00:00:00:00:02',
281                                        'dst_ip': '152.16.100.20',
282                                        'driver': 'i40e',
283                                        'vpci': '0000:05:00.0',
284                                        'dpdk_port_num': 0},
285                                'xe1': {'local_iface_name': 'ens786f1',
286                                        'vld_id': CgnaptApproxVnf.DOWNLINK,
287                                        'netmask': '255.255.255.0',
288                                        'local_ip': '152.16.40.19',
289                                        'dst_mac': '00:00:00:00:00:03',
290                                        'local_mac': '00:00:00:00:00:01',
291                                        'dst_ip': '152.16.40.20',
292                                        'driver': 'i40e',
293                                        'vpci': '0000:05:00.1',
294                                        'dpdk_port_num': 1}},
295                               'routing_table':
296                               [{'netmask': '255.255.255.0',
297                                 'gateway': '152.16.100.20',
298                                 'network': '152.16.100.20',
299                                 'if': 'xe0'},
300                                {'netmask': '255.255.255.0',
301                                 'gateway': '152.16.40.20',
302                                 'network': '152.16.40.20',
303                                 'if': 'xe1'}],
304                               'member-vnf-index': '2',
305                               'host': '1.2.1.1',
306                               'role': 'vnf',
307                               'user': 'root',
308                               'nd_route_tbl':
309                               [{'netmask': '112',
310                                 'gateway': '0064:ff9b:0:0:0:0:9810:6414',
311                                 'network': '0064:ff9b:0:0:0:0:9810:6414',
312                                 'if': 'xe0'},
313                                {'netmask': '112',
314                                 'gateway': '0064:ff9b:0:0:0:0:9810:2814',
315                                 'network': '0064:ff9b:0:0:0:0:9810:2814',
316                                 'if': 'xe1'}],
317                               'password': 'r00t',
318                               'VNF model': 'cgnapt_vnf.yaml'}}}
319
320     def setUp(self):
321         self.scenario_cfg = deepcopy(self.SCENARIO_CFG)
322
323     def test___init__(self, *args):
324         vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
325         cgnapt_approx_vnf = CgnaptApproxVnf(name, vnfd)
326         self.assertIsNone(cgnapt_approx_vnf._vnf_process)
327
328     @mock.patch('yardstick.network_services.vnf_generic.vnf.sample_vnf.time')
329     @mock.patch(SSH_HELPER)
330     def test_collect_kpi(self, ssh, *args):
331         mock_ssh(ssh)
332
333         vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
334         cgnapt_approx_vnf = CgnaptApproxVnf(name, vnfd)
335         cgnapt_approx_vnf._vnf_process = mock.MagicMock(
336             **{"is_alive.return_value": True, "exitcode": None})
337         cgnapt_approx_vnf.q_in = mock.MagicMock()
338         cgnapt_approx_vnf.q_out = mock.MagicMock()
339         cgnapt_approx_vnf.q_out.qsize = mock.Mock(return_value=0)
340         cgnapt_approx_vnf.resource = mock.Mock(autospec=ResourceProfile)
341         result = {'packets_dropped': 0, 'packets_fwd': 0, 'packets_in': 0}
342         self.assertEqual(result, cgnapt_approx_vnf.collect_kpi())
343
344     @mock.patch('yardstick.network_services.vnf_generic.vnf.sample_vnf.time')
345     @mock.patch(SSH_HELPER)
346     def test_vnf_execute_command(self, ssh, *args):
347         mock_ssh(ssh)
348
349         vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
350         cgnapt_approx_vnf = CgnaptApproxVnf(name, vnfd)
351         cgnapt_approx_vnf.q_in = mock.MagicMock()
352         cgnapt_approx_vnf.q_out = mock.MagicMock()
353         cgnapt_approx_vnf.q_out.qsize = mock.Mock(return_value=0)
354         cmd = "quit"
355         self.assertEqual("", cgnapt_approx_vnf.vnf_execute(cmd))
356
357     @mock.patch(SSH_HELPER)
358     def test_get_stats(self, ssh, *args):
359         mock_ssh(ssh)
360
361         vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
362         cgnapt_approx_vnf = CgnaptApproxVnf(name, vnfd)
363         cgnapt_approx_vnf.q_in = mock.MagicMock()
364         cgnapt_approx_vnf.q_out = mock.MagicMock()
365         cgnapt_approx_vnf.q_out.qsize = mock.Mock(return_value=0)
366         result = \
367             "CG-NAPT(.*\n)*Received 100, Missed 0, Dropped 0,Translated 100,ingress"
368         cgnapt_approx_vnf.vnf_execute = mock.Mock(return_value=result)
369         self.assertListEqual(list(result), list(cgnapt_approx_vnf.get_stats()))
370
371     def _get_file_abspath(self, filename):
372         curr_path = os.path.dirname(os.path.abspath(__file__))
373         file_path = os.path.join(curr_path, filename)
374         return file_path
375
376     @mock.patch("yardstick.network_services.vnf_generic.vnf.cgnapt_vnf.hex")
377     @mock.patch("yardstick.network_services.vnf_generic.vnf.cgnapt_vnf.eval")
378     @mock.patch('yardstick.network_services.vnf_generic.vnf.cgnapt_vnf.open')
379     @mock.patch(SSH_HELPER)
380     def test_run_vcgnapt(self, ssh, *args):
381         mock_ssh(ssh)
382
383         vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
384         cgnapt_approx_vnf = CgnaptApproxVnf(name, vnfd)
385         cgnapt_approx_vnf._build_config = mock.MagicMock()
386         cgnapt_approx_vnf.queue_wrapper = mock.MagicMock()
387         cgnapt_approx_vnf.ssh_helper = mock.MagicMock()
388         cgnapt_approx_vnf.ssh_helper.run = mock.MagicMock()
389         cgnapt_approx_vnf.scenario_helper.scenario_cfg = self.scenario_cfg
390         cgnapt_approx_vnf._run()
391         cgnapt_approx_vnf.ssh_helper.run.assert_called_once()
392
393     @mock.patch("yardstick.network_services.vnf_generic.vnf.sample_vnf.Context")
394     @mock.patch(SSH_HELPER)
395     def test_instantiate(self, ssh, *args):
396         mock_ssh(ssh)
397
398         vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
399         cgnapt_approx_vnf = CgnaptApproxVnf(name, vnfd)
400         cgnapt_approx_vnf.deploy_helper = mock.MagicMock()
401         cgnapt_approx_vnf.resource_helper = mock.MagicMock()
402         cgnapt_approx_vnf._build_config = mock.MagicMock()
403         self.scenario_cfg['vnf_options'] = {'acl': {'cfg': "",
404                                                     'rules': ""}}
405         cgnapt_approx_vnf.q_out.put("pipeline>")
406         cgnapt_vnf.WAIT_TIME = 3
407         self.scenario_cfg.update({"nodes": {"vnf__0": ""}})
408         self.assertIsNone(cgnapt_approx_vnf.instantiate(self.scenario_cfg,
409                                                         self.context_cfg))
410
411     @mock.patch("yardstick.network_services.vnf_generic.vnf.sample_vnf.time")
412     @mock.patch(SSH_HELPER)
413     def test_terminate(self, ssh, *args):
414         mock_ssh(ssh)
415
416         vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
417         cgnapt_approx_vnf = CgnaptApproxVnf(name, vnfd)
418         cgnapt_approx_vnf._vnf_process = mock.MagicMock()
419         cgnapt_approx_vnf._vnf_process.terminate = mock.Mock()
420         cgnapt_approx_vnf.used_drivers = {"01:01.0": "i40e",
421                                           "01:01.1": "i40e"}
422         cgnapt_approx_vnf.vnf_execute = mock.MagicMock()
423         cgnapt_approx_vnf.dpdk_nic_bind = "dpdk_nic_bind.py"
424         cgnapt_approx_vnf._resource_collect_stop = mock.Mock()
425         self.assertIsNone(cgnapt_approx_vnf.terminate())
426
427     @mock.patch("yardstick.network_services.vnf_generic.vnf.sample_vnf.time")
428     @mock.patch(SSH_HELPER)
429     def test__vnf_up_post(self, ssh, *args):
430         mock_ssh(ssh)
431
432         vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
433         self.scenario_cfg['options'][name]['napt'] = 'static'
434
435         cgnapt_approx_vnf = CgnaptApproxVnf(name, vnfd)
436         cgnapt_approx_vnf._vnf_process = mock.MagicMock()
437         cgnapt_approx_vnf._vnf_process.terminate = mock.Mock()
438         cgnapt_approx_vnf.vnf_execute = mock.MagicMock()
439         cgnapt_approx_vnf.scenario_helper.scenario_cfg = self.scenario_cfg
440         cgnapt_approx_vnf._resource_collect_stop = mock.Mock()
441         cgnapt_approx_vnf._vnf_up_post()
442
443     @mock.patch("yardstick.network_services.vnf_generic.vnf.sample_vnf.time")
444     @mock.patch(SSH_HELPER)
445     def test__vnf_up_post_short(self, ssh, *args):
446         mock_ssh(ssh)
447
448         vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
449         cgnapt_approx_vnf = CgnaptApproxVnf(name, vnfd)
450         cgnapt_approx_vnf._vnf_process = mock.MagicMock()
451         cgnapt_approx_vnf._vnf_process.terminate = mock.Mock()
452         cgnapt_approx_vnf.vnf_execute = mock.MagicMock()
453         cgnapt_approx_vnf.scenario_helper.scenario_cfg = self.scenario_cfg
454         cgnapt_approx_vnf._resource_collect_stop = mock.Mock()
455         cgnapt_approx_vnf._vnf_up_post()