1 # Copyright 2015-2017 Intel Corporation.
3 # Licensed under the Apache License, Version 2.0 (the "License");
4 # you may not use this file except in compliance with the License.
5 # You may obtain a copy of the License at
7 # http://www.apache.org/licenses/LICENSE-2.0
9 # Unless required by applicable law or agreed to in writing, software
10 # distributed under the License is distributed on an "AS IS" BASIS,
11 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 # See the License for the specific language governing permissions and
13 # limitations under the License.
15 """Base class for traffic controllers
22 from core.results.results_constants import ResultsConstants
23 from conf import settings
25 class TrafficController(object):
26 """Base class which defines a common functionality for all traffic
29 Used to setup and control a traffic generator for a particular deployment
32 def __init__(self, traffic_gen_class):
33 """Initialization common for all types of traffic controllers
35 :param traffic_gen_class: The traffic generator class to be used.
38 self._logger = logging.getLogger(__name__)
39 self._logger.debug("__init__")
40 self._traffic_gen_class = traffic_gen_class()
41 self._traffic_started = False
42 self._traffic_started_call_count = 0
45 self._packet_sizes = None
46 self._connected = False
48 self._mode = str(settings.getValue('mode')).lower()
51 def configure(self, traffic):
52 """Set configuration values just before test execution so they
53 can be changed during runtime by test steps.
55 if not self._connected:
56 self._traffic_gen_class.connect()
57 self._connected = True
59 self._duration = int(settings.getValue('TRAFFICGEN_DURATION'))
60 self._lossrate = float(settings.getValue('TRAFFICGEN_LOSSRATE'))
61 self._packet_sizes = settings.getValue('TRAFFICGEN_PKT_SIZES')
64 # update type with detailed traffic value
65 self._type = traffic['traffic_type']
68 """Call initialisation function.
72 def __exit__(self, type_, value, traceback):
73 """Stop traffic, clean up.
75 if self._traffic_started:
78 def _append_results(self, result_dict, packet_size):
79 """Adds common values to traffic generator results.
81 :param result_dict: Dictionary containing results from trafficgen
82 :param packet_size: Packet size value.
84 :returns: dictionary of results with additional entries.
87 ret_value = result_dict
89 ret_value[ResultsConstants.TYPE] = self._type
90 ret_value[ResultsConstants.PACKET_SIZE] = str(packet_size)
94 def traffic_required(self):
95 """Checks selected '--mode' of traffic generator and performs
96 its specific handling.
98 :returns: True - in case that traffic generator should be executed
99 False - if traffic generation is not required
101 if self._mode == 'trafficgen-off':
103 self._logger.debug("All is set. Please run traffic generator manually.")
104 input(os.linesep + "Press Enter to terminate vswitchperf..." +
105 os.linesep + os.linesep)
107 elif self._mode == 'trafficgen-pause':
110 choice = input(os.linesep + 'Transmission paused, should'
111 ' transmission be resumed? [y/n]' + os.linesep).lower()
112 if choice in ('yes', 'y', 'ye'):
114 elif choice in ('no', 'n'):
115 self._logger.info("Traffic transmission will be skipped.")
118 print("Please respond with 'yes', 'y', 'no' or 'n' ", end='')
121 def send_traffic(self, traffic):
122 """Triggers traffic to be sent from the traffic generator.
124 This is a blocking function.
126 :param traffic: A dictionary describing the traffic to send.
128 self._logger.debug('send_traffic with %s',
129 str(self._traffic_gen_class))
130 self.configure(traffic)
132 def send_traffic_async(self, traffic, dummy_function):
133 """Triggers traffic to be sent asynchronously.
135 This is not a blocking function.
137 :param traffic: A dictionary describing the traffic to send.
138 :param function: A dictionary describing the function to call between
139 send and wait in the form:
141 'function' : package.module.function,
144 If this function requires more than one argument, all should be
145 should be passed using the args list and appropriately handled.
147 # pylint: disable=unused-argument
148 self._logger.debug('send_traffic_async with %s',
149 str(self._traffic_gen_class))
150 self.configure(traffic)
152 def stop_traffic(self):
153 """Kills traffic being sent from the traffic generator.
155 self._logger.debug("stop_traffic()")
157 def print_results(self):
158 """IResult interface implementation.
161 for item in self._results:
162 logging.info("Record: %s", str(counter))
164 for(key, value) in list(item.items()):
165 logging.info(" Key: " + str(key) +
166 ", Value: " + str(value))
168 def get_results(self):
169 """IResult interface implementation.
173 def validate_send_traffic(self, _dummy_result, _dummy_traffic):
174 """Verify that send traffic has succeeded
177 if 'b2b_frames' in self._results[-1]:
178 return float(self._results[-1]['b2b_frames']) > 0
179 elif 'throughput_rx_fps' in self._results[-1]:
180 return float(self._results[-1]['throughput_rx_fps']) > 0
186 def validate_get_results(self, result):
187 """Verify that results has been returned
189 return self._results == result