From: yufengmx <yufengx.mo@intel.com>
To: dts@dpdk.org
Cc: yufengmx <yufengx.mo@intel.com>
Subject: [dts] [PATCH V1 6/10] [next]framework/pktgen_base: add new feature and fix
Date: Mon, 5 Aug 2019 13:50:40 +0800 [thread overview]
Message-ID: <1564984244-151448-7-git-send-email-yufengx.mo@intel.com> (raw)
In-Reply-To: <1564984244-151448-1-git-send-email-yufengx.mo@intel.com>
internal bug
*. add test method(latency/loss/throughput) delay/duration options new usage
definition and relevant process source code.
*. set delay option to be the warm up time after start transmission.
*. add __get_single_throughput_statistic/__get_multi_throughput_statistic methods to realize
measure_throughput support return several throughput numbers in a duration.
*. set duration option default value to 10 second.
*. add test method(latency/loss/throughput/rfc2544) options parameter usage comment,
which is the same as doc pktgen_prog_guide.rst.
*. add missing start traffic option input in measure_throughput method.
*. remove logger format setting after import libs to fix dts redundant logs.
*. set part of information logger display to debug level.
*. remove un-used libs import.
*. fix pep8 issue.
Signed-off-by: yufengmx <yufengx.mo@intel.com>
---
framework/pktgen_base.py | 179 +++++++++++++++++++++++++++++++++++++++--------
1 file changed, 149 insertions(+), 30 deletions(-)
diff --git a/framework/pktgen_base.py b/framework/pktgen_base.py
index e9d3fcb..8915ac5 100644
--- a/framework/pktgen_base.py
+++ b/framework/pktgen_base.py
@@ -29,27 +29,22 @@
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-import os
import time
import logging
from abc import abstractmethod
from copy import deepcopy
-from logger import getLogger
from pprint import pformat
from config import PktgenConf
+from logger import getLogger, set_verbose
# packet generator name
-from settings import PKTGEN_DPDK, PKTGEN_TREX, PKTGEN_IXIA, PKTGEN
+from settings import (PKTGEN_DPDK, PKTGEN_TREX, PKTGEN_IXIA, PKTGEN,
+ load_global_setting, DEBUG_SETTING)
# macro definition
TRANSMIT_CONT = 'continuous'
TRANSMIT_M_BURST = 'multi_burst'
TRANSMIT_S_BURST = 'single_burst'
-# set logger
-FORMAT = '%(message)s'
-logging.basicConfig(format=FORMAT)
-logger = logging.getLogger(os.path.basename(__file__)[:-3].upper())
-logger.setLevel(logging.INFO)
class PacketGenerator(object):
@@ -57,8 +52,11 @@ class PacketGenerator(object):
Basic class for packet generator, define basic function for each kinds of
generators
"""
+
def __init__(self, tester):
self.logger = getLogger(PKTGEN)
+ if load_global_setting(DEBUG_SETTING) == "yes":
+ set_verbose()
self.tester = tester
self.__streams = []
self._ports_map = []
@@ -82,8 +80,8 @@ class PacketGenerator(object):
tester_pci = info['pci']
if tester_pci == gen_pci:
msg = "gen port {0} map test port {1}".format(
- port_id, port_idx)
- self.logger.info(msg)
+ port_id, port_idx)
+ self.logger.debug(msg)
return port_idx
else:
port = -1
@@ -105,15 +103,15 @@ class PacketGenerator(object):
tester_pci = info['pci']
port = self._get_gen_port(tester_pci)
msg = "test port {0} map gen port {1}".format(port_id, port)
- self.logger.info(msg)
+ self.logger.debug(msg)
except:
port = -1
return port
def add_stream(self, tx_port, rx_port, pcap_file):
- pktgen_tx_port = self._convert_tester_port(tx_port)
- pktgen_rx_port = self._convert_tester_port(rx_port)
+ pktgen_tx_port = self._convert_tester_port(tx_port)
+ pktgen_rx_port = self._convert_tester_port(rx_port)
stream_id = len(self.__streams)
stream = {'tx_port': pktgen_tx_port,
@@ -163,39 +161,105 @@ class PacketGenerator(object):
def reset_streams(self):
self.__streams = []
- def measure_throughput(self, stream_ids=[], options={}):
- """
- Measure throughput on each tx ports
- """
+ def __warm_up_pktgen(self, stream_ids, options, delay):
+ ''' run warm up traffic before start main traffic '''
+ if not delay:
+ return
+ msg = 'run traffic {0}s to warm up {1} packet generator '.format(
+ delay, self.pktgen_type)
+ self.logger.info(msg)
+ self._start_transmission(stream_ids, options)
+ time.sleep(delay)
+ self._stop_transmission(stream_ids)
+
+ def __get_single_throughput_statistic(self, stream_ids):
bps_rx = []
pps_rx = []
- self._prepare_transmission(stream_ids=stream_ids)
- self._start_transmission(stream_ids)
-
- delay = options.get('delay') or 5
- time.sleep(delay)
used_rx_port = []
+ msg = 'begin get port statistic ...'
+ self.logger.info(msg)
for stream_id in stream_ids:
if self.__streams[stream_id]['rx_port'] not in used_rx_port:
rxbps_rates, rxpps_rates = self._retrieve_port_statistic(
- stream_id, 'throughput')
+ stream_id, 'throughput')
used_rx_port.append(self.__streams[stream_id]['rx_port'])
bps_rx.append(rxbps_rates)
pps_rx.append(rxpps_rates)
- self._stop_transmission(stream_id)
-
bps_rx_total = self._summary_statistic(bps_rx)
pps_rx_total = self._summary_statistic(pps_rx)
- self.logger.info("throughput: pps_rx %f, bps_rx %f" % (pps_rx_total, bps_rx_total))
+ self.logger.info(
+ "throughput: pps_rx %f, bps_rx %f" % (pps_rx_total, bps_rx_total))
return bps_rx_total, pps_rx_total
+ def __get_multi_throughput_statistic(self, stream_ids, duration, interval):
+ """
+ duration: define the measure duration (second)
+ interval: define the interval of get throughput number (second)
+
+ Return: a list of throughput instead of a single tuple of pps/bps rate
+ """
+ time_elapsed = 0
+ stats = []
+ while time_elapsed < duration:
+ time.sleep(interval)
+ stats.append(self.__get_single_throughput_statistic(stream_ids))
+ time_elapsed += interval
+ return stats
+
+ def measure_throughput(self, stream_ids=[], options={}):
+ """
+ Measure throughput on each tx ports
+
+ options usage:
+ rate:
+ port rate percent, float(0--100). Default value is 100.
+
+ delay:
+ warm up time before start main traffic. If it is set, it will start
+ a delay time traffic to make sure packet generator under good status.
+ Warm up flow is ignored by default.
+
+ interval:
+ a interval time of get throughput statistic (second)
+ If set this key value, pktgen will return several throughput statistic
+ data within a duration traffic. If not set this key value, only return one statistic
+ data. It is ignored by default.
+
+ duration:
+ traffic lasting time(second). Default value is 10 second.
+ """
+ interval = options.get('interval')
+ duration = options.get('duration') or 10
+ delay = options.get('delay')
+ self._prepare_transmission(stream_ids=stream_ids)
+ # start warm up traffic
+ self.__warm_up_pktgen(stream_ids, options, delay)
+ # main traffic
+ self._start_transmission(stream_ids, options)
+ # keep traffic within a duration time and get throughput statistic
+ if interval and duration:
+ stats = self.__get_multi_throughput_statistic(
+ stream_ids, duration, interval)
+ else:
+ time.sleep(duration)
+ stats = self.__get_single_throughput_statistic(stream_ids)
+ self._stop_transmission(stream_ids)
+ return stats
+
def _measure_loss(self, stream_ids=[], options={}):
"""
Measure lost rate on each tx/rx ports
"""
+ delay = options.get('delay')
+ duration = options.get('duration') or 10
self._prepare_transmission(stream_ids=stream_ids)
+ # start warm up traffic
+ self.__warm_up_pktgen(stream_ids, options, delay)
+ # main traffic
self._start_transmission(stream_ids, options)
+ # keep traffic within a duration time
+ time.sleep(duration)
self._stop_transmission(None)
result = {}
used_rx_port = []
@@ -216,6 +280,19 @@ class PacketGenerator(object):
return result
def measure_loss(self, stream_ids=[], options={}):
+ '''
+ options usage:
+ rate:
+ port rate percent, float(0--100). Default value is 100.
+
+ delay:
+ warm up time before start main traffic. If it is set, it will
+ start a delay time traffic to make sure packet generator
+ under good status. Warm up flow is ignored by default.
+
+ duration:
+ traffic lasting time(second). Default value is 10 second.
+ '''
result = self._measure_loss(stream_ids, options)
# here only to make sure that return value is the same as dts/etgen format
# In real testing scenario, this method can offer more data than it
@@ -224,9 +301,28 @@ class PacketGenerator(object):
def measure_latency(self, stream_ids=[], options={}):
"""
Measure latency on each tx/rx ports
+
+ options usage:
+ rate:
+ port rate percent, float(0--100). Default value is 100.
+
+ delay:
+ warm up time before start main traffic. If it is set, it will
+ start a delay time transmission to make sure packet generator
+ under correct status. Warm up flow is ignored by default.
+
+ duration:
+ traffic lasting time(second). Default value is 10 second.
"""
+ delay = options.get('delay')
+ duration = options.get('duration') or 10
self._prepare_transmission(stream_ids=stream_ids, latency=True)
+ # start warm up traffic
+ self.__warm_up_pktgen(stream_ids, options, delay)
+ # main traffic
self._start_transmission(stream_ids, options)
+ # keep traffic within a duration time
+ time.sleep(duration)
self._stop_transmission(None)
result = {}
@@ -254,7 +350,26 @@ class PacketGenerator(object):
return True
def measure_rfc2544(self, stream_ids=[], options={}):
- """ check loss rate with rate percent dropping """
+ """ check loss rate with rate percent dropping
+
+ options usage:
+ rate:
+ port rate percent at first round testing(0 ~ 100), default is 100.
+
+ pdr:
+ permit packet drop rate, , default is 0.
+
+ drop_step:
+ port rate percent drop step(0 ~ 100), default is 1.
+
+ delay:
+ warm up time before start main traffic. If it is set, it will
+ start a delay time traffic to make sure packet generator
+ under good status. Warm up flow is ignored by default.
+
+ duration:
+ traffic lasting time(second). Default value is 10 second.
+ """
loss_rate_table = []
rate_percent = float(100)
permit_loss_rate = options.get('pdr') or 0
@@ -263,7 +378,7 @@ class PacketGenerator(object):
result = self._measure_loss(stream_ids, options)
status = self._check_loss_rate(result, permit_loss_rate)
loss_rate_table.append(
- [options.get('rate') or rate_percent, result])
+ [options.get('rate') or rate_percent, result])
# if first time loss rate is ok, ignore left flow
if status:
# return data is the same with dts/etgen format
@@ -271,6 +386,9 @@ class PacketGenerator(object):
# here only pick one
return result.values()[0]
_options = deepcopy(options)
+ # if warm up option 'delay' is set, ignore it in next work flow
+ if 'delay' in _options:
+ _options.pop('delay')
while not status and rate_percent > 0:
rate_percent = rate_percent - rate_step
if rate_percent <= 0:
@@ -320,7 +438,7 @@ class PacketGenerator(object):
traffic_pps_min = pps
if traffic_pps_max - traffic_pps_min < step:
break
- pps = (traffic_pps_max - traffic_pps_min)/2 + traffic_pps_min
+ pps = (traffic_pps_max - traffic_pps_min) / 2 + traffic_pps_min
self.logger.info("zero loss pps is %f" % last_no_lost_mult)
# use last result as return data to keep the same with dts/etgen format
@@ -397,4 +515,5 @@ class PacketGenerator(object):
pass
-class DpdkPacketGenerator(PacketGenerator): pass # not implemented
\ No newline at end of file
+class DpdkPacketGenerator(PacketGenerator):
+ pass # not implemented
--
1.9.3
next prev parent reply other threads:[~2019-08-05 5:49 UTC|newest]
Thread overview: 11+ messages / expand[flat|nested] mbox.gz Atom feed top
2019-08-05 5:50 [dts] [PATCH V1 0/10] [next]dts/pktgen: add new feature and fix some internal bugs yufengmx
2019-08-05 5:50 ` [dts] [PATCH V1 1/10] [next]conf/pktgen: update option description yufengmx
2019-08-05 5:50 ` [dts] [PATCH V1 2/10] [next]doc/dts_gsg/pktgen_prog_guide: update description yufengmx
2019-08-05 5:50 ` [dts] [PATCH V1 3/10] [next]framework/logger: add pktgen logger and remove yufengmx
2019-08-05 5:50 ` [dts] [PATCH V1 4/10] [next]framework/dut: fix logger quit issue yufengmx
2019-08-05 5:50 ` [dts] [PATCH V1 5/10] [next]framework/tester: " yufengmx
2019-08-05 5:50 ` yufengmx [this message]
2019-08-05 5:50 ` [dts] [PATCH V1 7/10] [next]framework/pktgen_ixia: add new feature and fix yufengmx
2019-08-05 5:50 ` [dts] [PATCH V1 8/10] [next]framework/pktgen_trex: " yufengmx
2019-08-05 5:50 ` [dts] [PATCH V1 9/10] [next]framework/pktgen: add new feature and fix internal yufengmx
2019-08-05 5:50 ` [dts] [PATCH V1 0/10] [next]tests/nic_single_core_perf: update pktgen input yufengmx
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1564984244-151448-7-git-send-email-yufengx.mo@intel.com \
--to=yufengx.mo@intel.com \
--cc=dts@dpdk.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).