Move tests: unit/network_services/vnf_generic
[yardstick.git] / yardstick / tests / unit / network_services / vnf_generic / vnf / test_prox_helpers.py
1
2 # Copyright (c) 2016-2017 Intel Corporation
3 #
4 # Licensed under the Apache License, Version 2.0 (the "License");
5 # you may not use this file except in compliance with the License.
6 # You may obtain a copy of the License at
7 #
8 #      http://www.apache.org/licenses/LICENSE-2.0
9 #
10 # Unless required by applicable law or agreed to in writing, software
11 # distributed under the License is distributed on an "AS IS" BASIS,
12 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 # See the License for the specific language governing permissions and
14 # limitations under the License.
15 #
16
17 from itertools import repeat, chain
18 import os
19 import socket
20 import time
21
22 import mock
23 import unittest
24
25 from yardstick.tests import STL_MOCKS
26 from yardstick.common import utils
27 from yardstick.network_services.vnf_generic.vnf.base import VnfdHelper
28 from yardstick.network_services import constants
29
30 STLClient = mock.MagicMock()
31 stl_patch = mock.patch.dict("sys.modules", STL_MOCKS)
32 stl_patch.start()
33
34 if stl_patch:
35     from yardstick.network_services.vnf_generic.vnf.sample_vnf import ScenarioHelper
36     from yardstick.network_services.vnf_generic.vnf.prox_helpers import ProxSocketHelper
37     from yardstick.network_services.vnf_generic.vnf.prox_helpers import PacketDump
38     from yardstick.network_services.vnf_generic.vnf.prox_helpers import CoreSocketTuple
39     from yardstick.network_services.vnf_generic.vnf.prox_helpers import ProxTestDataTuple
40     from yardstick.network_services.vnf_generic.vnf.prox_helpers import ProxDpdkVnfSetupEnvHelper
41     from yardstick.network_services.vnf_generic.vnf.prox_helpers import TotStatsTuple
42     from yardstick.network_services.vnf_generic.vnf.prox_helpers import ProxDataHelper
43     from yardstick.network_services.vnf_generic.vnf.prox_helpers import ProxResourceHelper
44     from yardstick.network_services.vnf_generic.vnf.prox_helpers import ProxProfileHelper
45     from yardstick.network_services.vnf_generic.vnf.prox_helpers import ProxMplsProfileHelper
46     from yardstick.network_services.vnf_generic.vnf.prox_helpers import ProxBngProfileHelper
47     from yardstick.network_services.vnf_generic.vnf.prox_helpers import ProxVpeProfileHelper
48     from yardstick.network_services.vnf_generic.vnf.prox_helpers import ProxlwAFTRProfileHelper
49
50 class TestCoreTuple(unittest.TestCase):
51     def test___init__(self):
52         core_tuple = CoreSocketTuple('core 5s6')
53         self.assertEqual(core_tuple.core_id, 5)
54         self.assertEqual(core_tuple.socket_id, 6)
55         self.assertFalse(core_tuple.is_hyperthread())
56
57         core_tuple = CoreSocketTuple('core 5s6h')
58         self.assertEqual(core_tuple.core_id, 5)
59         self.assertEqual(core_tuple.socket_id, 6)
60         self.assertTrue(core_tuple.is_hyperthread())
61
62     def test___init__negative(self):
63         bad_inputs = [
64             '',
65             '5',
66             '5s',
67             '6h',
68             '5s6',
69             'core',
70             'core h',
71             'core 5s',
72             'core 5 6',
73             'core 5 6h',
74             'core 5d6',
75             'core 5d6h',
76             1,
77             2.3,
78             [],
79             {},
80             object(),
81         ]
82
83         for bad_input in bad_inputs:
84             with self.assertRaises(ValueError):
85                 CoreSocketTuple(bad_input)
86
87     def test_find_in_topology(self):
88         topology_in = {
89             6: {
90                 5: {
91                     'key1': ['a', 'b'],
92                     'key2': ['c', 'd'],
93                 },
94             },
95         }
96
97         core_tuple = CoreSocketTuple('core 5s6')
98
99         expected = 'a'
100         result = core_tuple.find_in_topology(topology_in)
101         self.assertEqual(result, expected)
102
103         core_tuple = CoreSocketTuple('core 5s6h')
104
105         expected = 'c'
106         result = core_tuple.find_in_topology(topology_in)
107         self.assertEqual(result, expected)
108
109     def test_find_in_topology_negative(self):
110         core_tuple = CoreSocketTuple('core 6s5')
111         with self.assertRaises(ValueError):
112             # no socket key
113             core_tuple.find_in_topology({})
114
115         with self.assertRaises(ValueError):
116             # no core key
117             core_tuple.find_in_topology({5: {}})
118
119         with self.assertRaises(ValueError):
120             # no first value (as needed by non-hyperthread core)
121             core_tuple.find_in_topology({5: {6: {'key1': []}}})
122
123         core_tuple = CoreSocketTuple('core 6s5h')
124         with self.assertRaises(ValueError):
125             # no second value (as needed by hyperthread core)
126             core_tuple.find_in_topology({5: {6: {'key1': ['e']}}})
127
128
129 class TestTotStatsTuple(unittest.TestCase):
130     def test___new___negative(self):
131         with self.assertRaises(TypeError):
132             # no values
133             TotStatsTuple()
134
135         with self.assertRaises(TypeError):
136             # one, non-integer value
137             TotStatsTuple('a')
138
139         with self.assertRaises(TypeError):
140             # too many values
141             TotStatsTuple(3, 4, 5, 6, 7)
142
143
144 class TestProxTestDataTuple(unittest.TestCase):
145     def test___init__(self):
146         prox_test_data = ProxTestDataTuple(1, 2, 3, 4, 5, 6, 7, 8, 9)
147         self.assertEqual(prox_test_data.tolerated, 1)
148         self.assertEqual(prox_test_data.tsc_hz, 2)
149         self.assertEqual(prox_test_data.delta_rx, 3)
150         self.assertEqual(prox_test_data.delta_tx, 4)
151         self.assertEqual(prox_test_data.delta_tsc, 5)
152         self.assertEqual(prox_test_data.latency, 6)
153         self.assertEqual(prox_test_data.rx_total, 7)
154         self.assertEqual(prox_test_data.tx_total, 8)
155         self.assertEqual(prox_test_data.requested_pps, 9)
156
157     def test_properties(self):
158         prox_test_data = ProxTestDataTuple(1, 2, 3, 4, 5, 6, 7, 8, 9)
159         self.assertEqual(prox_test_data.pkt_loss, 12.5)
160         self.assertEqual(prox_test_data.tx_mpps, 1.6 / 1e6)
161         self.assertEqual(prox_test_data.can_be_lost, 0)
162         self.assertEqual(prox_test_data.drop_total, 1)
163         self.assertFalse(prox_test_data.success)
164
165         prox_test_data = ProxTestDataTuple(10, 2, 3, 4, 5, 6, 997, 998, 9)
166         self.assertTrue(prox_test_data.success)
167
168     def test_pkt_loss_zero_division(self):
169         prox_test_data = ProxTestDataTuple(1, 2, 3, 4, 5, 6, 7, 0, 9)
170         self.assertEqual(prox_test_data.pkt_loss, 100.0)
171
172     def test_get_samples(self):
173         prox_test_data = ProxTestDataTuple(1, 2, 3, 4, 5, [6.1, 6.9, 6.4], 7, 8, 9)
174
175         expected = {
176             "Throughput": 1.2 / 1e6,
177             "DropPackets": 12.5,
178             "CurrentDropPackets": 12.5,
179             "RequestedTxThroughput": 9 / 1e6,
180             "TxThroughput": 1.6 / 1e6,
181             "RxThroughput": 1.2 / 1e6,
182             "PktSize": 64,
183             "PortSample": 1,
184             "LatencyMin": 6.1,
185             "LatencyMax": 6.9,
186             "LatencyAvg": 6.4,
187         }
188         result = prox_test_data.get_samples(64, port_samples={"PortSample": 1})
189         self.assertDictEqual(result, expected)
190
191         expected = {
192             "Throughput": 1.2 / 1e6,
193             "DropPackets": 0.123,
194             "CurrentDropPackets": 0.123,
195             "RequestedTxThroughput": 9 / 1e6,
196             "TxThroughput": 1.6 / 1e6,
197             "RxThroughput": 1.2 / 1e6,
198             "PktSize": 64,
199             "LatencyMin": 6.1,
200             "LatencyMax": 6.9,
201             "LatencyAvg": 6.4,
202         }
203         result = prox_test_data.get_samples(64, 0.123)
204         self.assertDictEqual(result, expected)
205
206     @mock.patch('yardstick.LOG_RESULT', create=True)
207     def test_log_data(self, mock_logger):
208         my_mock_logger = mock.MagicMock()
209         prox_test_data = ProxTestDataTuple(1, 2, 3, 4, 5, [6.1, 6.9, 6.4], 7, 8, 9)
210         prox_test_data.log_data()
211         self.assertEqual(my_mock_logger.debug.call_count, 0)
212         self.assertEqual(mock_logger.debug.call_count, 0)
213
214         mock_logger.debug.reset_mock()
215         prox_test_data.log_data(my_mock_logger)
216         self.assertEqual(my_mock_logger.debug.call_count, 0)
217         self.assertEqual(mock_logger.debug.call_count, 0)
218
219
220 class TestPacketDump(unittest.TestCase):
221     PAYLOAD = "payload"
222
223     def test__init__(self):
224         PacketDump("port_id", len(self.PAYLOAD), self.PAYLOAD)
225
226     def test___str__(self):
227         expected = '<PacketDump port: port_id payload: {}>'.format(self.PAYLOAD)
228         dump1 = PacketDump("port_id", len(self.PAYLOAD), self.PAYLOAD)
229         self.assertEqual(str(dump1), expected)
230
231     def test_port_id(self):
232         p = PacketDump("port_id", len(self.PAYLOAD), self.PAYLOAD)
233         self.assertEqual(p.port_id, "port_id")
234
235     def test_data_len(self):
236         p = PacketDump("port_id", len(self.PAYLOAD), self.PAYLOAD)
237         self.assertEqual(p.data_len, len(self.PAYLOAD))
238
239     def test_payload(self):
240         p = PacketDump("port_id", len(self.PAYLOAD), self.PAYLOAD)
241         self.assertEqual(p.payload(), self.PAYLOAD)
242
243         self.assertEqual(p.payload(3), self.PAYLOAD[3:])
244
245         self.assertEqual(p.payload(end=3), self.PAYLOAD[:4])
246
247         self.assertEqual(p.payload(2, 4), self.PAYLOAD[2:5])
248
249
250 PACKET_DUMP_1 = """\
251 pktdump,3,11
252 hello world
253 """
254
255 PACKET_DUMP_2 = """\
256 pktdump,3,11
257 hello world
258 pktdump,2,9
259 brown fox jumped over
260 pktdump,4,8
261 lazy
262 dog
263 """
264
265 PACKET_DUMP_NON_1 = """\
266 not_a_dump,1,2
267 other data
268 """
269
270 PACKET_DUMP_MIXED_1 = """\
271 pktdump,3,11
272 hello world
273 not_a_dump,1,2
274 other data
275 """
276
277 PACKET_DUMP_BAD_1 = """\
278 pktdump,one,12
279 bad port id
280 """
281
282 PACKET_DUMP_BAD_2 = """\
283 pktdump,3,twelve
284 bad data length
285 """
286
287 PACKET_DUMP_BAD_3 = """\
288 pktdump,3
289 no data length value
290 """
291
292
293 class TestProxSocketHelper(unittest.TestCase):
294
295     def setUp(self):
296         self.mock_time_sleep = mock.patch.object(time, 'sleep').start()
297
298     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.socket')
299     def test___init__(self, mock_socket):
300         expected = mock_socket.socket()
301         prox = ProxSocketHelper()
302         result = prox._sock
303         self.assertEqual(result, expected)
304
305     def test_connect(self):
306         mock_sock = mock.MagicMock()
307         prox = ProxSocketHelper(mock_sock)
308         prox.connect('10.20.30.40', 23456)
309         self.assertEqual(mock_sock.connect.call_count, 1)
310
311     def test_get_sock(self):
312         mock_sock = mock.MagicMock()
313         prox = ProxSocketHelper(mock_sock)
314         result = prox.get_socket()
315         self.assertIs(result, mock_sock)
316
317     # TODO(elfoley): Split this into three tests
318     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.select')
319     def test_get_data(self, mock_select):
320         mock_select.select.side_effect = [[1], [0]]
321         mock_socket = mock.MagicMock()
322         mock_recv = mock_socket.recv()
323         mock_recv.decode.return_value = ""
324         prox = ProxSocketHelper(mock_socket)
325         ret = prox.get_data()
326         self.assertEqual(ret, "")
327         self.assertEqual(len(prox._pkt_dumps), 0)
328
329         mock_select.select.reset_mock()
330         mock_select.select.side_effect = chain([['a'], ['']], repeat([1], 3))
331         mock_recv.decode.return_value = PACKET_DUMP_1
332         ret = prox.get_data()
333         self.assertEqual(mock_select.select.call_count, 2)
334         self.assertEqual(ret, 'pktdump,3,11')
335         self.assertEqual(len(prox._pkt_dumps), 1)
336
337         mock_select.select.reset_mock()
338         mock_select.select.side_effect = chain([[object()], [None]], repeat([1], 3))
339         mock_recv.decode.return_value = PACKET_DUMP_2
340         ret = prox.get_data()
341         self.assertEqual(mock_select.select.call_count, 1)
342         self.assertEqual(ret, 'jumped over')
343         self.assertEqual(len(prox._pkt_dumps), 3)
344
345     def test__parse_socket_data_mixed_data(self):
346         prox = ProxSocketHelper(mock.MagicMock())
347         ret, _ = prox._parse_socket_data(PACKET_DUMP_NON_1, False)
348         self.assertEqual(ret, 'not_a_dump,1,2')
349         self.assertEqual(len(prox._pkt_dumps), 0)
350
351         ret, _ = prox._parse_socket_data(PACKET_DUMP_MIXED_1, False)
352         self.assertEqual(ret, 'not_a_dump,1,2')
353         self.assertEqual(len(prox._pkt_dumps), 1)
354
355     def test__parse_socket_data_bad_data(self):
356         prox = ProxSocketHelper(mock.MagicMock())
357         with self.assertRaises(ValueError):
358             prox._parse_socket_data(PACKET_DUMP_BAD_1, False)
359
360         with self.assertRaises(ValueError):
361             prox._parse_socket_data(PACKET_DUMP_BAD_2, False)
362
363         ret, _ = prox._parse_socket_data(PACKET_DUMP_BAD_3, False)
364         self.assertEqual(ret, 'pktdump,3')
365
366     def test__parse_socket_data_pkt_dump_only(self):
367         prox = ProxSocketHelper(mock.MagicMock())
368         ret, _ = prox._parse_socket_data('', True)
369         self.assertFalse(ret)
370
371         ret, _ = prox._parse_socket_data(PACKET_DUMP_1, True)
372         self.assertTrue(ret)
373
374         ret, _ = prox._parse_socket_data(PACKET_DUMP_2, True)
375         self.assertTrue(ret)
376
377     def test_put_command(self):
378         mock_socket = mock.MagicMock()
379         prox = ProxSocketHelper(mock_socket)
380         prox.put_command("data")
381         mock_socket.sendall.assert_called_once()
382
383     def test_put_command_socket_error(self):
384         mock_socket = mock.MagicMock()
385         mock_socket.sendall.side_effect = OSError
386         prox = ProxSocketHelper(mock_socket)
387         prox.put_command("data")
388         mock_socket.sendall.assert_called_once()
389
390     def test_get_packet_dump(self):
391         mock_socket = mock.MagicMock()
392         prox = ProxSocketHelper(mock_socket)
393         prox._pkt_dumps = []
394         self.assertIsNone(prox.get_packet_dump())
395
396         prox._pkt_dumps = [234]
397         self.assertEqual(prox.get_packet_dump(), 234)
398         self.assertEqual(prox._pkt_dumps, [])
399
400     def test_stop_all_reset(self):
401         mock_socket = mock.MagicMock()
402         prox = ProxSocketHelper(mock_socket)
403         prox.stop_all_reset()
404         mock_socket.sendall.assert_called()
405
406     def test_stop_all(self):
407         mock_socket = mock.MagicMock()
408         prox = ProxSocketHelper(mock_socket)
409         prox.stop_all()
410         mock_socket.sendall.assert_called()
411
412     def test_stop(self):
413         mock_socket = mock.MagicMock()
414         prox = ProxSocketHelper(mock_socket)
415         prox.stop([3, 4, 5], 16)
416         mock_socket.sendall.assert_called()
417
418     def test_start_all(self):
419         mock_socket = mock.MagicMock()
420         prox = ProxSocketHelper(mock_socket)
421         prox.start_all()
422         mock_socket.sendall.assert_called()
423
424     def test_start(self):
425         mock_socket = mock.MagicMock()
426         prox = ProxSocketHelper(mock_socket)
427         prox.start([3, 4, 5])
428         mock_socket.sendall.assert_called()
429
430     def test_reset_stats(self):
431         mock_socket = mock.MagicMock()
432         prox = ProxSocketHelper(mock_socket)
433         prox.reset_stats()
434         mock_socket.sendall.assert_called()
435
436     def test_set_pkt_size(self):
437         mock_socket = mock.MagicMock()
438         prox = ProxSocketHelper(mock_socket)
439         prox.set_pkt_size([3, 4, 5], 1024)
440         self.assertEqual(mock_socket.sendall.call_count, 3)
441
442     def test_set_value(self):
443         mock_socket = mock.MagicMock()
444         prox = ProxSocketHelper(mock_socket)
445         prox.set_value([3, 4, 5], 10, 20, 30)
446         self.assertEqual(mock_socket.sendall.call_count, 3)
447
448     def test_reset_values(self):
449         mock_socket = mock.MagicMock()
450         prox = ProxSocketHelper(mock_socket)
451         prox.reset_values([3, 4, 5])
452         self.assertEqual(mock_socket.sendall.call_count, 3)
453
454     def test_set_speed(self):
455         mock_socket = mock.MagicMock()
456         prox = ProxSocketHelper(mock_socket)
457         prox.set_speed([3, 4, 5], 1000)
458         self.assertEqual(mock_socket.sendall.call_count, 3)
459
460     def test_slope_speed(self):
461         core_data = [
462             {
463                 'cores': [3, 4, 5],
464                 'speed': 1000,
465             },
466             {
467                 'cores': [9, 10, 11],
468                 'speed': '500.5',
469             },
470         ]
471
472         mock_socket = mock.MagicMock()
473         prox = ProxSocketHelper(mock_socket)
474         prox.set_speed = set_speed = mock.MagicMock()
475         prox.slope_speed(core_data, 5)
476         self.assertEqual(set_speed.call_count, 20)
477
478         set_speed.reset_mock()
479         prox.slope_speed(core_data, 5, 5)
480         self.assertEqual(set_speed.call_count, 10)
481
482     def test_set_pps(self):
483         mock_socket = mock.MagicMock()
484         prox = ProxSocketHelper(mock_socket)
485         prox.set_pps([3, 4, 5], 1000, 512)
486         self.assertEqual(mock_socket.sendall.call_count, 3)
487
488     def test_lat_stats(self):
489         latency_output = [
490             '1, 2 , 3',  # has white space
491             '4,5',  # too short
492             '7,8,9,10.5,11',  # too long with float, but float is in unused portion
493             'twelve,13,14',  # value as English word
494             '15,16.2,17',  # float in used portion
495         ]
496
497         mock_socket = mock.MagicMock()
498         prox = ProxSocketHelper(mock_socket)
499         prox.get_data = mock.MagicMock(side_effect=latency_output)
500
501         expected = (
502             {
503                 3: 1,
504                 5: 7,
505             },
506             {
507                 3: 2,
508                 5: 8,
509             },
510             {
511                 3: 3,
512                 5: 9,
513             },
514         )
515         result = prox.lat_stats([3, 4, 5, 6, 7], 16)
516         self.assertEqual(mock_socket.sendall.call_count, 5)
517         self.assertEqual(result, expected)
518
519     def test_get_all_tot_stats_error(self):
520         mock_socket = mock.MagicMock()
521         prox = ProxSocketHelper(mock_socket)
522         prox.get_data = mock.MagicMock(return_value='3,4,5')
523         expected = [0, 0, 0, 0]
524         result = prox.get_all_tot_stats()
525         self.assertEqual(result, expected)
526
527     def test_get_all_tot_stats(self):
528         mock_socket = mock.MagicMock()
529         prox = ProxSocketHelper(mock_socket)
530         prox.get_data = mock.MagicMock(return_value='3,4,5,6')
531         expected = 3, 4, 5, 6
532         result = prox.get_all_tot_stats()
533         self.assertEqual(result, expected)
534
535     def test_hz(self):
536         mock_socket = mock.MagicMock()
537         prox = ProxSocketHelper(mock_socket)
538         prox.get_data = mock.MagicMock(return_value='3,4,5,6')
539         expected = 6
540         result = prox.hz()
541         self.assertEqual(result, expected)
542
543     def test_core_stats(self):
544         core_stats = [
545             '3,4,5,6',
546             '7,8,9,10,NaN',
547             '11,12,13,14,15',
548         ]
549
550         mock_socket = mock.MagicMock()
551         prox = ProxSocketHelper(mock_socket)
552         prox.get_data = mock.MagicMock(side_effect=core_stats)
553         expected = 21, 24, 27, 14
554         result = prox.core_stats([3, 4, 5], 16)
555         self.assertEqual(result, expected)
556
557     def test_port_stats(self):
558         port_stats = [
559             ','.join(str(n) for n in range(3, 15)),
560             ','.join(str(n) for n in range(8, 32, 2)),
561             ','.join(str(n) for n in range(5, 89, 7)),
562         ]
563
564         mock_socket = mock.MagicMock()
565         prox = ProxSocketHelper(mock_socket)
566         prox.get_data = mock.MagicMock(side_effect=port_stats)
567         expected = [16, 26, 36, 46, 56, 66, 76, 86, 96, 106, 116, 126]
568         result = prox.port_stats([3, 4, 5])
569         self.assertEqual(result, expected)
570
571     def test_measure_tot_stats(self):
572         start_tot = 3, 4, 5, 6
573         end_tot = 7, 9, 11, 13
574         delta_tot = 4, 5, 6, 7
575
576         get_data_output = [
577             ','.join(str(n) for n in start_tot),
578             ','.join(str(n) for n in end_tot),
579         ]
580
581         mock_socket = mock.MagicMock()
582         prox = ProxSocketHelper(mock_socket)
583         prox.get_data = mock.MagicMock(side_effect=get_data_output)
584         expected = {
585             'start_tot': start_tot,
586             'end_tot': end_tot,
587             'delta': delta_tot,
588         }
589         with prox.measure_tot_stats() as result:
590             pass
591         self.assertEqual(result, expected)
592
593     def test_tot_stats(self):
594         mock_socket = mock.MagicMock()
595         prox = ProxSocketHelper(mock_socket)
596         prox.get_data = mock.MagicMock(return_value='3,4,5,6')
597         expected = 3, 4, 5
598         result = prox.tot_stats()
599         self.assertEqual(result, expected)
600
601     def test_tot_ierrors(self):
602         mock_socket = mock.MagicMock()
603         prox = ProxSocketHelper(mock_socket)
604         prox.get_data = mock.MagicMock(return_value='3,4,5,6')
605         expected = 3, 3
606         result = prox.tot_ierrors()
607         self.assertEqual(result, expected)
608
609     def test_set_count(self):
610         mock_socket = mock.MagicMock()
611         prox = ProxSocketHelper(mock_socket)
612         prox.set_count(432, [3, 4, 5])
613         self.assertEqual(mock_socket.sendall.call_count, 3)
614
615     def test_dump_rx(self):
616         mock_socket = mock.MagicMock()
617         prox = ProxSocketHelper(mock_socket)
618         prox.dump_rx(3, 5, 8)
619         self.assertEqual(mock_socket.sendall.call_count, 1)
620
621     def test_quit(self):
622         mock_socket = mock.MagicMock()
623         prox = ProxSocketHelper(mock_socket)
624         prox.quit()
625         mock_socket.sendall.assert_called()
626
627     def test_force_quit(self):
628         mock_socket = mock.MagicMock()
629         prox = ProxSocketHelper(mock_socket)
630         prox.force_quit()
631         mock_socket.sendall.assert_called()
632
633
634 class TestProxDpdkVnfSetupEnvHelper(unittest.TestCase):
635
636     VNFD0 = {
637         'short-name': 'ProxVnf',
638         'vdu': [
639             {
640                 'routing_table': [
641                     {
642                         'network': '152.16.100.20',
643                         'netmask': '255.255.255.0',
644                         'gateway': '152.16.100.20',
645                         'if': 'xe0',
646                     },
647                     {
648                         'network': '152.16.40.20',
649                         'netmask': '255.255.255.0',
650                         'gateway': '152.16.40.20',
651                         'if': 'xe1',
652                     },
653                 ],
654                 'description': 'PROX approximation using DPDK',
655                 'name': 'proxvnf-baremetal',
656                 'nd_route_tbl': [
657                     {
658                         'network': '0064:ff9b:0:0:0:0:9810:6414',
659                         'netmask': '112',
660                         'gateway': '0064:ff9b:0:0:0:0:9810:6414',
661                         'if': 'xe0',
662                     },
663                     {
664                         'network': '0064:ff9b:0:0:0:0:9810:2814',
665                         'netmask': '112',
666                         'gateway': '0064:ff9b:0:0:0:0:9810:2814',
667                         'if': 'xe1',
668                     },
669                 ],
670                 'id': 'proxvnf-baremetal',
671                 'external-interface': [
672                     {
673                         'virtual-interface': {
674                             'dst_mac': '00:00:00:00:00:04',
675                             'vpci': '0000:05:00.0',
676                             'local_ip': '152.16.100.19',
677                             'type': 'PCI-PASSTHROUGH',
678                             'vld_id': 'uplink_0',
679                             'netmask': '255.255.255.0',
680                             'dpdk_port_num': 0,
681                             'bandwidth': '10 Gbps',
682                             'driver': "i40e",
683                             'dst_ip': '152.16.100.19',
684                             'local_iface_name': 'xe0',
685                             'local_mac': '00:00:00:00:00:02',
686                             'ifname': 'xe0',
687                         },
688                         'vnfd-connection-point-ref': 'xe0',
689                         'name': 'xe0',
690                     },
691                     {
692                         'virtual-interface': {
693                             'dst_mac': '00:00:00:00:00:03',
694                             'vpci': '0000:05:00.1',
695                             'local_ip': '152.16.40.19',
696                             'type': 'PCI-PASSTHROUGH',
697                             'vld_id': 'downlink_0',
698                             'driver': "i40e",
699                             'netmask': '255.255.255.0',
700                             'dpdk_port_num': 1,
701                             'bandwidth': '10 Gbps',
702                             'dst_ip': '152.16.40.20',
703                             'local_iface_name': 'xe1',
704                             'local_mac': '00:00:00:00:00:01',
705                             'ifname': 'xe1',
706                         },
707                         'vnfd-connection-point-ref': 'xe1',
708                         'name': 'xe1',
709                     },
710                 ],
711             },
712         ],
713         'description': 'PROX approximation using DPDK',
714         'mgmt-interface': {
715             'vdu-id': 'proxvnf-baremetal',
716             'host': '1.2.1.1',
717             'password': 'r00t',
718             'user': 'root',
719             'ip': '1.2.1.1',
720         },
721         'benchmark': {
722             'kpi': [
723                 'packets_in',
724                 'packets_fwd',
725                 'packets_dropped',
726             ],
727         },
728         'id': 'ProxApproxVnf',
729         'name': 'ProxVnf',
730     }
731
732     VNFD = {
733         'vnfd:vnfd-catalog': {
734             'vnfd': [
735                 VNFD0,
736             ],
737         },
738     }
739
740     def test_global_section(self):
741         setup_helper = ProxDpdkVnfSetupEnvHelper(mock.MagicMock(), mock.MagicMock(),
742                                                  mock.MagicMock())
743
744         setup_helper._prox_config_data = [('a', [])]
745
746         with self.assertRaises(KeyError):
747             _ = setup_helper.global_section
748
749         global_section = (
750             'global', [
751                 ('not_name', 'other data'),
752                 ('name_not', 'more data'),
753                 ('name', 'prox type'),
754             ],
755         )
756
757         setup_helper._prox_config_data = [
758             ('section1', []),
759             ('section2', [
760                 ('a', 'b'),
761                 ('c', 'd'),
762             ]),
763             ('core 1', []),
764             ('core 2', [
765                 ('index', 8),
766                 ('mode', ''),
767             ]),
768             global_section,
769             ('core 3', [
770                 ('index', 5),
771                 ('mode', 'gen'),
772                 ('name', 'tagged'),
773             ]),
774             ('section3', [
775                 ('key1', 'value1'),
776                 ('key2', 'value2'),
777                 ('key3', 'value3'),
778             ]),
779             ('core 4', [
780                 ('index', 7),
781                 ('mode', 'gen'),
782                 ('name', 'udp'),
783             ]),
784         ]
785
786         result = setup_helper.global_section
787         self.assertEqual(result, global_section[1])
788
789     def test_find_in_section(self):
790         setup_helper = ProxDpdkVnfSetupEnvHelper(mock.MagicMock(), mock.MagicMock(),
791                                                  mock.MagicMock())
792
793         setup_helper._prox_config_data = [
794             ('global', [
795                 ('not_name', 'other data'),
796                 ('name_not', 'more data'),
797                 ('name', 'prox type'),
798             ]),
799             ('section1', []),
800             ('section2', [
801                 ('a', 'b'),
802                 ('c', 'd'),
803             ]),
804             ('core 1', []),
805             ('core 2', [
806                 ('index', 8),
807                 ('mode', ''),
808             ]),
809             ('core 3', [
810                 ('index', 5),
811                 ('mode', 'gen'),
812                 ('name', 'tagged'),
813             ]),
814             ('section3', [
815                 ('key1', 'value1'),
816                 ('key2', 'value2'),
817                 ('key3', 'value3'),
818             ]),
819             ('core 4', [
820                 ('index', 7),
821                 ('mode', 'gen'),
822                 ('name', 'udp'),
823             ]),
824         ]
825
826         expected = 'value3'
827         result = setup_helper.find_in_section('section3', 'key3')
828         self.assertEqual(result, expected)
829
830         expected = 'default value'
831         result = setup_helper.find_in_section('section3', 'key4', 'default value')
832         self.assertEqual(result, expected)
833
834         with self.assertRaises(KeyError):
835             setup_helper.find_in_section('section4', 'key1')
836
837         with self.assertRaises(KeyError):
838             setup_helper.find_in_section('section1', 'key1')
839
840     def test__replace_quoted_with_value(self):
841         # empty string
842         input_str = ''
843         expected = ''
844         result = ProxDpdkVnfSetupEnvHelper._replace_quoted_with_value(input_str, 'cat')
845         self.assertEqual(result, expected)
846
847         # no quoted substring
848         input_str = 'lion tiger bear'
849         expected = 'lion tiger bear'
850         result = ProxDpdkVnfSetupEnvHelper._replace_quoted_with_value(input_str, 'cat')
851         self.assertEqual(result, expected)
852
853         # partially quoted substring
854         input_str = 'lion "tiger bear'
855         expected = 'lion "tiger bear'
856         result = ProxDpdkVnfSetupEnvHelper._replace_quoted_with_value(input_str, 'cat')
857         self.assertEqual(result, expected)
858
859         # one quoted substring
860         input_str = 'lion "tiger" bear'
861         expected = 'lion "cat" bear'
862         result = ProxDpdkVnfSetupEnvHelper._replace_quoted_with_value(input_str, 'cat')
863         self.assertEqual(result, expected)
864
865         # two quoted substrings
866         input_str = 'lion "tiger" bear "shark" whale'
867         expected = 'lion "cat" bear "shark" whale'
868         result = ProxDpdkVnfSetupEnvHelper._replace_quoted_with_value(input_str, 'cat')
869         self.assertEqual(result, expected)
870
871         # two quoted substrings, both replaced
872         input_str = 'lion "tiger" bear "shark" whale'
873         expected = 'lion "cat" bear "cat" whale'
874         result = ProxDpdkVnfSetupEnvHelper._replace_quoted_with_value(input_str, 'cat', 2)
875         self.assertEqual(result, expected)
876
877     def test__get_tx_port(self):
878         # no data
879         input_data = {'section1': []}
880         expected = -1
881         result = ProxDpdkVnfSetupEnvHelper._get_tx_port('section1', input_data)
882         self.assertEqual(result, expected)
883
884         # data for other section
885         input_data = {
886             'section1': [],
887             'section2': [
888                 ('rx port', '3'),
889                 ('tx port', '4'),
890             ],
891         }
892         expected = -1
893         result = ProxDpdkVnfSetupEnvHelper._get_tx_port('section1', input_data)
894         self.assertEqual(result, expected)
895
896         # data for section
897         input_data['section1'] = section1 = [
898             ('rx port', '4', 'more', 432),
899             ('tx port', '3'),
900         ]
901         expected = 3
902         result = ProxDpdkVnfSetupEnvHelper._get_tx_port('section1', input_data)
903         self.assertEqual(result, expected)
904
905         # more data for section,
906         section1.extend([
907             ('rx port', '2'),
908             ('tx port', '1', 'and more', 234),
909         ])
910         expected = 1
911         result = ProxDpdkVnfSetupEnvHelper._get_tx_port('section1', input_data)
912         self.assertEqual(result, expected)
913
914     # TODO(elfoley): Split this into several smaller tests
915     def test_write_prox_config(self):
916         input_data = {}
917         expected = ''
918         result = ProxDpdkVnfSetupEnvHelper.write_prox_config(input_data)
919         self.assertEqual(result, expected)
920
921         input_data = [
922             [
923                 'section1',
924                 [],
925             ],
926         ]
927         expected = '[section1]'
928         result = ProxDpdkVnfSetupEnvHelper.write_prox_config(input_data)
929         self.assertEqual(result, expected)
930
931         input_data = [
932             [
933                 'section1',
934                 [],
935             ],
936             [
937                 'section2',
938                 [
939                     ['key1', 'value1'],
940                     ['__name__', 'not this one'],
941                     ['key2', None],
942                     ['key3', 234],
943                     ['key4', 'multi-line\nvalue'],
944                 ],
945             ],
946         ]
947         expected = os.linesep.join([
948             '[section1]',
949             '[section2]',
950             'key1=value1',
951             'key2',
952             'key3=234',
953             'key4=multi-line\n\tvalue',
954         ])
955         result = ProxDpdkVnfSetupEnvHelper.write_prox_config(input_data)
956         self.assertEqual(result, expected)
957
958     def test_prox_config_data(self):
959         setup_helper = ProxDpdkVnfSetupEnvHelper(mock.MagicMock(), mock.MagicMock(),
960                                                  mock.MagicMock())
961
962         setup_helper.config_queue = config_queue = mock.MagicMock()
963         config_queue.get.return_value = expected = [('s', [('a', 3), ('b', 45)])]
964
965         result = setup_helper.prox_config_data
966         self.assertEqual(result, expected)
967
968     @mock.patch.object(utils, 'find_relative_file')
969     def test_build_config_file_no_additional_file(self, mock_find_path):
970         vnf1 = {
971             'prox_args': {'-c': ""},
972             'prox_path': 'd',
973             'prox_config': 'e/f',
974             'prox_generate_parameter': False,
975         }
976
977         mock_find_path.side_effect = ['1', '2']
978
979         vnfd_helper = mock.MagicMock()
980         ssh_helper = mock.MagicMock()
981         scenario_helper = ScenarioHelper('vnf1')
982         scenario_helper.scenario_cfg = {
983             'task_path': 'a/b',
984             'options': {
985                 'vnf1': vnf1,
986             },
987         }
988
989         helper = ProxDpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
990         helper.copy_to_target = mock.MagicMock(return_value='3')
991         helper.generate_prox_config_file = mock.MagicMock(return_value='4')
992         helper.upload_prox_config = mock.MagicMock(return_value='5')
993
994         self.assertEqual(helper.additional_files, {})
995         self.assertNotEqual(helper._prox_config_data, '4')
996         self.assertNotEqual(helper.remote_path, '5')
997         helper.build_config_file()
998         self.assertEqual(helper.additional_files, {})
999         self.assertEqual(helper._prox_config_data, '4')
1000         self.assertEqual(helper.remote_path, '5')
1001
1002     @mock.patch.object(utils, 'find_relative_file')
1003     def test_build_config_file_additional_file_string(self, mock_find_path):
1004         vnf1 = {
1005             'prox_args': {'-c': ""},
1006             'prox_path': 'd',
1007             'prox_config': 'e/f',
1008             'prox_files': 'g/h.i',
1009             'prox_generate_parameter': True,
1010         }
1011
1012         mock_find_path.side_effect = ['1', '2']
1013         vnfd_helper = mock.MagicMock()
1014         ssh_helper = mock.MagicMock()
1015         scenario_helper = ScenarioHelper('vnf1')
1016         scenario_helper.scenario_cfg = {
1017             'task_path': 'a/b',
1018             'options': {
1019                 'vnf1': vnf1,
1020             },
1021         }
1022
1023         vnfd_helper.port_pairs.all_ports = ['xe0', 'xe1', 'xe2', 'xe3']
1024         helper = ProxDpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
1025         helper.copy_to_target = mock.MagicMock(side_effect=['33', '34', '35'])
1026         helper.generate_prox_config_file = mock.MagicMock(return_value='44')
1027         helper.upload_prox_config = mock.MagicMock(return_value='55')
1028
1029         self.assertEqual(helper.additional_files, {})
1030         expected = {'h.i': '33'}
1031         helper.build_config_file()
1032         self.assertDictEqual(helper.additional_files, expected)
1033
1034     @mock.patch.object(utils, 'find_relative_file')
1035     def test_build_config_file_additional_file(self, mock_find_path):
1036         vnf1 = {
1037             'prox_args': {'-c': ""},
1038             'prox_path': 'd',
1039             'prox_config': 'e/f',
1040             'prox_files': [
1041                 'g/h.i',
1042                 'j/k/l',
1043                 'm_n',
1044             ],
1045         }
1046
1047         mock_find_path.side_effect = ['1', '2'] + [str(i) for i in range(len(vnf1['prox_files']))]
1048         vnfd_helper = mock.MagicMock()
1049         ssh_helper = mock.MagicMock()
1050         scenario_helper = ScenarioHelper('vnf1')
1051         scenario_helper.scenario_cfg = {
1052             'task_path': 'a/b',
1053             'options': {
1054                 'vnf1': vnf1,
1055             },
1056         }
1057
1058         helper = ProxDpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
1059         helper.copy_to_target = mock.MagicMock(side_effect=['33', '34', '35'])
1060         helper.generate_prox_config_file = mock.MagicMock(return_value='44')
1061         helper.upload_prox_config = mock.MagicMock(return_value='55')
1062
1063         self.assertEqual(helper.additional_files, {})
1064         self.assertNotEqual(helper._prox_config_data, '44')
1065         self.assertNotEqual(helper.remote_path, '55')
1066         expected = {'h.i': '33', 'l': '34', 'm_n': '35'}
1067         helper.build_config_file()
1068         self.assertDictEqual(helper.additional_files, expected)
1069         self.assertEqual(helper._prox_config_data, '44')
1070         self.assertEqual(helper.remote_path, '55')
1071
1072     def test_build_config(self):
1073         vnf1 = {
1074             'prox_args': {'-f': ""},
1075             'prox_path': '/opt/nsb_bin/prox',
1076             'prox_config': 'configs/gen_l2fwd-2.cfg',
1077             'prox_files': [
1078                 'g/h.i',
1079                 'j/k/l',
1080                 'm_n',
1081             ],
1082         }
1083
1084         vnfd_helper = mock.Mock()
1085         ssh_helper = mock.Mock()
1086         ssh_helper.join_bin_path.return_value = '/opt/nsb_bin/prox'
1087         scenario_helper = ScenarioHelper('vnf1')
1088         scenario_helper.scenario_cfg = {
1089             'task_path': 'a/b',
1090             'options': {
1091                 'vnf1': vnf1,
1092             },
1093         }
1094
1095         expected = ("sudo bash -c 'cd /opt/nsb_bin; /opt/nsb_bin/prox -o cli "
1096                     "-f  -f /tmp/prox.cfg '")
1097
1098         helper = ProxDpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper,
1099                                            scenario_helper)
1100         with mock.patch.object(helper, 'build_config_file') as mock_cfg_file:
1101             helper.remote_path = '/tmp/prox.cfg'
1102             prox_cmd = helper.build_config()
1103             self.assertEqual(prox_cmd, expected)
1104             mock_cfg_file.assert_called_once()
1105
1106     def test__insert_additional_file(self):
1107         vnfd_helper = mock.MagicMock()
1108         ssh_helper = mock.MagicMock()
1109         scenario_helper = mock.MagicMock()
1110
1111         helper = ProxDpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
1112         helper.additional_files = {"ipv4.lua": "/tmp/ipv4.lua"}
1113         res = helper._insert_additional_file('dofile("ipv4.lua")')
1114         self.assertEqual(res, 'dofile("/tmp/ipv4.lua")')
1115
1116     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.ConfigParser')
1117     def test_generate_prox_config_file(self, mock_parser_type):
1118         def init(*args):
1119             if sections_data:
1120                 args[-1].extend(sections_data)
1121             return mock.MagicMock()
1122
1123         sections_data = []
1124
1125         mock_parser_type.side_effect = init
1126
1127         vnfd_helper = VnfdHelper(self.VNFD0)
1128         ssh_helper = mock.MagicMock()
1129         scenario_helper = mock.MagicMock()
1130
1131         helper = ProxDpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
1132         helper.additional_files = {}
1133
1134         expected = []
1135         result = helper.generate_prox_config_file('a/b')
1136         self.assertEqual(result, expected)
1137
1138         helper.additional_files = {"ipv4.lua": "/tmp/ipv4.lua"}
1139
1140         helper.remote_prox_file_name = 'remote'
1141         sections_data = [
1142             [
1143                 'lua',
1144                 [
1145                     ['dofile("ipv4.lua")', ''],
1146                 ],
1147             ],
1148             [
1149                 'port 0',
1150                 [
1151                     ['ip', ''],
1152                     ['mac', 'foo'],
1153                     ['dst mac', '@@1'],
1154                     ['tx port', '1'],
1155                 ],
1156             ],
1157             [
1158                 'port 2',
1159                 [
1160                     ['ip', ''],
1161                     ['$sut_mac0', '@@dst_mac0'],
1162                     ['tx port', '0'],
1163                     ['single', '@'],
1164                     ['user_table', 'dofile("ipv4.lua")'],
1165                     ['missing_addtional_file', 'dofile("nosuch")'],
1166                 ],
1167             ],
1168         ]
1169
1170         expected = [
1171             [
1172                 'lua',
1173                 [
1174                     ['dofile("/tmp/ipv4.lua")', ''],
1175                 ],
1176             ],
1177             [
1178                 'port 0',
1179                 [
1180                     ['ip', ''],
1181                     ['mac', 'hardware'],
1182                     ['dst mac', '00:00:00:00:00:03'],
1183                     ['tx port', '1'],
1184                 ],
1185             ],
1186             [
1187                 'port 2',
1188                 [
1189                     ['ip', ''],
1190                     ['$sut_mac0', '00 00 00 00 00 04'],
1191                     ['tx port', '0'],
1192                     ['single', '@'],
1193                     ['user_table', 'dofile("/tmp/ipv4.lua")'],
1194                     ['missing_addtional_file', 'dofile("nosuch")'],
1195                 ],
1196             ],
1197         ]
1198         result = helper.generate_prox_config_file('/c/d/e')
1199         self.assertEqual(result, expected, str(result))
1200
1201     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.ConfigParser')
1202     def test_generate_prox_config_file_negative(self, mock_parser_type):
1203         def init(*args):
1204             args[-1].update(sections_data)
1205             return mock.MagicMock()
1206
1207         sections_data = {}
1208
1209         mock_parser_type.side_effect = init
1210
1211         vnfd_helper = mock.MagicMock()
1212         vnfd_helper.interfaces = []
1213         ssh_helper = mock.MagicMock()
1214         scenario_helper = mock.MagicMock()
1215
1216         helper = ProxDpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
1217         helper.additional_files = {}
1218         helper.remote_prox_file_name = 'remote'
1219         vnfd_helper.interfaces = [
1220             {
1221                 'virtual-interface': {
1222                     'dpdk_port_num': 3,
1223                     'dst_mac': '00:00:00:de:ad:88',
1224                 },
1225             },
1226             {
1227                 'virtual-interface': {
1228                     'dpdk_port_num': 5,
1229                     'dst_mac': '00:00:00:de:ad:ff',
1230                 },
1231             },
1232             {
1233                 'virtual-interface': {
1234                     'dpdk_port_num': 7,
1235                     'dst_mac': '00:00:00:de:ad:ff',
1236                 },
1237             },
1238         ]
1239         sections_data = {
1240             'port 3': [
1241                 ['ip', ''],
1242                 ['mac', 'foo'],
1243                 ['dst mac', ''],
1244             ],
1245             'port 5': [
1246                 ['ip', ''],
1247                 ['dst mac', ''],
1248                 ['tx port', '0'],
1249                 ['???', 'dofile "here" 23'],
1250             ],
1251         }
1252
1253         with self.assertRaises(Exception):
1254             helper.generate_prox_config_file('a/b')
1255
1256     def test_put_string_to_file(self):
1257         vnfd_helper = mock.MagicMock()
1258         vnfd_helper.interfaces = []
1259         ssh_helper = mock.MagicMock()
1260         scenario_helper = mock.MagicMock()
1261
1262         helper = ProxDpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
1263
1264         expected = 'a/b'
1265         result = helper.put_string_to_file('my long string', 'a/b')
1266         self.assertEqual(result, expected)
1267
1268     def test_copy_to_target(self):
1269         vnfd_helper = mock.MagicMock()
1270         vnfd_helper.interfaces = []
1271         ssh_helper = mock.MagicMock()
1272         scenario_helper = mock.MagicMock()
1273
1274         helper = ProxDpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
1275         expected = '/tmp/c'
1276         result = helper.copy_to_target('a/b', 'c')
1277         self.assertEqual(result, expected)
1278
1279     def test_upload_prox_config(self):
1280         vnfd_helper = mock.MagicMock()
1281         vnfd_helper.interfaces = []
1282         ssh_helper = mock.MagicMock()
1283         scenario_helper = mock.MagicMock()
1284
1285         helper = ProxDpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
1286         helper.write_prox_config = mock.MagicMock(return_value='a long string')
1287         expected = '/tmp/a'
1288         result = helper.upload_prox_config('a', {})
1289         self.assertEqual(result, expected)
1290
1291
1292 class TestProxResourceHelper(unittest.TestCase):
1293
1294     VNFD0 = {
1295         'short-name': 'ProxVnf',
1296         'vdu': [
1297             {
1298                 'routing_table': [
1299                     {
1300                         'network': '152.16.100.20',
1301                         'netmask': '255.255.255.0',
1302                         'gateway': '152.16.100.20',
1303                         'if': 'xe0',
1304                     },
1305                     {
1306                         'network': '152.16.40.20',
1307                         'netmask': '255.255.255.0',
1308                         'gateway': '152.16.40.20',
1309                         'if': 'xe1',
1310                     },
1311                 ],
1312                 'description': 'PROX approximation using DPDK',
1313                 'name': 'proxvnf-baremetal',
1314                 'nd_route_tbl': [
1315                     {
1316                         'network': '0064:ff9b:0:0:0:0:9810:6414',
1317                         'netmask': '112',
1318                         'gateway': '0064:ff9b:0:0:0:0:9810:6414',
1319                         'if': 'xe0',
1320                     },
1321                     {
1322                         'network': '0064:ff9b:0:0:0:0:9810:2814',
1323                         'netmask': '112',
1324                         'gateway': '0064:ff9b:0:0:0:0:9810:2814',
1325                         'if': 'xe1',
1326                     },
1327                 ],
1328                 'id': 'proxvnf-baremetal',
1329                 'external-interface': [
1330                     {
1331                         'virtual-interface': {
1332                             'dst_mac': '00:00:00:00:00:04',
1333                             'vpci': '0000:05:00.0',
1334                             'local_ip': '152.16.100.19',
1335                             'type': 'PCI-PASSTHROUGH',
1336                             'vld_id': 'uplink_0',
1337                             'netmask': '255.255.255.0',
1338                             'dpdk_port_num': 0,
1339                             'bandwidth': '10 Gbps',
1340                             'driver': "i40e",
1341                             'dst_ip': '152.16.100.19',
1342                             'local_iface_name': 'xe0',
1343                             'local_mac': '00:00:00:00:00:02',
1344                             'ifname': 'xe0',
1345                         },
1346                         'vnfd-connection-point-ref': 'xe0',
1347                         'name': 'xe0',
1348                     },
1349                     {
1350                         'virtual-interface': {
1351                             'dst_mac': '00:00:00:00:00:03',
1352                             'vpci': '0000:05:00.1',
1353                             'local_ip': '152.16.40.19',
1354                             'type': 'PCI-PASSTHROUGH',
1355                             'vld_id': 'downlink_0',
1356                             'driver': "i40e",
1357                             'netmask': '255.255.255.0',
1358                             'dpdk_port_num': 1,
1359                             'bandwidth': '10 Gbps',
1360                             'dst_ip': '152.16.40.20',
1361                             'local_iface_name': 'xe1',
1362                             'local_mac': '00:00:00:00:00:01',
1363                             'ifname': 'xe1',
1364                         },
1365                         'vnfd-connection-point-ref': 'xe1',
1366                         'name': 'xe1',
1367                     },
1368                 ],
1369             },
1370         ],
1371         'description': 'PROX approximation using DPDK',
1372         'mgmt-interface': {
1373             'vdu-id': 'proxvnf-baremetal',
1374             'host': '1.2.1.1',
1375             'password': 'r00t',
1376             'user': 'root',
1377             'ip': '1.2.1.1',
1378         },
1379         'benchmark': {
1380             'kpi': [
1381                 'packets_in',
1382                 'packets_fwd',
1383                 'packets_dropped',
1384             ],
1385         },
1386         'id': 'ProxApproxVnf',
1387         'name': 'ProxVnf',
1388     }
1389
1390     VNFD = {
1391         'vnfd:vnfd-catalog': {
1392             'vnfd': [
1393                 VNFD0,
1394             ],
1395         },
1396     }
1397
1398     def test_find_pci(self):
1399         input_str_list = [
1400             'no target here',
1401             'nor here',
1402             'and still not',
1403         ]
1404         result = ProxResourceHelper.find_pci('target', input_str_list)
1405         self.assertFalse(result)
1406
1407         input_str_list = [
1408             'no target here',
1409             'nor here',
1410             'this is a target',
1411             'did we miss it',
1412         ]
1413         result = ProxResourceHelper.find_pci('target', input_str_list)
1414         self.assertTrue(result)
1415
1416     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.RETRY_INTERVAL', 0)
1417     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.ProxSocketHelper')
1418     def test_sut(self, *args):
1419         helper = ProxResourceHelper(mock.MagicMock())
1420         self.assertIsNone(helper.client)
1421         result = helper.sut
1422         self.assertIsNotNone(result)
1423         self.assertIs(result, helper.client)
1424         self.assertIs(result, helper.sut)
1425
1426     def test_test_type(self):
1427         setup_helper = mock.MagicMock()
1428         setup_helper.find_in_section.return_value = expected = 'prox type'
1429
1430         helper = ProxResourceHelper(setup_helper)
1431
1432         self.assertIsNone(helper._test_type)
1433         self.assertEqual(helper.test_type, expected)
1434         self.assertEqual(helper._test_type, expected)
1435         self.assertEqual(helper.test_type, expected)
1436
1437     def test_collect_collectd_kpi(self):
1438         helper = ProxResourceHelper(mock.MagicMock())
1439         helper.resource = resource = mock.MagicMock()
1440
1441         resource.check_if_system_agent_running.return_value = 0, '1234'
1442         resource.amqp_collect_nfvi_kpi.return_value = 543
1443         resource.check_if_system_agent_running.return_value = (0, None)
1444
1445         expected = {'core': 543}
1446         result = helper.collect_collectd_kpi()
1447         self.assertDictEqual(result, expected)
1448
1449     def test_collect_kpi(self):
1450         helper = ProxResourceHelper(mock.MagicMock())
1451         helper._queue = queue = mock.MagicMock()
1452         helper._result = {'z': 123}
1453         helper.resource = resource = mock.MagicMock()
1454
1455         resource.check_if_system_agent_running.return_value = 0, '1234'
1456         resource.amqp_collect_nfvi_kpi.return_value = 543
1457         resource.check_if_system_agent_running.return_value = (0, None)
1458
1459         queue.empty.return_value = False
1460         queue.get.return_value = {'a': 789}
1461
1462         expected = {'z': 123, 'a': 789, 'collect_stats': {'core': 543}}
1463         result = helper.collect_kpi()
1464         self.assertDictEqual(result, expected)
1465
1466     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.time')
1467     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.ProxSocketHelper')
1468     def test__connect(self, mock_socket_helper_type, *args):
1469         client = mock_socket_helper_type()
1470         client.connect.side_effect = chain(repeat(socket.error, 5), [None])
1471
1472         setup_helper = mock.MagicMock()
1473         setup_helper.vnfd_helper.interfaces = []
1474
1475         helper = ProxResourceHelper(setup_helper)
1476
1477         result = helper._connect()
1478         self.assertIs(result, client)
1479
1480         client.connect.side_effect = chain(repeat(socket.error, 65), [None])
1481
1482         with self.assertRaises(Exception):
1483             helper._connect()
1484
1485     def test_run_traffic(self):
1486         setup_helper = mock.MagicMock()
1487         helper = ProxResourceHelper(setup_helper)
1488         traffic_profile = mock.MagicMock(**{"done": True})
1489         helper.run_traffic(traffic_profile)
1490         self.assertEqual(helper._terminated.value, 1)
1491
1492     def test__run_traffic_once(self):
1493         setup_helper = mock.MagicMock()
1494         helper = ProxResourceHelper(setup_helper)
1495         traffic_profile = mock.MagicMock(**{"done": True})
1496         helper._run_traffic_once(traffic_profile)
1497         self.assertEqual(helper._terminated.value, 1)
1498
1499     def test_start_collect(self):
1500         setup_helper = mock.MagicMock()
1501         helper = ProxResourceHelper(setup_helper)
1502         helper.resource = resource = mock.MagicMock()
1503         self.assertIsNone(helper.start_collect())
1504         resource.start.assert_called_once()
1505
1506     def test_terminate(self):
1507         setup_helper = mock.MagicMock()
1508         helper = ProxResourceHelper(setup_helper)
1509         with self.assertRaises(NotImplementedError):
1510             helper.terminate()
1511
1512     def test_up_post(self):
1513         setup_helper = mock.MagicMock()
1514         helper = ProxResourceHelper(setup_helper)
1515         helper.client = expected = mock.MagicMock()
1516         result = helper.up_post()
1517         self.assertEqual(result, expected)
1518
1519     def test_execute(self):
1520         setup_helper = mock.MagicMock()
1521         helper = ProxResourceHelper(setup_helper)
1522         helper.client = mock.MagicMock()
1523
1524         expected = helper.client.my_command()
1525         result = helper.execute('my_command')
1526         self.assertEqual(result, expected)
1527
1528         # TODO(elfoley): Make this a separate test: test_execute_no_client
1529         helper.client = object()
1530
1531         result = helper.execute('my_command')
1532         self.assertIsNone(result)
1533
1534
1535 class TestProxDataHelper(unittest.TestCase):
1536
1537     def test_totals_and_pps(self):
1538         pkt_size = 180
1539         vnfd_helper = mock.MagicMock()
1540         vnfd_helper.port_pairs.all_ports = list(range(4))
1541
1542         sut = mock.MagicMock()
1543         sut.port_stats.return_value = list(range(10))
1544
1545         data_helper = ProxDataHelper(
1546             vnfd_helper, sut, pkt_size, 25, None,
1547             constants.NIC_GBPS_DEFAULT * constants.ONE_GIGABIT_IN_BITS)
1548
1549         self.assertEqual(data_helper.rx_total, 6)
1550         self.assertEqual(data_helper.tx_total, 7)
1551         self.assertEqual(data_helper.requested_pps, 6.25e6)
1552
1553     def test_samples(self):
1554         vnfd_helper = mock.MagicMock()
1555         vnfd_helper.port_pairs.all_ports = list(range(4))
1556         vnfd_helper.ports_iter.return_value = [('xe1', 3), ('xe2', 7)]
1557
1558         sut = mock.MagicMock()
1559         sut.port_stats.return_value = list(range(10))
1560
1561         data_helper = ProxDataHelper(vnfd_helper, sut, None, None, None, None)
1562
1563         expected = {
1564             'xe1': {
1565                 'in_packets': 6,
1566                 'out_packets': 7,
1567             },
1568             'xe2': {
1569                 'in_packets': 6,
1570                 'out_packets': 7,
1571             },
1572         }
1573         result = data_helper.samples
1574         self.assertDictEqual(result, expected)
1575
1576     def test___enter__(self):
1577         vnfd_helper = mock.MagicMock()
1578         vnfd_helper.port_pairs.all_ports = list(range(4))
1579         vnfd_helper.ports_iter.return_value = [('xe1', 3), ('xe2', 7)]
1580
1581         sut = mock.MagicMock()
1582         sut.port_stats.return_value = list(range(10))
1583
1584         data_helper = ProxDataHelper(vnfd_helper, sut, None, None,
1585             5.4, constants.NIC_GBPS_DEFAULT * constants.ONE_GIGABIT_IN_BITS)
1586         data_helper._totals_and_pps = 12, 32, 4.5
1587         data_helper.tsc_hz = 9.8
1588         data_helper.measured_stats = {'delta': TotStatsTuple(6.1, 6.2, 6.3, 6.4)}
1589         data_helper.latency = 7
1590
1591         self.assertIsNone(data_helper.result_tuple)
1592         self.assertEqual(data_helper.line_speed, 10000000000)
1593
1594         expected = ProxTestDataTuple(5.4, 9.8, 6.1, 6.2, 6.3, 7, 12, 32, 4.5)
1595         with data_helper:
1596             pass
1597
1598         result = data_helper.result_tuple
1599         self.assertEqual(result, expected)
1600
1601         data_helper.make_tuple()
1602         self.assertIs(data_helper.result_tuple, result)
1603
1604     def test___enter___negative(self):
1605         vnfd_helper = mock.MagicMock()
1606
1607         data_helper = ProxDataHelper(vnfd_helper, None, None, None, None, None)
1608
1609         vnfd_helper.port_pairs.all_ports = []
1610         with self.assertRaises(AssertionError):
1611             with data_helper:
1612                 pass
1613
1614         vnfd_helper.port_pairs.all_ports = [0, 1, 2]
1615         with self.assertRaises(AssertionError):
1616             with data_helper:
1617                 pass
1618
1619     def test_measure_tot_stats(self):
1620         vnfd_helper = mock.MagicMock()
1621         vnfd_helper.port_pairs.all_ports = list(range(4))
1622
1623         start = (3, 4, 1, 2)
1624         end = (9, 7, 6, 8)
1625
1626         sut = ProxSocketHelper(mock.MagicMock())
1627         sut.get_all_tot_stats = mock.MagicMock(side_effect=[start, end])
1628
1629         data_helper = ProxDataHelper(vnfd_helper, sut, None, None, 5.4, None)
1630
1631         self.assertIsNone(data_helper.measured_stats)
1632
1633         expected = {
1634             'start_tot': start,
1635             'end_tot': end,
1636             'delta': TotStatsTuple(6, 3, 5, 6),
1637         }
1638         with data_helper.measure_tot_stats():
1639             pass
1640
1641         self.assertEqual(data_helper.measured_stats, expected)
1642
1643     def test_capture_tsc_hz(self):
1644         vnfd_helper = mock.MagicMock()
1645         vnfd_helper.port_pairs.all_ports = list(range(4))
1646
1647         sut = mock.MagicMock()
1648         sut.hz.return_value = '54.6'
1649
1650         data_helper = ProxDataHelper(vnfd_helper, sut, None, None, None, None)
1651
1652         self.assertIsNone(data_helper.tsc_hz)
1653
1654         expected = 54.6
1655         data_helper.capture_tsc_hz()
1656         self.assertEqual(data_helper.tsc_hz, expected)
1657
1658
1659 class TestProxProfileHelper(unittest.TestCase):
1660
1661     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.utils')
1662     def test_get_cls(self, mock_utils):
1663         mock_type1 = mock.MagicMock()
1664         mock_type1.__prox_profile_type__ = 'another_type'
1665         mock_type2 = mock.MagicMock()
1666         mock_type2.__prox_profile_type__ = 'my_type'
1667         mock_utils.itersubclasses.return_value = [mock_type1, mock_type2]
1668
1669         self.assertEqual(ProxProfileHelper.get_cls('my_type'), mock_type2)
1670
1671     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.utils')
1672     def test_get_cls_default(self, mock_utils):
1673         mock_utils.itersubclasses.return_value = []
1674         ProxProfileHelper.get_cls('my_type')
1675
1676     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.SocketTopology')
1677     def test_cpu_topology(self, mock_socket_topology):
1678         mock_socket_topology.parse_cpuinfo.return_value = 432
1679
1680         resource_helper = mock.MagicMock()
1681         resource_helper.setup_helper.ssh_helper.execute.return_value = 0, 'output', ''
1682
1683         helper = ProxProfileHelper(resource_helper)
1684         self.assertIsNone(helper._cpu_topology)
1685         result = helper.cpu_topology
1686         self.assertEqual(result, 432)
1687         self.assertIs(result, helper._cpu_topology)
1688         self.assertIs(result, helper.cpu_topology)
1689
1690     # TODO(elfoley): Split this test; there are two sets of inputs/outputs
1691     def test_test_cores(self):
1692         resource_helper = mock.MagicMock()
1693         resource_helper.setup_helper.prox_config_data = []
1694
1695         helper = ProxProfileHelper(resource_helper)
1696         helper._cpu_topology = []
1697
1698         expected = []
1699         result = helper.test_cores
1700         self.assertEqual(result, expected)
1701
1702         resource_helper.setup_helper.prox_config_data = [
1703             ('section1', []),
1704             ('section2', [
1705                 ('a', 'b'),
1706                 ('c', 'd'),
1707             ]),
1708             ('core 1s3', []),
1709             ('core 2s5', [
1710                 ('index', 8),
1711                 ('mode', ''),
1712             ]),
1713             ('core 3s1', [
1714                 ('index', 5),
1715                 ('mode', 'gen'),
1716             ]),
1717             ('core 4s9h', [
1718                 ('index', 7),
1719                 ('mode', 'gen'),
1720             ]),
1721         ]
1722
1723         helper = ProxProfileHelper(resource_helper)
1724         helper._cpu_topology = {
1725             1: {
1726                 3: {
1727                     'key1': (23, 32),
1728                     'key2': (12, 21),
1729                     'key3': (44, 33),
1730                 },
1731             },
1732             9: {
1733                 4: {
1734                     'key1': (44, 32),
1735                     'key2': (23, 21),
1736                     'key3': (12, 33),
1737                 },
1738             },
1739         }
1740
1741         self.assertIsNone(helper._test_cores)
1742         expected = [3, 4]
1743         result = helper.test_cores
1744         self.assertEqual(result, expected)
1745         self.assertIs(result, helper._test_cores)
1746         self.assertIs(result, helper.test_cores)
1747
1748     # TODO(elfoley): Split this test; there are two sets of inputs/outputs
1749     def test_latency_cores(self):
1750         resource_helper = mock.MagicMock()
1751         resource_helper.setup_helper.prox_config_data = []
1752
1753         helper = ProxProfileHelper(resource_helper)
1754         helper._cpu_topology = []
1755
1756         expected = []
1757         result = helper.latency_cores
1758         self.assertEqual(result, expected)
1759
1760         resource_helper.setup_helper.prox_config_data = [
1761             ('section1', []),
1762             ('section2', [
1763                 ('a', 'b'),
1764                 ('c', 'd'),
1765             ]),
1766             ('core 1s3', []),
1767             ('core 2s5', [
1768                 ('index', 8),
1769                 ('mode', ''),
1770             ]),
1771             ('core 3s1', [
1772                 ('index', 5),
1773                 ('mode', 'lat'),
1774             ]),
1775             ('core 4s9h', [
1776                 ('index', 7),
1777                 ('mode', 'lat'),
1778             ]),
1779         ]
1780
1781         helper = ProxProfileHelper(resource_helper)
1782         helper._cpu_topology = {
1783             1: {
1784                 3: {
1785                     'key1': (23, 32),
1786                     'key2': (12, 21),
1787                     'key3': (44, 33),
1788                 },
1789             },
1790             9: {
1791                 4: {
1792                     'key1': (44, 32),
1793                     'key2': (23, 21),
1794                     'key3': (12, 33),
1795                 },
1796             },
1797         }
1798
1799         self.assertIsNone(helper._latency_cores)
1800         expected = [3, 4]
1801         result = helper.latency_cores
1802         self.assertEqual(result, expected)
1803         self.assertIs(result, helper._latency_cores)
1804         self.assertIs(result, helper.latency_cores)
1805
1806     def test_all_rx_cores(self):
1807         helper = ProxBngProfileHelper(mock.MagicMock())
1808         helper._latency_cores = expected = [3, 4, 6]
1809         helper._test_cores = [5, 2, 1]
1810
1811         result = helper.all_rx_cores
1812         self.assertEqual(result, expected)
1813
1814     def test_get_cores(self):
1815         resource_helper = mock.MagicMock()
1816         resource_helper.setup_helper.prox_config_data = [
1817             ('section1', []),
1818             ('section2', [
1819                 ('a', 'b'),
1820                 ('c', 'd'),
1821             ]),
1822             ('core 1', []),
1823             ('core 2', [
1824                 ('index', 8),
1825                 ('mode', ''),
1826             ]),
1827             ('core 3', [
1828                 ('index', 5),
1829                 ('mode', 'gen'),
1830             ]),
1831             ('core 4', [
1832                 ('index', 7),
1833                 ('mode', 'gen'),
1834             ]),
1835         ]
1836
1837         helper = ProxProfileHelper(resource_helper)
1838         helper._cpu_topology = {
1839             0: {
1840                 1: {
1841                     5: (5, 1, 0)
1842                 },
1843                 2: {
1844                     6: (6, 2, 0)
1845                 },
1846                 3: {
1847                     7: (7, 3, 0)
1848                 },
1849                 4: {
1850                     8: (8, 3, 0)
1851                 },
1852             }
1853         }
1854
1855         expected = [3, 4]
1856         result = helper.get_cores(helper.PROX_CORE_GEN_MODE)
1857         self.assertEqual(result, expected)
1858
1859     def test_get_latency(self):
1860         resource_helper = mock.MagicMock()
1861         resource_helper.setup_helper.vnfd_helper.interfaces = []
1862
1863         helper = ProxProfileHelper(resource_helper)
1864         helper._latency_cores = []
1865
1866         expected = []
1867         result = helper.get_latency()
1868         self.assertEqual(result, expected)
1869
1870         helper._latency_cores = [1, 2]
1871         helper.client = mock.MagicMock()
1872
1873         expected = helper.sut.lat_stats()
1874         result = helper.get_latency()
1875         self.assertIs(result, expected)
1876
1877     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.time')
1878     def test_traffic_context(self, *args):
1879         setup_helper = mock.MagicMock()
1880         setup_helper.vnfd_helper.interfaces = []
1881
1882         helper = ProxProfileHelper(setup_helper)
1883         helper._cpu_topology = {
1884             0: {
1885                 1: {
1886                     5: (5, 1, 0)
1887                 },
1888                 2: {
1889                     6: (6, 2, 0)
1890                 },
1891                 3: {
1892                     7: (7, 3, 0)
1893                 },
1894                 4: {
1895                     8: (8, 3, 0)
1896                 },
1897             }
1898         }
1899
1900         setup_helper.prox_config_data = [
1901             ('global', [
1902                 ('not_name', 'other data'),
1903                 ('name_not', 'more data'),
1904                 ('name', helper.__prox_profile_type__),
1905             ]),
1906             ('section1', []),
1907             ('section2', [
1908                 ('a', 'b'),
1909                 ('c', 'd'),
1910             ]),
1911             ('core 1', []),
1912             ('core 2', [
1913                 ('index', 8),
1914                 ('mode', ''),
1915             ]),
1916             ('core 3', [
1917                 ('index', 5),
1918                 ('mode', 'gen'),
1919                 ('name', 'tagged'),
1920             ]),
1921             ('core 4', [
1922                 ('index', 7),
1923                 ('mode', 'gen'),
1924                 ('name', 'udp'),
1925             ]),
1926         ]
1927
1928         client = mock.MagicMock()
1929         client.hz.return_value = 2
1930         client.port_stats.return_value = tuple(range(12))
1931
1932         helper.client = client
1933         helper.get_latency = mock.MagicMock(return_value=[3.3, 3.6, 3.8])
1934
1935         helper._test_cores = [3, 4]
1936
1937         with helper.traffic_context(64, 1):
1938             pass
1939
1940     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.time')
1941     def test_run_test(self, _):
1942         resource_helper = mock.MagicMock()
1943         resource_helper.step_delta = 0.4
1944         resource_helper.vnfd_helper.port_pairs.all_ports = list(range(2))
1945         resource_helper.sut.port_stats.return_value = list(range(10))
1946
1947         helper = ProxProfileHelper(resource_helper)
1948
1949         helper.run_test(120, 5, 6.5,
1950                         constants.NIC_GBPS_DEFAULT * constants.ONE_GIGABIT_IN_BITS)
1951
1952
1953 class TestProxMplsProfileHelper(unittest.TestCase):
1954
1955     def test_mpls_cores(self):
1956         resource_helper = mock.MagicMock()
1957         resource_helper.setup_helper.prox_config_data = [
1958             ('section1', []),
1959             ('section2', [
1960                 ('a', 'b'),
1961                 ('c', 'd'),
1962             ]),
1963             ('core 1', []),
1964             ('core 2', [
1965                 ('index', 8),
1966                 ('mode', ''),
1967             ]),
1968             ('core 3', [
1969                 ('index', 5),
1970                 ('mode', 'gen'),
1971                 ('name', 'tagged'),
1972             ]),
1973             ('core 4', [
1974                 ('index', 7),
1975                 ('mode', 'gen'),
1976                 ('name', 'udp'),
1977             ]),
1978         ]
1979
1980         helper = ProxMplsProfileHelper(resource_helper)
1981         helper._cpu_topology = {
1982             0: {
1983                 1: {
1984                     5: (5, 1, 0)
1985                 },
1986                 2: {
1987                     6: (6, 2, 0)
1988                 },
1989                 3: {
1990                     7: (7, 3, 0)
1991                 },
1992                 4: {
1993                     8: (8, 3, 0)
1994                 },
1995             }
1996         }
1997
1998         expected_tagged = [3]
1999         expected_plain = [4]
2000         self.assertIsNone(helper._cores_tuple)
2001         self.assertEqual(helper.tagged_cores, expected_tagged)
2002         self.assertEqual(helper.plain_cores, expected_plain)
2003         self.assertEqual(helper._cores_tuple, (expected_tagged, expected_plain))
2004
2005     def test_traffic_context(self):
2006         setup_helper = mock.MagicMock()
2007         helper = ProxMplsProfileHelper(setup_helper)
2008
2009         with helper.traffic_context(120, 5.4):
2010             pass
2011
2012
2013 class TestProxBngProfileHelper(unittest.TestCase):
2014
2015     def test_bng_cores(self):
2016         resource_helper = mock.MagicMock()
2017         resource_helper.setup_helper.prox_config_data = [
2018             ('section1', []),
2019             ('section2', [
2020                 ('a', 'b'),
2021                 ('c', 'd'),
2022             ]),
2023             ('core 1', []),
2024             ('core 2', [
2025                 ('index', 8),
2026                 ('mode', ''),
2027             ]),
2028             ('core 3', [
2029                 ('index', 5),
2030                 ('mode', 'gen'),
2031                 ('name', 'cpe'),
2032             ]),
2033             ('core 4', [
2034                 ('index', 7),
2035                 ('mode', 'gen'),
2036                 ('name', 'inet'),
2037             ]),
2038             ('core 6', [
2039                 ('index', 3),
2040                 ('mode', 'gen'),
2041                 ('name', 'arp_task'),
2042             ]),
2043             ('core 9', [
2044                 ('index', 2),
2045                 ('mode', 'gen'),
2046                 ('name', 'arp'),
2047             ]),
2048         ]
2049
2050         helper = ProxBngProfileHelper(resource_helper)
2051         helper._cpu_topology = {
2052             0: {
2053                 1: {
2054                     5: (5, 1, 0)
2055                 },
2056                 2: {
2057                     6: (6, 2, 0)
2058                 },
2059                 3: {
2060                     7: (7, 3, 0)
2061                 },
2062                 4: {
2063                     8: (8, 3, 0)
2064                 },
2065                 6: {
2066                     1: (4, 8, 0)
2067                 },
2068                 9: {
2069                     2: (3, 7, 0)
2070                 },
2071             }
2072         }
2073
2074         expected_cpe = [3]
2075         expected_inet = [4]
2076         expected_arp = [6, 9]
2077         expected_arp_task = [0, 6]
2078         expected_combined = (expected_cpe, expected_inet, expected_arp, expected_arp_task)
2079
2080         self.assertIsNone(helper._cores_tuple)
2081         self.assertEqual(helper.cpe_cores, expected_cpe)
2082         self.assertEqual(helper.inet_cores, expected_inet)
2083         self.assertEqual(helper.arp_cores, expected_arp)
2084         self.assertEqual(helper.arp_task_cores, expected_arp_task)
2085         self.assertEqual(helper._cores_tuple, expected_combined)
2086
2087     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.time')
2088     def test_run_test(self, _):
2089         resource_helper = mock.MagicMock()
2090         resource_helper.step_delta = 0.4
2091         resource_helper.vnfd_helper.port_pairs.all_ports = list(range(2))
2092         resource_helper.sut.port_stats.return_value = list(range(10))
2093
2094         helper = ProxBngProfileHelper(resource_helper)
2095
2096         helper.run_test(120, 5, 6.5,
2097                         constants.NIC_GBPS_DEFAULT * constants.ONE_GIGABIT_IN_BITS)
2098
2099         # negative pkt_size is the only way to make ratio > 1
2100         helper.run_test(-1000, 5, 6.5,
2101                         constants.NIC_GBPS_DEFAULT * constants.ONE_GIGABIT_IN_BITS)
2102
2103
2104 class TestProxVpeProfileHelper(unittest.TestCase):
2105
2106     def test_vpe_cores(self):
2107         resource_helper = mock.MagicMock()
2108         resource_helper.setup_helper.prox_config_data = [
2109             ('section1', []),
2110             ('section2', [
2111                 ('a', 'b'),
2112                 ('c', 'd'),
2113             ]),
2114             ('core 1', []),
2115             ('core 2', [
2116                 ('index', 8),
2117                 ('mode', ''),
2118             ]),
2119             ('core 3', [
2120                 ('index', 5),
2121                 ('mode', 'gen'),
2122                 ('name', 'cpe'),
2123             ]),
2124             ('core 4', [
2125                 ('index', 7),
2126                 ('mode', 'gen'),
2127                 ('name', 'inet'),
2128             ]),
2129         ]
2130
2131         helper = ProxVpeProfileHelper(resource_helper)
2132         helper._cpu_topology = {
2133             0: {
2134                 1: {
2135                     5: (5, 1, 0)
2136                 },
2137                 2: {
2138                     6: (6, 2, 0)
2139                 },
2140                 3: {
2141                     7: (7, 3, 0)
2142                 },
2143                 4: {
2144                     8: (8, 3, 0)
2145                 },
2146             }
2147         }
2148
2149         expected_cpe = [3]
2150         expected_inet = [4]
2151         expected_combined = (expected_cpe, expected_inet)
2152
2153         self.assertIsNone(helper._cores_tuple)
2154         self.assertEqual(helper.cpe_cores, expected_cpe)
2155         self.assertEqual(helper.inet_cores, expected_inet)
2156         self.assertEqual(helper._cores_tuple, expected_combined)
2157
2158     def test_vpe_ports(self):
2159         resource_helper = mock.MagicMock()
2160         resource_helper.setup_helper.prox_config_data = [
2161             ('section1', []),
2162             ('section2', [
2163                 ('a', 'b'),
2164                 ('c', 'd'),
2165             ]),
2166             ('port 3', [
2167                 ('index', '5'),
2168                 ('name', 'cpe'),
2169                 ('mac', 'hardware'),
2170             ]),
2171             ('port 4', [
2172                 ('index', '7'),
2173                 ('name', 'inet'),
2174                 ('mac', 'hardware'),
2175             ]),
2176         ]
2177
2178         helper = ProxVpeProfileHelper(resource_helper)
2179         helper._port_list = {
2180             0: {
2181                 1: {
2182                     5: 'cpe'
2183                 },
2184                 2: {
2185                     6: 'inet'
2186                 },
2187                 3: {
2188                     7: 'cpe'
2189                 },
2190                 4: {
2191                     8: 'inet'
2192                 },
2193             }
2194         }
2195
2196         expected_cpe = [3]
2197         expected_inet = [4]
2198         expected_combined = (expected_cpe, expected_inet)
2199
2200         self.assertIsNone(helper._ports_tuple)
2201         self.assertEqual(helper.cpe_ports, expected_cpe)
2202         self.assertEqual(helper.inet_ports, expected_inet)
2203         self.assertEqual(helper._ports_tuple, expected_combined)
2204
2205     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.time')
2206     def test_run_test(self, _):
2207         resource_helper = mock.MagicMock()
2208         resource_helper.step_delta = 0.4
2209         resource_helper.vnfd_helper.port_pairs.all_ports = list(range(2))
2210         resource_helper.sut.port_stats.return_value = list(range(10))
2211
2212         helper = ProxVpeProfileHelper(resource_helper)
2213
2214         helper.run_test(120, 5, 6.5)
2215         helper.run_test(-1000, 5, 6.5)  # negative pkt_size is the only way to make ratio > 1
2216
2217
2218 class TestProxlwAFTRProfileHelper(unittest.TestCase):
2219
2220     def test_lwaftr_cores(self):
2221         resource_helper = mock.MagicMock()
2222         resource_helper.setup_helper.prox_config_data = [
2223             ('section1', []),
2224             ('section2', [
2225                 ('a', 'b'),
2226                 ('c', 'd'),
2227             ]),
2228             ('core 1', []),
2229             ('core 2', [
2230                 ('index', 8),
2231                 ('mode', ''),
2232             ]),
2233             ('core 3', [
2234                 ('index', 5),
2235                 ('mode', 'gen'),
2236                 ('name', 'tun'),
2237             ]),
2238             ('core 4', [
2239                 ('index', 7),
2240                 ('mode', 'gen'),
2241                 ('name', 'inet'),
2242             ]),
2243         ]
2244
2245         helper = ProxlwAFTRProfileHelper(resource_helper)
2246         helper._cpu_topology = {
2247             0: {
2248                 1: {
2249                     5: (5, 1, 0)
2250                 },
2251                 2: {
2252                     6: (6, 2, 0)
2253                 },
2254                 3: {
2255                     7: (7, 3, 0)
2256                 },
2257                 4: {
2258                     8: (8, 3, 0)
2259                 },
2260             }
2261         }
2262
2263         expected_tun = [3]
2264         expected_inet = [4]
2265         expected_combined = (expected_tun, expected_inet)
2266
2267         self.assertIsNone(helper._cores_tuple)
2268         self.assertEqual(helper.tun_cores, expected_tun)
2269         self.assertEqual(helper.inet_cores, expected_inet)
2270         self.assertEqual(helper._cores_tuple, expected_combined)
2271
2272     def test_tun_ports(self):
2273         resource_helper = mock.MagicMock()
2274         resource_helper.setup_helper.prox_config_data = [
2275             ('section1', []),
2276             ('section2', [
2277                 ('a', 'b'),
2278                 ('c', 'd'),
2279             ]),
2280             ('port 3', [
2281                 ('index', '5'),
2282                 ('name', 'lwB4'),
2283                 ('mac', 'hardware'),
2284             ]),
2285             ('port 4', [
2286                 ('index', '7'),
2287                 ('name', 'inet'),
2288                 ('mac', 'hardware'),
2289             ]),
2290         ]
2291
2292         helper = ProxlwAFTRProfileHelper(resource_helper)
2293         helper._port_list = {
2294             0: {
2295                 1: {
2296                     5: 'lwB4'
2297                 },
2298                 2: {
2299                     6: 'inet'
2300                 },
2301                 3: {
2302                     7: 'lwB4'
2303                 },
2304                 4: {
2305                     8: 'inet'
2306                 },
2307             }
2308         }
2309
2310         expected_tun = [3]
2311         expected_inet = [4]
2312         expected_combined = (expected_tun, expected_inet)
2313
2314         self.assertIsNone(helper._ports_tuple)
2315         self.assertEqual(helper.tun_ports, expected_tun)
2316         self.assertEqual(helper.inet_ports, expected_inet)
2317         self.assertEqual(helper._ports_tuple, expected_combined)
2318
2319     @mock.patch('yardstick.network_services.vnf_generic.vnf.prox_helpers.time')
2320     def test_run_test(self, _):
2321         resource_helper = mock.MagicMock()
2322         resource_helper.step_delta = 0.4
2323         resource_helper.vnfd_helper.port_pairs.all_ports = list(range(2))
2324         resource_helper.sut.port_stats.return_value = list(range(10))
2325
2326         helper = ProxlwAFTRProfileHelper(resource_helper)
2327
2328         helper.run_test(120, 5, 6.5)
2329         helper.run_test(-1000, 5, 6.5)  # negative pkt_size is the only way to make ratio > 1