aboutsummaryrefslogtreecommitdiffstats
path: root/yardstick/network_services/libs/ixia_libs
diff options
context:
space:
mode:
authorDeepak S <deepak.s@linux.intel.com>2017-06-20 14:18:57 -0700
committerRoss Brattain <ross.b.brattain@intel.com>2017-08-08 12:57:42 -0700
commit4545b967760ca795a3c67f043eaca60798a90570 (patch)
tree5ced218450c7fb96e1b6230080fc5cfc901b50fa /yardstick/network_services/libs/ixia_libs
parent5ce3b6f8c8b3217091e51a6041455738603d90b8 (diff)
IXIA traffic generator
Change-Id: I09bcb3f2c4b945283070d442589d3bf00468abbc Signed-off-by: Deepak S <deepak.s@linux.intel.com> Signed-off-by: Edward MacGillivray <edward.s.macgillivray@intel.com> Signed-off-by: Ross Brattain <ross.b.brattain@intel.com>
Diffstat (limited to 'yardstick/network_services/libs/ixia_libs')
-rw-r--r--yardstick/network_services/libs/ixia_libs/IxNet/IxNet.py335
-rw-r--r--yardstick/network_services/libs/ixia_libs/IxNet/__init__.py0
-rw-r--r--yardstick/network_services/libs/ixia_libs/__init__.py0
3 files changed, 335 insertions, 0 deletions
diff --git a/yardstick/network_services/libs/ixia_libs/IxNet/IxNet.py b/yardstick/network_services/libs/ixia_libs/IxNet/IxNet.py
new file mode 100644
index 000000000..815a2a21c
--- /dev/null
+++ b/yardstick/network_services/libs/ixia_libs/IxNet/IxNet.py
@@ -0,0 +1,335 @@
+# Copyright (c) 2016-2017 Intel Corporation
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+from __future__ import absolute_import
+from __future__ import print_function
+import sys
+import logging
+
+import re
+from itertools import product
+
+from yardstick.common.utils import ErrorClass
+
+try:
+ import IxNetwork
+except ImportError:
+ IxNetwork = ErrorClass
+
+log = logging.getLogger(__name__)
+
+IP_VERSION_4 = 4
+IP_VERSION_6 = 6
+
+
+class TrafficStreamHelper(object):
+
+ TEMPLATE = '{0.traffic_item}/{0.stream}:{0.param_id}/{1}'
+
+ def __init__(self, traffic_item, stream, param_id):
+ super(TrafficStreamHelper, self).__init__()
+ self.traffic_item = traffic_item
+ self.stream = stream
+ self.param_id = param_id
+
+ def __getattr__(self, item):
+ return self.TEMPLATE.format(self, item)
+
+
+class FramesizeHelper(object):
+
+ def __init__(self):
+ super(FramesizeHelper, self).__init__()
+ self.weighted_pairs = []
+ self.weighted_range_pairs = []
+
+ @property
+ def weighted_pairs_arg(self):
+ return '-weightedPairs', self.weighted_pairs
+
+ @property
+ def weighted_range_pairs_arg(self):
+ return '-weightedRangePairs', self.weighted_range_pairs
+
+ def make_args(self, *args):
+ return self.weighted_pairs_arg + self.weighted_range_pairs_arg + args
+
+ def populate_data(self, framesize_data):
+ for key, value in framesize_data.items():
+ if value == '0':
+ continue
+
+ replaced = re.sub('[Bb]', '', key)
+ self.weighted_pairs.extend([
+ replaced,
+ value,
+ ])
+ pairs = [
+ replaced,
+ replaced,
+ value,
+ ]
+ self.weighted_range_pairs.append(pairs)
+
+
+class IxNextgen(object):
+
+ STATS_NAME_MAP = {
+ "traffic_item": 'Traffic Item',
+ "Tx_Frames": 'Tx Frames',
+ "Rx_Frames": 'Rx Frames',
+ "Tx_Frame_Rate": 'Tx Frame Rate',
+ "Rx_Frame_Rate": 'Tx Frame Rate',
+ "Store-Forward_Avg_latency_ns": 'Store-Forward Avg Latency (ns)',
+ "Store-Forward_Min_latency_ns": 'Store-Forward Min Latency (ns)',
+ "Store-Forward_Max_latency_ns": 'Store-Forward Max Latency (ns)',
+ }
+
+ PORT_STATS_NAME_MAP = {
+ "stat_name": 'Stat Name',
+ "Frames_Tx": 'Frames Tx.',
+ "Valid_Frames_Rx": 'Valid Frames Rx.',
+ "Frames_Tx_Rate": 'Frames Tx. Rate',
+ "Valid_Frames_Rx_Rate": 'Valid Frames Rx. Rate',
+ "Tx_Rate_Kbps": 'Tx. Rate (Kbps)',
+ "Rx_Rate_Kbps": 'Rx. Rate (Kbps)',
+ "Tx_Rate_Mbps": 'Tx. Rate (Mbps)',
+ "Rx_Rate_Mbps": 'Rx. Rate (Mbps)',
+ }
+
+ LATENCY_NAME_MAP = {
+ "Store-Forward_Avg_latency_ns": 'Store-Forward Avg Latency (ns)',
+ "Store-Forward_Min_latency_ns": 'Store-Forward Min Latency (ns)',
+ "Store-Forward_Max_latency_ns": 'Store-Forward Max Latency (ns)',
+ }
+
+ RANDOM_MASK_MAP = {
+ IP_VERSION_4: '0.0.0.255',
+ IP_VERSION_6: '0:0:0:0:0:0:0:ff',
+ }
+
+ MODE_SEEDS_MAP = {
+ 0: ('private', ['256', '2048']),
+ }
+
+ MODE_SEEDS_DEFAULT = 'public', ['2048', '256']
+
+ @staticmethod
+ def find_view_obj(view_name, views):
+ edited_view_name = '::ixNet::OBJ-/statistics/view:"{}"'.format(view_name)
+ return next((view for view in views if edited_view_name == view), '')
+
+ @staticmethod
+ def get_config(tg_cfg):
+ external_interface = tg_cfg["vdu"][0]["external-interface"]
+ card_port0 = external_interface[0]["virtual-interface"]["vpci"]
+ card_port1 = external_interface[1]["virtual-interface"]["vpci"]
+ card0, port0 = card_port0.split(':')[:2]
+ card1, port1 = card_port1.split(':')[:2]
+ cfg = {
+ 'py_lib_path': tg_cfg["mgmt-interface"]["tg-config"]["py_lib_path"],
+ 'machine': tg_cfg["mgmt-interface"]["ip"],
+ 'port': tg_cfg["mgmt-interface"]["tg-config"]["tcl_port"],
+ 'chassis': tg_cfg["mgmt-interface"]["tg-config"]["ixchassis"],
+ 'card1': card0,
+ 'port1': port0,
+ 'card2': card1,
+ 'port2': port1,
+ 'output_dir': tg_cfg["mgmt-interface"]["tg-config"]["dut_result_dir"],
+ 'version': tg_cfg["mgmt-interface"]["tg-config"]["version"],
+ 'bidir': True,
+ }
+ return cfg
+
+ def __init__(self, ixnet=None):
+ self.ixnet = ixnet
+ self._objRefs = dict()
+ self._cfg = None
+ self._logger = logging.getLogger(__name__)
+ self._params = None
+ self._bidir = None
+
+ def iter_over_get_lists(self, x1, x2, y2, offset=0):
+ for x in self.ixnet.getList(x1, x2):
+ y_list = self.ixnet.getList(x, y2)
+ for i, y in enumerate(y_list, offset):
+ yield x, y, i
+
+ def set_random_ip_multi_attribute(self, ipv4, seed, fixed_bits, random_mask, l3_count):
+ self.ixnet.setMultiAttribute(
+ ipv4,
+ '-seed', str(seed),
+ '-fixedBits', str(fixed_bits),
+ '-randomMask', str(random_mask),
+ '-valueType', 'random',
+ '-countValue', str(l3_count))
+
+ def set_random_ip_multi_attributes(self, ip, version, seeds, l3):
+ try:
+ random_mask = self.RANDOM_MASK_MAP[version]
+ except KeyError:
+ raise ValueError('Unknown version %s' % version)
+
+ l3_count = l3['count']
+ if "srcIp" in ip:
+ fixed_bits = l3['srcip4']
+ self.set_random_ip_multi_attribute(ip, seeds[0], fixed_bits, random_mask, l3_count)
+ if "dstIp" in ip:
+ fixed_bits = l3['dstip4']
+ self.set_random_ip_multi_attribute(ip, seeds[1], fixed_bits, random_mask, l3_count)
+
+ def add_ip_header(self, params, version):
+ for it, ep, i in self.iter_over_get_lists('/traffic', 'trafficItem', "configElement"):
+ mode, seeds = self.MODE_SEEDS_MAP.get(i, self.MODE_SEEDS_DEFAULT)
+ l3 = params[mode]['outer_l3']
+
+ for ip, ip_bits, _ in self.iter_over_get_lists(ep, 'stack', 'field'):
+ self.set_random_ip_multi_attributes(ip_bits, version, seeds, l3)
+
+ self.ixnet.commit()
+
+ def _connect(self, tg_cfg):
+ self._cfg = self.get_config(tg_cfg)
+
+ sys.path.append(self._cfg["py_lib_path"])
+ self.ixnet = IxNetwork.IxNet()
+
+ machine = self._cfg['machine']
+ port = str(self._cfg['port'])
+ version = str(self._cfg['version'])
+ result = self.ixnet.connect(machine, '-port', port, '-version', version)
+ return result
+
+ def clear_ixia_config(self):
+ self.ixnet.execute('newConfig')
+
+ def load_ixia_profile(self, profile):
+ self.ixnet.execute('loadConfig', self.ixnet.readFrom(profile))
+
+ def ix_load_config(self, profile):
+ self.clear_ixia_config()
+ self.load_ixia_profile(profile)
+
+ def ix_assign_ports(self):
+ vports = self.ixnet.getList(self.ixnet.getRoot(), 'vport')
+ ports = [
+ (self._cfg['chassis'], self._cfg['card1'], self._cfg['port1']),
+ (self._cfg['chassis'], self._cfg['card2'], self._cfg['port2']),
+ ]
+
+ vport_list = self.ixnet.getList("/", "vport")
+ self.ixnet.execute('assignPorts', ports, [], vport_list, True)
+ self.ixnet.commit()
+
+ for vport in vports:
+ if self.ixnet.getAttribute(vport, '-state') != 'up':
+ log.error("Both thr ports are down...")
+
+ def ix_update_frame(self, params):
+ streams = ["configElement"]
+
+ for param in params.values():
+ framesize_data = FramesizeHelper()
+ traffic_items = self.ixnet.getList('/traffic', 'trafficItem')
+ param_id = param['id']
+ for traffic_item, stream in product(traffic_items, streams):
+ helper = TrafficStreamHelper(traffic_item, stream, param_id)
+
+ self.ixnet.setMultiAttribute(helper.transmissionControl,
+ '-type', '{0}'.format(param['traffic_type']),
+ '-duration', '{0}'.format(param['duration']))
+
+ stream_frame_rate_path = helper.frameRate
+ self.ixnet.setMultiAttribute(stream_frame_rate_path, '-rate', param['iload'])
+ if param['outer_l2']['framesPerSecond']:
+ self.ixnet.setMultiAttribute(stream_frame_rate_path,
+ '-type', 'framesPerSecond')
+
+ framesize_data.populate_data(param['outer_l2']['framesize'])
+
+ make_attr_args = framesize_data.make_args('-incrementFrom', '66',
+ '-randomMin', '66',
+ '-quadGaussian', [],
+ '-type', 'weightedPairs',
+ '-presetDistribution', 'cisco',
+ '-incrementTo', '1518')
+
+ self.ixnet.setMultiAttribute(helper.frameSize, *make_attr_args)
+
+ self.ixnet.commit()
+
+ def update_ether_multi_attribute(self, ether, mac_addr):
+ self.ixnet.setMultiAttribute(ether,
+ '-singleValue', mac_addr,
+ '-fieldValue', mac_addr,
+ '-valueType', 'singleValue')
+
+ def update_ether_multi_attributes(self, ether, l2):
+ if "ethernet.header.destinationAddress" in ether:
+ self.update_ether_multi_attribute(ether, str(l2['dstmac']))
+
+ if "ethernet.header.sourceAddress" in ether:
+ self.update_ether_multi_attribute(ether, str(l2['srcmac']))
+
+ def ix_update_ether(self, params):
+ for ti, ep, index in self.iter_over_get_lists('/traffic', 'trafficItem',
+ "configElement", 1):
+ iter1 = (v['outer_l2'] for v in params.values() if str(v['id']) == str(index))
+ try:
+ l2 = next(iter1, {})
+ except KeyError:
+ continue
+
+ for ip, ether, _ in self.iter_over_get_lists(ep, 'stack', 'field'):
+ self.update_ether_multi_attributes(ether, l2)
+
+ self.ixnet.commit()
+
+ def ix_update_udp(self, params):
+ pass
+
+ def ix_update_tcp(self, params):
+ pass
+
+ def ix_start_traffic(self):
+ tis = self.ixnet.getList('/traffic', 'trafficItem')
+ for ti in tis:
+ self.ixnet.execute('generate', [ti])
+ self.ixnet.execute('apply', '/traffic')
+ self.ixnet.execute('start', '/traffic')
+
+ def ix_stop_traffic(self):
+ tis = self.ixnet.getList('/traffic', 'trafficItem')
+ for _ in tis:
+ self.ixnet.execute('stop', '/traffic')
+
+ def build_stats_map(self, view_obj, name_map):
+ return {kl: self.execute_get_column_values(view_obj, kr) for kl, kr in name_map.items()}
+
+ def execute_get_column_values(self, view_obj, name):
+ return self.ixnet.execute('getColumnValues', view_obj, name)
+
+ def ix_get_statistics(self):
+ views = self.ixnet.getList('/statistics', 'view')
+ view_obj = self.find_view_obj("Traffic Item Statistics", views)
+ stats = self.build_stats_map(view_obj, self.STATS_NAME_MAP)
+
+ self.find_view_obj("Port Statistics", views)
+ ports_stats = self.build_stats_map(view_obj, self.PORT_STATS_NAME_MAP)
+
+ views = self.ixnet.getList('/statistics', 'view')
+ view_obj = self.find_view_obj("Flow Statistics", views)
+ stats["latency"] = self.build_stats_map(view_obj, self.LATENCY_NAME_MAP)
+
+ return stats, ports_stats
diff --git a/yardstick/network_services/libs/ixia_libs/IxNet/__init__.py b/yardstick/network_services/libs/ixia_libs/IxNet/__init__.py
new file mode 100644
index 000000000..e69de29bb
--- /dev/null
+++ b/yardstick/network_services/libs/ixia_libs/IxNet/__init__.py
diff --git a/yardstick/network_services/libs/ixia_libs/__init__.py b/yardstick/network_services/libs/ixia_libs/__init__.py
new file mode 100644
index 000000000..e69de29bb
--- /dev/null
+++ b/yardstick/network_services/libs/ixia_libs/__init__.py