* [dts] [v2] doc/dts_gsg: refresh dts guides
@ 2021-04-13 9:13 Lijuan Tu
2021-04-13 2:05 ` Tu, Lijuan
0 siblings, 1 reply; 2+ messages in thread
From: Lijuan Tu @ 2021-04-13 9:13 UTC (permalink / raw)
To: dts; +Cc: Lijuan Tu, Haiyang Zhao, hanyingya
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #1: Type: text/plain; charset=y, Size: 280852 bytes --]
* quick_start: new added for user quick to start DTS
* user guide: updated and reworked to align with DTS codes
* other: remove docs which are not match code and target to update next release
Signed-off-by: Lijuan Tu <lijuan.tu@intel.com>
Signed-off-by: Haiyang Zhao <haiyangx.zhao@intel.com>
Signed-off-by: hanyingya <yingyax.han@intel.com>
---
v2: fix types.
doc/dts_gsg/config.rst | 336 -----------
doc/dts_gsg/image/dts_result.png | Bin 7885 -> 10924 bytes
doc/dts_gsg/index.rst | 17 +-
doc/dts_gsg/intro.rst | 139 -----
doc/dts_gsg/migrate_from_etgen_to_pktgen.rst | 229 --------
doc/dts_gsg/multiple_vm.rst | 87 ---
doc/dts_gsg/pktgen_prog_guide.rst | 584 -------------------
doc/dts_gsg/quick_start.rst | 310 +++++++++++
doc/dts_gsg/review.rst | 104 ----
doc/dts_gsg/scenario.rst | 152 -----
doc/dts_gsg/support_igb_uio.rst | 102 ----
doc/dts_gsg/sys_reqs.rst | 202 -------
doc/dts_gsg/trex.rst | 23 -
doc/dts_gsg/trex_known_issue.rst | 113 ----
doc/dts_gsg/tutorial.rst | 139 -----
.../usage_of_create_eal_and_start_testpmd.rst | 103 ----
doc/dts_gsg/usr_guide/igb_uio.rst | 102 ++++
doc/dts_gsg/usr_guide/image/dts_func_deploy.png | Bin 0 -> 24729 bytes
doc/dts_gsg/usr_guide/image/dts_result.png | Bin 0 -> 10924 bytes
doc/dts_gsg/usr_guide/index.rst | 42 ++
doc/dts_gsg/usr_guide/intro.rst | 90 +++
doc/dts_gsg/usr_guide/ixia.rst | 248 +++++++++
doc/dts_gsg/usr_guide/results.rst | 101 ++++
doc/dts_gsg/usr_guide/sys_reqs.rst | 131 +++++
doc/dts_gsg/usr_guide/trex.rst | 377 +++++++++++++
doc/dts_gsg/usr_guide/usage.rst | 350 ++++++++++++
doc/dts_gsg/virtualization.rst | 617 ---------------------
27 files changed, 1754 insertions(+), 2944 deletions(-)
delete mode 100644 doc/dts_gsg/config.rst
delete mode 100644 doc/dts_gsg/intro.rst
delete mode 100644 doc/dts_gsg/migrate_from_etgen_to_pktgen.rst
delete mode 100644 doc/dts_gsg/multiple_vm.rst
delete mode 100644 doc/dts_gsg/pktgen_prog_guide.rst
create mode 100644 doc/dts_gsg/quick_start.rst
delete mode 100644 doc/dts_gsg/review.rst
delete mode 100644 doc/dts_gsg/scenario.rst
delete mode 100644 doc/dts_gsg/support_igb_uio.rst
delete mode 100644 doc/dts_gsg/sys_reqs.rst
delete mode 100644 doc/dts_gsg/trex.rst
delete mode 100644 doc/dts_gsg/trex_known_issue.rst
delete mode 100644 doc/dts_gsg/tutorial.rst
delete mode 100644 doc/dts_gsg/usage_of_create_eal_and_start_testpmd.rst
create mode 100644 doc/dts_gsg/usr_guide/igb_uio.rst
create mode 100644 doc/dts_gsg/usr_guide/image/dts_func_deploy.png
create mode 100644 doc/dts_gsg/usr_guide/image/dts_result.png
create mode 100644 doc/dts_gsg/usr_guide/index.rst
create mode 100644 doc/dts_gsg/usr_guide/intro.rst
create mode 100644 doc/dts_gsg/usr_guide/ixia.rst
create mode 100644 doc/dts_gsg/usr_guide/results.rst
create mode 100644 doc/dts_gsg/usr_guide/sys_reqs.rst
create mode 100644 doc/dts_gsg/usr_guide/trex.rst
create mode 100644 doc/dts_gsg/usr_guide/usage.rst
delete mode 100755 doc/dts_gsg/virtualization.rst
diff --git a/doc/dts_gsg/config.rst b/doc/dts_gsg/config.rst
deleted file mode 100644
index e02d152..0000000
--- a/doc/dts_gsg/config.rst
+++ /dev/null
@@ -1,336 +0,0 @@
-Configuring DPDK Test Suite
-===========================
-
-DPDK Test Suite command line
-----------------------------
-
-DPDK Test Suite supports multiple parameters and these parameters, which will select different of working mode of test framework. In the meantime, DPDK Test Suite can work with none parameter, then every parameter will set to its default value.
-For Example, please see specific usage, you can get these information via DPDK Test Suite help messages.
-
-.. code-block:: console
-
- usage: main.py [-h] [--config-file CONFIG_FILE] [--git GIT] [--patch PATCH]
- [--snapshot SNAPSHOT] [--output OUTPUT] [-s] [-r] [-p PROJECT]
- [--suite-dir SUITE_DIR] [-t TEST_CASES] [-d DIR] [-v]
- [--virttype VIRTTYPE] [--debug] [--debugcase] [--re_run RE_RUN]
- [--commands COMMANDS]
-
-
-DPDK Test Suite supports the following parameters:
-
-.. table::
-
- +---------------------------+---------------------------------------------------+------------------+
- | parameter | description | Default Value |
- +---------------------------+---------------------------------------------------+------------------+
- | -h,--help | show this help message and exit | |
- +---------------------------+---------------------------------------------------+------------------+
- | --config-file CONFIG_FILE | configuration file that describes the test cases, | execution.cfg |
- | | DUTs and targets | |
- +---------------------------+---------------------------------------------------+------------------+
- | --git GIT | Indicate git label to use as input | None |
- +---------------------------+---------------------------------------------------+------------------+
- | --patch PATCH | apply a patch to the package under test | None |
- +---------------------------+---------------------------------------------------+------------------+
- | --snapshot SNAPSHOT | snapshot .tgz file to use as input | dep/dpdk.tar.gz |
- +---------------------------+---------------------------------------------------+------------------+
- | --output OUTPUT | Output directory where DPDK Test Suite log and | output |
- | | result saved | |
- +---------------------------+---------------------------------------------------+------------------+
- | -s --skip-setup | Skips all possible setup steps done on both DUT | |
- | | and tester boards. | |
- +---------------------------+---------------------------------------------------+------------------+
- | -r | Reads the DUT configuration from a cache. If not | |
- | | specified, the DUT configuration will be | |
- | | calculated as usual and cached. | |
- +---------------------------+---------------------------------------------------+------------------+
- | -p PROJECT | Specify that which project will be tested dpdk | |
- | --project PROJECT | | |
- +---------------------------+---------------------------------------------------+------------------+
- | -t TEST_CASES | Executes only the followings test cases | None |
- | [TEST_CASES ...] | | |
- | --test-cases | | |
- | TEST_CASES | | |
- | [TEST_CASES ...] | | |
- +---------------------------+---------------------------------------------------+------------------+
- | -d DIR --dir DIR | Output directory where dpdk package is extracted | dpdk |
- +---------------------------+---------------------------------------------------+------------------+
- | --suite-dir | Test suite directory where test suites will be | tests |
- | | imported | |
- +---------------------------+---------------------------------------------------+------------------+
- | -v, --verbose | Enable verbose output, all log shown on screen | |
- +---------------------------+---------------------------------------------------+------------------+
- | --virttype | Set virtualization hypervisor type. Support kvm | |
- | | and libvirtd by now. | |
- +---------------------------+---------------------------------------------------+------------------+
- | --debug | Enable debug mode, running process can be | |
- | | interrupted and enter debug mode. | |
- +---------------------------+---------------------------------------------------+------------------+
- | --debugcase | Enter into debug mode before running every test | |
- | | case. | |
- +---------------------------+---------------------------------------------------+------------------+
- | --re_run TIMES | Rerun failed test cases for stable result | 0 |
- +---------------------------+---------------------------------------------------+------------------+
- | --commands COMMANDS | Run self assigned commands at different stages of | |
- | | execution. Format is [commands]:dut|tester:pre- | |
- | | init|post-init:check|ignore | |
- | | E.g. [/root/setup.sh]:dut:pre-init:check | |
- +---------------------------+---------------------------------------------------+------------------+
-
-Please see more information about some critical parameters as the following:
-
-**--config-file**
-
-DPDK Test Suite configure file defines some critical parameters. It must contain the DUT CRB IP address, wish list of test suites, DPDK target information and test mode parameter.
-
-**--git**
-
-When we use –-git parameter, DPDK Test Suite will clone the source code from dpdk.org git repository, then checkout branch specified by the parameter.
-
-**--patch**
-
-DPDK Test Suite also support apply specified patch list by --patch parameter before build DPDK packet.
-
-**--skip-setup**
-
-If DPDK source code doesn’t changed, you can use --skip-setup to skip unzip and compilation of DPDK source code, just reuse original source code.
-
-**--project**
-
-Parameter –-project can load customized project model and do its own project initialization.
-
-**--output**
-
-If we perform multiple validation at the same time, result files in output folder maybe overwritten. Then we can use –-output parameter to specify the output folder and save execution log and result files. This option will make sure that all test result will be stored in the different excel files and rst files, doesn’t conflict each other.
-
-.. note::
- The current working folder of DPDK Test Suite is "DTS root directory" and default output folder is “output”
-
-**--t**
-
-You can only run some specified cases in test suites.
-
-We can use parameter –-t to determine those cases.
-
-**--suite-dir**
-
-DPDK Test Suite support load suites from different folders, this will be helpful when there’s several projects existing in the same time.
-
-**--verbose**
-
-DPDK Test Suite support verbose mode. When enable this mode, all log messages will be output on screen and helpful for debug.
-
-**--virttype**
-
-Choose virtualization hypervisor type. By now this configuration is useless.
-
-**--debug**
-
-DPDK Test Suite support debug mode. After keyboard ctrl+c message to DTS process, will run into this mode. User can do further debug by attached to sessions or call pdb module by interact interface.
-
-Debug interact support commands as below:
-
-.. code-block:: console
-
- help(): show help message
- list(): list all connected sessions
- connect(name): connect to session directly
- exit(): exit dts
- quit(): quit debug mode and into normal mode
- debug(): call python debug module
-
-**--debugcase**
-
-Another approach to run into debug mode. With this option on, DTS will hang and wait for user command before execution of each test case.
-
-**--re_run**
-
-Some cases may failed due to miscellaneous packets, rerun those test cases can generate the stable result.
-
-**--commands**
-
-Allow user specify some commands which can be executed on DUT or Tester in the process of DPDK Test Suite preparation.
-
-DPDK Release Preparation
-------------------------
-
-Firstly, you need to download the latest code from dpdk.org, then archive and compress it into zipped file. After that, please move this zipped file to DPDK Test Suite "dep" folder. Once launch test framework, DPDK Test Suite will copy this zipped file to root folder on DUT. Finally this source code zip file will be unzipped and built.
-
-.. code-block:: console
-
- [root@tester dts]# ls
- [root@tester dts]# conf dep doc dts executions framework nics output test_plans tests tools
-
-
-If enables patch option, DPDK Test Suite will also make patch the unzipped folder and compile it.
-
-.. code-block:: console
-
- [root@tester dts]# ./dts --patch 1.patch --patch 2.patch
-
-Create your own execution configuration
----------------------------------------
-
-First of all, you must create a file named execution.cfg as below.
-
-.. code-block:: console
-
- [Execution1]
- crbs=192.168.1.1
- test_suites=
- hello_world,
- l2fwd
- targets=
- x86_64-default-linuxapp-gcc,
- parameters=nic_type=niantic:func=true
- scenario=pf_passthrough
-
-* crbs: IP address of the DUT CRB. The detail information of this CRB is defined in file crbs.py.
-* test_suites: defines list of test suites, which will plan to be executed.
-* targets: list of DPDK targets to be tested.
-* parameters: you can define multiple keywords
-* scenario: Scenario of DPDK virtualization environment for this execution.
-
- – nic_type : is the type of the NIC to use. The types are defined in the file settings.py.
- There's one special type named as **cfg**, which mean network information will be loaded from file.
-
- – func=true run only functional test
-
- – perf=true run only performance test
-
-Then please add the detail information about your CRB in **conf/crbs.conf** as follows:
-
-.. code-block:: console
-
- [192.168.1.1]
- dut_ip=192.168.1.1
- dut_user=root
- dut_passwd=
- os=linux
- tester_ip=192.168.1.2
- tester_passwd=
- ixia_group=group1
- channels=4
- bypass_core0=True
-
-
-.. table::
-
- +-----------------+----------------------------------------------------+
- | Item | description |
- +-----------------+----------------------------------------------------+
- | dut_ip | IP address of DUT |
- +-----------------+----------------------------------------------------+
- | dut_user | UserName of DPDK Test Suite used to login into DUT |
- +-----------------+----------------------------------------------------+
- | dut_passwd | Password of DPDK Test Suite used to login into DUT |
- +-----------------+----------------------------------------------------+
- | os | Distribution of operation system |
- +-----------------+----------------------------------------------------+
- | tester_ip | IP address of tester |
- +-----------------+----------------------------------------------------+
- | tester_passwd | Password to login into Tester |
- +-----------------+----------------------------------------------------+
- | ixia_group | IXIA group name for DUT |
- +-----------------+----------------------------------------------------+
- | channels | number of memory channels for DPDK EAL |
- +-----------------+----------------------------------------------------+
- | bypass_core0 | skip the first core when initialize DPDK |
- +-----------------+----------------------------------------------------+
-
-If you need to configure network topology, please add it in **conf/ports.cfg**, e.g.:
-
-.. code-block:: console
-
- [192.168.1.1]
- ports =
- pci=0000:06:00.0,peer=0000:81:00.0;
- pci=0000:06:00.1,peer=0000:81:00.1;
- pci=0000:08:00.0,peer=IXIA:1.1;
- pci=0000:08:00.1,peer=IXIA:1.2;
-
-.. table::
-
- +-----------------+----------------------------------------------------+
- | Item | description |
- +-----------------+----------------------------------------------------+
- | pci | Device pci address of DUT |
- +-----------------+----------------------------------------------------+
- | peer | Device pci address of Tester port which connected |
- | | to the DUT device |
- +-----------------+----------------------------------------------------+
-
-Launch DPDK Test Suite
-----------------------
-
-After we have prepared the zipped dpdk file and configuration file, just type the followed command “./dts”, it will start the validation process.
-
-DPDK Test Suite will create communication sessions first.
-
-.. code-block:: console
-
- DUT 192.168.1.1
- INFO: ssh root@192.168.1.1
- INFO: ssh root@192.168.1.1
- INFO: ssh root@192.168.1.2
- INFO: ssh root@192.168.1.2
-
-
-Then copy snapshot zipped dpdk source code to DUT.
-
-.. code-block:: console
-
- DTS_DUT_CMD: scp dep/dpdk.tar.gz root@192.168.1.1:
-
-Collect CPU core and network device information of DUT and tester.
-
-Automatically detect the network topology of DUT and tester.
-
-.. code-block:: console
-
- DTS_TESTER_RESULT: DUT PORT MAP: [4, 5, 6, 7]
-
-Build dpdk source code and then setup the running environment.
-
-.. code-block:: console
-
- DTS_DUT_CMD: make -j install T=x86_64-native-linuxapp-gcc
- DTS_DUT_CMD: awk '/Hugepagesize/ {print $2}' /proc/meminfo
- DTS_DUT_CMD: awk '/HugePages_Total/ { print $2 }' /proc/meminfo
- DTS_DUT_CMD: umount `awk '/hugetlbfs/ { print $2 }' /proc/mounts`
- DTS_DUT_CMD: mkdir -p /mnt/huge
- DTS_DUT_CMD: mount -t hugetlbfs nodev /mnt/huge
- DTS_DUT_CMD: modprobe uio
- DTS_DUT_CMD: rmmod -f igb_uio
- DTS_DUT_CMD: insmod ./x86_64-native-linuxapp-gcc/kmod/igb_uio.ko
- DTS_DUT_CMD: lsmod | grep igb_uio
- DTS_DUT_CMD: usertools/dpdk_nic_bind.py --bind=igb_uio 08:00.0 08:00.1 0a:00.0 0a:00.1
-
-Begin the validation process of test suite.
-
-.. code-block:: console
-
- TEST SUITE : TestCmdline
- INFO: NIC : niantic
- SUITE_DUT_CMD: make -j -C examples/cmdline
- SUITE_DUT_CMD: ./examples/cmdline/build/app/cmdline -n 1 -c 0x2
- INFO: Test Case test_cmdline_sample_commands Begin
-
-
-Clean-up DUT and tester after all validation finished.
-
-.. code-block:: console
-
- DTS_DUT_CMD: rmmod igb_uio
- DTS_DUT_CMD: modprobe igb
- DTS_DUT_CMD: modprobe ixgbe
- DTS_DUT_CMD: modprobe e1000e
- DTS_DUT_CMD: modprobe e1000
- DTS_DUT_CMD: modprobe virtio_net
- DTS_TESTER_CMD: rmmod igb_uio
- DTS_TESTER_CMD: modprobe igb
- DTS_TESTER_CMD: modprobe ixgbe
- DTS_TESTER_CMD: modprobe e1000e
- DTS_TESTER_CMD: modprobe e1000
- DTS_TESTER_CMD: modprobe virtio_net
-
diff --git a/doc/dts_gsg/image/dts_result.png b/doc/dts_gsg/image/dts_result.png
index f39f5f8dc817066e3603c785f9d20ebe33bdce53..65e0ada586bfb5264eab02f7a6dedfe898e12849 100644
GIT binary patch
literal 10924
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
HZukEHHd%iB
literal 7885
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
Uy+P7iFyQ*7siv!1scakbAMi{ZPXGV_
diff --git a/doc/dts_gsg/index.rst b/doc/dts_gsg/index.rst
index 0c84f46..aab4411 100644
--- a/doc/dts_gsg/index.rst
+++ b/doc/dts_gsg/index.rst
@@ -28,6 +28,7 @@
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+=====================
Getting Started Guide
=====================
@@ -35,17 +36,5 @@ Getting Started Guide
:maxdepth: 2
:numbered:
- intro
- sys_reqs
- config
- review
- tutorial
- virtualization
- scenario
- multiple_vm
- pktgen_prog_guide
- migrate_from_etgen_to_pktgen
- trex
- trex_known_issue
- usage_of_create_eal_and_start_testpmd
- support_igb_uio
+ quick_start
+ usr_guide/index
diff --git a/doc/dts_gsg/intro.rst b/doc/dts_gsg/intro.rst
deleted file mode 100644
index e8753a0..0000000
--- a/doc/dts_gsg/intro.rst
+++ /dev/null
@@ -1,139 +0,0 @@
-Introduction
-============
-
-This document describes how to install and configure the Data Plane Development Kit Test Suite (DPDK Test Suite) in a Linux environment. Users can refer this document to enable this test infrastructure in their environment and don’t need go deeply with too much details about this framework.
-DPDK Test Suite is an automation test tool for DPDK software, a python-base library. It can run on the tester machine, and communicate/manage DUT by SSH connection. DTF supports different kind of traffic generators, including DPDK-based PacketGen, third-party professional tester equipment (IXIA®).
-Data Plane Development Kit Test Suite (DPDK Test Suite) includes one set of test cases and DPDK generic test framework. DPDK Test Suite provides test example, references and framework for open source community. Based on DPDK Test Suite, everyone can develop their test plan, automation script and configuration for own features and platform. In addition, DPDK Test Suite provides a solution to allow that DPDK developers contribute their function test to certify their patch integration. It only requires limited effort to maintain test cases once merged into DPDK Test Suite. Everyone can utilize DPDK Test Suite to measure performance and functionality for features.
-
-Please see DPDK Test Suite architecture in the following figures:
-
-.. figure:: image/dts_soft_arch.png
-
-As generic test framework, DPDK Test Suite provides the following functions:
-
-* Able to work with DUT (Device Under Test), which installed Fedora, Ubuntu, WindRiver, FreeBSD, RedHat and SUSE.
-* Support virtualization hypervisors like Xen and Qemu.
-* Support both software and hardware traffic generators, including Scapy, DPDK-based PacketGen and IXIA traffic generator, even third party packet generator via TCL or Python library.
-* Provide configure files to customize test suite and test cases to run under DUT.
-* Provide debug and log functionalities for tracking test cases execution process.
-* Support to output test result by excel, log text file, etc.
-* DPDK Test Suite provides one set of basic library to manage tester, DUT, test case, exception, generate report, and configure test plan by user configure files. It’s easy to develop user-defined test suite and test plan by self, and these test cases are able to integrate into DPDK Test Suite.
-* With this test framework, user can automatically identify network topology, and easy to configure/deploy environment for DUT and tester, and provides flexibility to scale test capability by configuration.
-
-DPDK Test Suite environment includes DUT (Device under Test), Tester and packet generator. DPDK software will deployed and run on DUT. DPDK Test Suite should run on the Tester.
-
-Please see architecture in the following figures:
-
-
-.. figure:: image/dts_network_arch.png
-
-This architecture provides automatically mechanism to manage tester, DUT and packet generators, and remove dependency between test script and test environment/hardware. It defines one abstraction layer for DPDK Test Suite, and provides extensibility to add more test script.
-In the DPDK Test Suite Test Framework, it provides the following modules to help to manage device, platform, configure and test results.
-
-.. table::
-
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | File Name | Description |
- +=======================+==============================================================================================================================================================+
- | dts.py | Main Application for DPDK Test Suite |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | main.py | Test script to parse input parameter |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | dut.py | Setup device under test including tool chain, IP address |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | tester.py | Provide API to setup tester environment including IP, port, etc. |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | project_dpdk.py | Provide running environment for DPDK. |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | exception.py | Manage User-defined exceptions used across the framework |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | test_cases.py | Provide a base class for creating DPDK Test Suite test cases |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | logger.py | Deal with different log files to record event or message |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | serializer.py | Provide wrapper class to manage temporary variables during execution |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | settings.py | Setting for default network card and its identifiers supported by the framework |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | utils.py | Provide shared simple functions like IP address conversion and mask creation |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | ssh_connection.py | Create session to host, implement send_expect and copy function |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | ssh_pexpect.py | Handle ssh sessions between tester and DUT, Implement send_expect function to send command and get output data, Also support transfer files to tester or DUT |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | pmd_output.py | Module for get all statics value by port in testpmd |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | rst.py | Generate Rst Test Result Report |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | stats_reporter.py | Simple text file statistics generator |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | test_result.py | Generic result container. Useful to store/retrieve results during a DTF execution |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | excel_reporter.py | Excel spreadsheet generator |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | plotgraph.py | Generate graphs for each test suite |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | plotting.py | Generate Plots for performance test results |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | etgen.py | Software packet generator |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | ixia_buffer_parser.py | Helper class that parses a list of files containing IXIA captured frames extracting a sequential number on them |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | ixiaDCB.tcl | Third party Library which provided by IXIA, used to configure IXIA tester |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | ixiaPing6.tcl | Third party Library which provided by IXIA, used to ping IXIA tester |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | IxiaWish.tcl | Third party Library which provided by IXIA, set up TCL environment to use correct multiversion-compatible applications |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | texttable.py | Third party Library , create simple ASCII tables |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | qemu_kvm.py | Provide functionality for management and monitoring QEMU hypervisor |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | qemu_libvirt.py | Provide functionality for usage of libvirt library |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | virt_base.py | Base class for virtual machine, supply basic management functions |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | virt_dut.py | Generate instance for virtual machine, usage model is like DUT |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | virt_resource.py | Provide resource management for virtual machine |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | virt_scene.py | Generate virtualization scenario based on configuration file |
- +-----------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
-
-Beside Framework tool, DPDK Test Suite also defines one set of test cases. It includes basic test suite to verify basic functionality of DPDK library. These test script provides example and reference. Everyone can develop their test cases, verify their features functionality, and commit generic test report to maintainer. However, user-defined test cases, test plans and scripts must follow DPDK Test Suite standard including code standard, naming conventions, configure format, rst test plan, API.
-
-Please see test cases, which are included in the DPDK compliance test suites:
-
-.. table::
-
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | Test Suite | Descriptions |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | Command line | Define a demo example of command line interface in RTE |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | hello_world | Print a ``helloworld`` message on every enabled logic core. |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | Multi process | Demonstrates the basics of sharing information between DPDK processes. |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | Timer | Shows how timer can be used in a RTE application. |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | Blocklist/AllowList | Tests Allowlist/Blocklist Features by Poll Mode Drivers. |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | checksum_offload | Tests RX/TX L3/L4 Checksum offload features by Poll Mode Drivers |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | jumbo_frame | Tests jumbo frames features by Poll Mode Drivers |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | testpmd | Provides benchmark tests for the Intel Ethernet Controller (Niantic) Poll Mode Driver. |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | l2fwd | Provides a basic packet processing application using DPDK. It is a layer-2 (L2) forwarding application which takes traffic from a single RX port and transmits it with few modification on a single TX port. |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | L3fwd | Verifies Layer-3 Forwarding results using ``l3fwd`` application. |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | IP fragment | Verifies IPv4 fragmentation using ``ipv4_frag`` application. |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | Flow direction | Verifies the Flow Director feature of the Intel 82599 10GbE Ethernet Controller |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | link_flowctrl | Verifies Ethernet Link Flow Control Features by Poll Mode Drivers |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
- | ieee1588 | Tests the IEEE1588 Precise Time Protocol offload supported in Poll Mode Drivers. |
- +---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
diff --git a/doc/dts_gsg/migrate_from_etgen_to_pktgen.rst b/doc/dts_gsg/migrate_from_etgen_to_pktgen.rst
deleted file mode 100644
index e08d00b..0000000
--- a/doc/dts_gsg/migrate_from_etgen_to_pktgen.rst
+++ /dev/null
@@ -1,229 +0,0 @@
-
-======================
-Etgen to Pktgen Guides
-======================
-
-If you are working on etgen, and this document can help you to update your
-test suites to pktgen rapidly. Etgen is not under maitenance, and it will
-be removed from DTS some days.
-
-pktgen usage please refer to doc `pktgen_prog_guide <pktgen_prog_guide.html>`__.
-
-import new class
-----------------
-
-#. import a new module:
-
-.. code-block:: python
-
- from pktgen import PacketGeneratorHelper
-
-initialize an instance in `def set_up_all(self)`
-------------------------------------------------
-
-.. code-block:: python
-
- def set_up_all(self):
- ...
- self.pktgen_helper = PacketGeneratorHelper()
-
-create streams for pktgen instance
-----------------------------------
-each pcap file should only contain one packet.
-
-.. code-block:: python
-
- pcap1 = os.sep.join([self.pktgen.output_path, "{0}.pcap".format(port)])
- flow1 = "Ether()/IP()/UDP()/("X")"
- self.tester.scapy_append('wrpcap("%s", [flow])' % (pcap1, flow1))
- self.tester.scapy_execute()
-
- pcap2 = os.sep.join([self.pktgen.output_path, "{0}.pcap".format(port)])
- flow2 = "Ether()/IP()/UDP()/("X")"
- self.tester.scapy_append('wrpcap("%s", [flow])' % (pcap2, flow2))
- self.tester.scapy_execute()
-
- tgen_input = []
- tgen_input.append([tx_port, rx_port, pcap1])
- tgen_input.append([tx_port, rx_port, pcap2])
-
-pcap field variable(optional)
------------------------------
-If no protocol layer field vary requirement, ignore this content.
-
-field key definition
-~~~~~~~~~~~~~~~~~~~~
-
-#. ip protocol layer:
-
-.. code-block:: python
-
- # protocol layer name
- 'mac': {
- # field name
- 'src': {
- # field value vary range
- 'range': 64,
- # field value vary step
- 'step': 1,
- # action: inc/dec/random
- 'action': 'inc'},
- 'dst': {'range': 64, 'step': 1, 'action': 'inc'},
- }
-
-#. mac protocol layer:
-
-.. code-block:: python
-
- # protocol layer name
- 'mac': {
- # field name
- 'src': {
- # field value vary range
- 'range': 64,
- # field value vary step
- 'step': 1,
- # action: inc/dec/random
- 'action': 'inc'},
- 'dst': {'range': 64, 'step': 1, 'action': 'inc'},
- }
-
-#. vlan protocol layer:
-
-.. code-block:: python
-
- # protocol layer name
- 'vlan': {
- '0': {
- # field value vary range
- 'range': 64,
- # field value vary step
- 'step': 1,
- # action: inc/dec/random
- 'action': 'inc'},
- }
-
-usage example
-~~~~~~~~~~~~~
-
-.. code-block:: python
-
- def set_up_all(self):
- ...
- self.pktgen_helper = PacketGeneratorHelper()
- ...
-
- def set_fields(self):
- fields_config = {
- 'ip': {
- 'src': {'range': 64, 'action': 'inc'},
- 'dst': {'action': 'random'}},}
- return fields_config
-
- def test_perf_xxxx(self):
- ...
- vm_config= self.set_fields() # optional
- # clear streams before add new streams
- self.tester.pktgen.clear_streams()
- # run packet generator
- ratePercent = 100
- streams = self.pktgen_helper.prepare_stream_from_tginput(
- tgenInput, ratePercent, vm_config, self.tester.pktgen)
- _, pps = self.tester.pktgen.measure_throughput(stream_ids=streams)
- ...
-
-change etgen interface to pktgen interface
-------------------------------------------
-pktgen interface use the same input parameter/return value definition as
-etgen interface.
-
-throughput
-~~~~~~~~~~
-
-etgen:
-
-.. code-block:: python
-
- self.tester.traffic_generator_throughput(tgen_input)
-
-pktgen:
-
-.. code-block:: python
-
- vm_config= self.set_fields() # optional
- # clear streams before add new streams
- self.tester.pktgen.clear_streams()
- # run packet generator
- ratePercent = 100
- streams = self.pktgen_helper.prepare_stream_from_tginput(
- tgenInput, ratePercent, vm_config, self.tester.pktgen)
- _, pps = self.tester.pktgen.measure_throughput(stream_ids=streams)
-
-loss
-~~~~
-
-etgen:
-
-.. code-block:: python
-
- self.tester.traffic_generator_loss(tgen_input)
-
-pktgen:
-
-.. code-block:: python
-
- vm_config= self.set_fields() # optional
- # clear streams before add new streams
- self.tester.pktgen.clear_streams()
- # run packet generator
- ratePercent = 100
- streams = self.pktgen_helper.prepare_stream_from_tginput(
- tgenInput, ratePercent, vm_config, self.tester.pktgen)
- result = self.tester.pktgen.measure_loss(stream_ids=streams)
-
-latency
-~~~~~~~
-
-etgen:
-
-.. code-block:: python
-
- self.tester.traffic_generator_latency(tgen_input)
-
-pktgen:
-
-.. code-block:: python
-
- vm_config= self.set_fields() # optional
- # clear streams before add new streams
- self.tester.pktgen.clear_streams()
- # run packet generator
- ratePercent = 100
- streams = self.pktgen_helper.prepare_stream_from_tginput(
- tgenInput, ratePercent, vm_config, self.tester.pktgen)
- latencys = self.tester.pktgen.measure_latency(stream_ids=streams)
-
-rfc2544
-~~~~~~~
-
-etgen:
-
-.. code-block:: python
-
- self.tester.run_rfc2544(tgen_input)
-
-pktgen:
-
-.. code-block:: python
-
- vm_config= self.set_fields() # optional
- # clear streams before add new streams
- self.tester.pktgen.clear_streams()
- # run packet generator
- ratePercent = 100
- streams = self.pktgen_helper.prepare_stream_from_tginput(
- tgenInput, ratePercent, vm_config, self.tester.pktgen)
- # set traffic option
- traffic_opt = {'pdr': 0.01, 'duration': 5}
- zero_loss_rate, tx_pkts, rx_pkts = \
- self.tester.pktgen.measure_rfc2544(stream_ids=streams, options=traffic_opt)
diff --git a/doc/dts_gsg/multiple_vm.rst b/doc/dts_gsg/multiple_vm.rst
deleted file mode 100644
index 07dd44f..0000000
--- a/doc/dts_gsg/multiple_vm.rst
+++ /dev/null
@@ -1,87 +0,0 @@
-Multiple Virtual Machines Management
-====================================
-
-When managing multiple virtual machines, waiting around 2 minutes for each VM will be exhausted. So DTS imported parallel threads model into multiple VMs management scenario.
-
-.. note::
- Critical resources and actions which can't be handled in parallel have been protected by function level lock.
-
-Command arguments
------------------
-
-Multiple VMs module support start VMs or send commands to VMs in parallel with specified arguments format.
-
-Arguments for "start" command:
-
-.. table::
-
- +-----------------+----------------------------------+----------------+-------------+
- | name | Description | Default value | Must have |
- | | | | |
- +-----------------+----------------------------------+----------------+-------------+
- | name | virtual machine name | N/A | Yes |
- +-----------------+----------------------------------+----------------+-------------+
- | dut_id | index of DUT | 0 | No |
- +-----------------+----------------------------------+----------------+-------------+
- | autodetect_topo | whether detect network topology | False | No |
- | | automatically | | |
- +-----------------+----------------------------------+----------------+-------------+
- | virt_config | virtual machine config location | N/A | Alternative |
- +-----------------+----------------------------------+----------------+-------------+
- | virt_params | local parameters of virtual | N/A | Alternative |
- | | machine | | |
- +-----------------+----------------------------------+----------------+-------------+
-
-Arguments for "cmd" command:
-
-.. table::
-
- +-----------------+----------------------------------+----------------+-------------+
- | name | Description | Default value | Must have |
- | | | | |
- +-----------------+----------------------------------+----------------+-------------+
- | name | virtual machine name | N/A | Yes |
- +-----------------+----------------------------------+----------------+-------------+
- | dut_id | index of DUT | 0 | No |
- +-----------------+----------------------------------+----------------+-------------+
- | commands | list of commands which will be | N/A | Yes |
- | | sent into the vitual machine | | |
- +-----------------+----------------------------------+----------------+-------------+
- | expects | list of expect output of the | N/A | Yes |
- | | commands | | |
- +-----------------+----------------------------------+----------------+-------------+
- | timeouts | list of timeout value of the | N/A | Yes |
- | | commands | | |
- +-----------------+----------------------------------+----------------+-------------+
-
-.. note::
- If there's nothing expected for the command, still need to define expected string as blank
-
-Multiple module will catagorize and save the result value after all tasks have been done. Later users can retrieve the result by function get_parallel_result.
-
-Sample Code
------------
-
-.. code-block:: console
-
- vm_task = MultipleVM(max_vm=self.VM_NUM, duts=self.duts)
-
- for dut_id in range(len(self.duts)):
- for vm_idx in range(VM_NUM):
- vm_name = "vm%d" % vm_idx
- args = {'name': vm_name,
- 'dut_id': dut_id,
- 'autodetect_topo': False,
- 'virt_params': {
- 'qemu': [{'path': '/usr/local/bin/qemu-system-x86_64'}],
- 'cpu': [{'model': 'host', 'number': '1', 'cpupin': ''}],
- 'mem': [{'size': '1024', 'hugepage': 'yes'}],
- 'disk': [{'file': '/storage/vm-image/%s.qcow2' % vm_name}],
- 'login': [{'user': 'root', 'password': 'root'}],
- 'device': None}
- }
-
- vm_task.add_parallel_task(action="start", config=args)
-
- vm_task.do_parallel_task()
- print vm_task.get_parallel_result()
diff --git a/doc/dts_gsg/pktgen_prog_guide.rst b/doc/dts_gsg/pktgen_prog_guide.rst
deleted file mode 100644
index 26ba56a..0000000
--- a/doc/dts_gsg/pktgen_prog_guide.rst
+++ /dev/null
@@ -1,584 +0,0 @@
-
-===================
-Pktgen How-to Guide
-===================
-
-The old module *etgen* is only support hardward packet generator `Ixia Explorer`
-which is not friendly for users to get. So DTS community refined DTS framework to
-support another software packet generator `Trex` which is an open source project,
-and user can get it easily.
-
-these definition and usage pattern come from doc `pktgen-API-1.1.docx` and etgen
-usage in dts. For trex(CISCO) rapid iterative development speed, we lack of
-adequate manpower to keep up with it. Here we recommend to use trex v2.41/v2.42/v2.43
-to run pktgen/trex.
-
-add stream
-==========
-add stream in pktgen streams table.
-
-one stream content including::
-
- tx_port: transmit port idx in tester.ports_info.
- rx_port: receive port idx in tester.ports_info.
- pcap: pcap file or Packet instance, Only support one packet in it.
-
-.. code-block:: python
-
- tx_port = self.tester.get_local_port(dut_port_index1)
- rx_port = self.tester.get_local_port(dut_port_index2)
-
- stream_id = hPktgen.add_stream(tx_port, rx_port, pcap)
-
-config stream
-=============
-configure a stream option.
-
-definition
-----------
-Currently pktgen support ethernet/ipv4/vlan protocol layer some field vary with
-increase/decrease/random value.
-
-stream option contain::
-
- 'pcap': network packet format
- 'fields_config': protocol layer field behavior(optional)
- 'stream_config': stream transmit behavior
- 'flow_control': port flow control(optional)
-
-pcap
-++++
-It is a network packet format. It can be a absolute path of pcap file or
-an instance of scapy Packet. It should only contain one packet format.
-
-.. code-block:: python
-
- Example 1:
-
- pcap = <Ether dst=FF:FF:FF:FF:FF:FF src=00:00:00:00:00:00 type=IPv4 |<IP frag=0 proto=udp src=0.0.0.1 dst=0.0.0.255 |<UDP sport=22 dport=50 |<Raw load='xxxxxxxxxxxxxxxxxx' |>>>>
-
- Example 2:
-
- pcap = "/root/xxx.pcap"
-
-field option
-++++++++++++
-define every layer's field behavior.
-
-'mac'
-`````
-'mac' is ethernet protocol layer name.
-
-.. code-block:: python
-
- # field name
- 'src': {
- # action: inc/dec/random
- 'action':'inc',
- # field end value should be bigger than field start value
- 'end': '00:00:00:00:00:FF',
- # field start value
- 'start': '00:00:00:00:00:02',
- # field value vary step
- 'step': 1},
- 'dst': {
- # action: inc/dec/random
- 'action':'inc',
- # field end value should be bigger than field start value
- 'end': 'ff:00:00:00:00:FF',
- # field start value
- 'start': 'ff:00:00:00:00:02',
- # field value vary step
- 'step': 1},
-
-'ip'
-````
-'ip' is ip protocol layer name.
-
-.. code-block:: python
-
- # field name
- 'src': {
- # action: inc/dec/random
- 'action': 'inc',
- # field end value should be bigger than field start value
- 'end': '16.0.0.16',
- # field start value
- 'start': '16.0.0.1',
- # field value vary step
- 'step': 1},
- # field name
- 'dst': {
- # action: inc/dec/random
- 'action': 'inc',
- # field end value should be bigger than field start value
- 'end': '48.0.0.255',
- # field start value
- 'start': '48.0.0.1',
- # field value vary step
- 'step': 1},
-
-'vlan'
-``````
-'vlan' is vlan protocol layer name.
-
-.. code-block:: python
-
- # internal vlan
- 0: {
- # action: inc/dec/random
- 'action': 'inc',
- # field end value should be bigger than field start value
- 'end': 52,
- # field start value
- 'start': 50,
- # field value vary step
- 'step': 1},
- # external vlan
- 1: {
- # action: inc/dec/random
- 'action': 'inc',
- # field end value should be bigger than field start value
- 'end': 52,
- # field start value
- 'start': 50,
- # field value vary step
- 'step': 1},
-
-'stream_config'
-+++++++++++++++
-define a stream transmit behavior.
-
-basic content including::
-
- 'rate': 0 ~ 100 int type, port line rate should set it.
- 'transmit_mode': TRANSMIT_CONT/TRANSMIT_S_BURST
- TRANSMIT_CONT define a continuous transmit.
- TRANSMIT_S_BURST define a burst transmit with custom number of packets.
-
-.. code-block:: python
-
- from pktgen_base import TRANSMIT_CONT, TRANSMIT_S_BURST
-
- stream_config = {
- 'rate': 100,
- # TRANSMIT_CONT define a continuous transmit.
- # TRANSMIT_S_BURST define a burst transmit with custom number of packets.
- 'transmit_mode': TRANSMIT_CONT
- }
-
-stream option examples
-----------------------
-
-normal stream option
-++++++++++++++++++++
-normal stream ignore `fields_config` configuration option.
-
-.. code-block:: python
-
- Example 1:
- option = {
- 'pcap': "/root/xxx.pcap",
- 'stream_config': {
- 'rate': 100,
- 'transmit_mode': TRANSMIT_CONT}}
-
- Example 2:
- option = {
- 'pcap': <Ether dst=00:00:00:00:20:00 src=00:00:00:00:00:FF type=IPv4 |<IP frag=0 proto=udp src=0.0.0.1 dst=0.0.0.255 |<UDP sport=22 dport=50 |<Raw load='xxxxxxxxxxxxxxxxxx' |>>>>,
- 'stream_config': {
- 'rate': 100,
- 'transmit_mode': TRANSMIT_CONT}}
-
-stream option with mac increase/decrease/random
-+++++++++++++++++++++++++++++++++++++++++++++++
-
-.. code-block:: python
-
- action = 'inc' or 'dec' or 'random'
- option = {
- 'pcap': "/root/xxx.pcap",
- 'fields_config': {
- 'mac': {
- 'dst': {
- 'action': action,
- 'end': '00:00:00:00:20:00',
- 'start': '00:00:00:00:00:FF',
- 'step': 1},
- 'src': {
- 'action': action,
- 'end': '00:00:00:00:00:FF',
- 'start': '00:00:00:00:00:02',
- 'step': 1}}},
- 'stream_config': {
- 'rate': 100,
- 'transmit_mode': TRANSMIT_CONT
- }
- }
-
-stream option with ip increase/decrease/random
-++++++++++++++++++++++++++++++++++++++++++++++
-
-.. code-block:: python
-
- action = 'inc' or 'dec' or 'random'
- option = {
- 'pcap': "/root/xxx.pcap",
- 'fields_config': {
- 'ip': {
- 'dst': {
- 'action': action,
- 'end': '48.0.0.255',
- 'start': '48.0.0.1',
- 'step': 1},
- 'src': {
- 'action': action,
- 'end': '16.0.0.16',
- 'start': '16.0.0.1',
- 'step': 1}}},
- 'stream_config': {
- 'rate': 100,
- 'transmit_mode': TRANSMIT_CONT,
- }
- }
-
-stream option with vlan increase/decrease/random
-++++++++++++++++++++++++++++++++++++++++++++++++
-
-.. code-block:: python
-
- action = 'inc' or 'dec' or 'random'
- option = {
- 'pcap': "/root/xxx.pcap",
- 'fields_config': {
- 'ip': {
- 0: {
- 'action': action,
- 'end': 55,
- 'start': 50,
- 'step': 1},
- 'stream_config': {
- 'rate': 100,
- 'transmit_mode': TRANSMIT_CONT,
- }
- }
-
-burst stream option
-+++++++++++++++++++
-
-.. code-block:: python
-
- option = {
- 'pcap': "/root/xxx.pcap",
- 'stream_config': {
- 'rate': 100,
- # set stream transmit mode
- 'transmit_mode': TRANSMIT_S_BURST,
- 'txmode' : {
- # total packets
- 'total_pkts': 1000},
- }
- }
-
-stream option with flow control
-+++++++++++++++++++++++++++++++
-flow control open (trex not supported)
-
-.. code-block:: python
-
- option = {
- 'flow_control': {
- # 0: disable flow control
- # 1: enable flow control
- 'flag': 1},
- 'pcap': "/root/xxx.pcap",
- 'stream_config': {
- 'rate': 100,
- 'transmit_mode': TRANSMIT_CONT}}
-
-measure
-=======
-pktgen measure_xxxx return value is the same as etgen, `measure_xxxx` and
-`measure` are both supported. If traffic option is not set, use default values.
-
-two usage examples of pktgen measure method
--------------------------------------------
-
-.. code-block:: python
-
- Example 1:
-
- from pktgen import getPacketGenerator, PKTGEN_TREX
-
- hPktgen = getPacketGenerator(tester, PKTGEN_TREX)
-
- traffic_option = {'rate': 100}
- hPktgen.measure_throughput(stream_ids, traffic_opt)
-
- Example 2:
-
- from pktgen import getPacketGenerator, PKTGEN_TREX
-
- hPktgen = getPacketGenerator(tester, PKTGEN_TREX)
-
- traffic_option = {
- 'method': 'throughput',
- 'rate': 100
- }
- hPktgen.measure(stream_ids, traffic_opt)
-
-throughput
-----------
-throughput testing scenario.
-
-option
-++++++
-.. code-block:: python
-
- traffic_option = {
- # test method name, if use `measure_throughput`, ignore this key
- 'method': 'throughput',
- # port rate percent, float(0--100), default value is 100.(reserved)
- 'rate': 100,
- # warm up time before start main transmission. If it is set, it will start
- # a custom time transmission to make sure packet generator under good
- # status. It is an optional key.
- 'delay': 5,
- # the interval time of get throughput statistic (second).
- # If set this key value, pktgen will return several throughput statistic
- # data in a duration. If not set this key value, only return one statistic
- # data. It is used coupled with `duration` option.
- 'interval': 1,
- # this key works with ``interval`` key. If it is set, the callback
- # of suite level will be executed after getting throughput statistic.
- # callback method should define as below, don't add sleep in this method.
- 'callback' : callback_method,
- # transmission lasting time(second), default value is 10 second.
- 'duration': 5}
-
-return value
-++++++++++++
-bps_rx_total: Received bits per second
-pps_rx_total: Received packets per second
-
-.. code-block:: python
-
- return_value = (bps_rx_total, pps_rx_total)
-
-loss
-----
-loss rate testing scenario.
-
-option
-++++++
-
-.. code-block:: python
-
- traffic_option = {
- # test method name, if use `measure_loss`, ignore this key
- 'method': 'loss',
- # port rate percent, float(0--100), default value is 100.(reserved)
- 'rate': 100,
- # warm up time before start main transmission. If it is set, it will start
- # a custom time transmission to make sure packet generator under good
- # status. It is an optional key.
- 'delay': 5,
- # transmission lasting time(second), default value is 10 second.
- 'duration': 5}
-
-return value
-++++++++++++
-
-.. code-block:: python
-
- loss_stats = (loss_rate, tx_pkts, rx_pkts)
-
-latency
--------
-latency testing scenario.
-
-option
-++++++
-
-.. code-block:: python
-
- traffic_option = {
- # test method name, if use `measure_latency`, ignore this key
- 'method': 'latency',
- # port rate percent, float(0--100), default value is 100.(reserved)
- 'rate': 100,
- # warm up time before start main transmission. If it is set, it will start
- # a custom time transmission to make sure packet generator under ready
- # status. It is an optional key.
- 'delay': 5,
- # transmission lasting time(second), default value is 10 second.
- 'duration': 5}
-
-return value
-++++++++++++
-
-.. code-block:: python
-
- latency_stats = { 'min': 15,
- 'max': 15,
- 'average': 15,}
-
-rfc2544 option
---------------
-rfc2544 testing scenario by decreasing step.
-
-option
-++++++
-
-.. code-block:: python
-
- traffic_option = {
- # test method name, if use `measure_rfc2544`, ignore this key.
- 'method': 'rfc2544',
- # port rate percent at first round testing, 0 ~ 100, default is 100.
- 'rate': 100,
- # permit packet drop rate, default is 0.001.
- 'pdr': 0.001,
- # port rate percent drop step, 0 ~ 100 , default is 1.
- 'drop_step': 1,
- # warm up time before start main transmission. If it is set, it will start
- # a custom time transmission to make sure packet generator under ready
- # status. It is an optional key.
- 'delay': 5,
- # transmission lasting time(second), default value is 10 second.
- 'duration': 5}
-
-return value
-++++++++++++
-
-.. code-block:: python
-
- loss_stats = (loss_rate, tx_pkts, rx_pkts)
-
-rfc2544_dichotomy option
-------------------------
-rfc2544 testing scenario using dichotomy algorithm.
-
-option
-++++++
-
-.. code-block:: python
-
- traffic_option = {
- # test method name, if use `measure_rfc2544_dichotomy` method, ignore this key.
- 'method': 'rfc2544_dichotomy',
- # dichotomy algorithm lower bound rate percent, default is 0.
- 'min_rate': 0,
- # dichotomy algorithm upper bound rate percent, default is 100.
- 'max_rate': 100,
- # dichotomy algorithm accuracy, default 0.001.
- 'accuracy': 0.001,
- # permit packet drop rate, default is 0.001.
- 'pdr': 0.001,
- # warm up time before start main transmission. If it is set, it will start
- # a custom time transmission to make sure packet generator under ready
- # status. It is an optional key.
- 'delay': 5,
- # transmission lasting time(second), default value is 10 second.
- 'duration': 10}
-
-return value
-++++++++++++
-
-.. code-block:: python
-
- loss_stats = (loss_rate, tx_pkts, rx_pkts)
-
-
-reference example
-=================
-This example show how to use pktgen in suite script. In fact, most scenario are
-more simpler than this. Part of code is pseudo code and it can't be ran directly.
-
-testing scenario::
-
- create four streams on two links, each link attach two streams. On one link,
- one stream set mac src increase and packet format is a pcap file, the other
- stream set ip src random / dst decrease and packet format is a scapy Packet
- instance. All streams use continuous transmit and run rfc2544 scenario using
- trex packet generator.
-
-.. code-block:: python
-
- # import pktgen lib
- from pktgen import getPacketGenerator, PKTGEN_TREX, TRANSMIT_CONT
-
- # create a pktgen instance
- hPktgen = getPacketGenerator(tester, PKTGEN_TREX)
-
- # create packet
- pcap1 = <Ether dst=FF:FF:FF:FF:FF:FF src=00:00:00:00:00:00 type=IPv4 |<IP frag=0 proto=udp src=0.0.0.1 dst=0.0.0.255 |<UDP sport=22 dport=50 |<Raw load='xxxxxxxxxxxxxxxxxx' |>>>>
- pcap2 = "/root/xxx.pcap"
-
- # attach stream to pktgen
- stream_ids = []
- tx_port1 = self.tester.get_local_port(dut_port_index1)
- rx_port1 = self.tester.get_local_port(dut_port_index2)
- stream_id_1 = hPktgen.add_stream(tx_port1, rx_port1, pcap1)
- stream_id_2 = hPktgen.add_stream(tx_port1, rx_port1, pcap2)
- stream_ids.append(stream_id_1)
- stream_ids.append(stream_id_2)
-
- tx_port2 = self.tester.get_local_port(dut_port_index2)
- rx_port2 = self.tester.get_local_port(dut_port_index1)
- stream_id_3 = hPktgen.add_stream(tx_port2, rx_port2, pcap1)
- stream_id_4 = hPktgen.add_stream(tx_port2, rx_port2, pcap2)
- stream_ids.append(stream_id_3)
- stream_ids.append(stream_id_4)
-
- # set pcap1 with mac protocol layer field vary configuration
- stream_option1 = {
- 'pcap': pcap1,
- 'fields_config': {
- 'mac': {
- 'src': {
- 'action': 'inc',
- 'end': '00:00:00:00:00:FF',
- 'start': '00:00:00:00:00:00',
- 'step': 1}}},
- 'stream_config': {
- 'rate': 100,
- 'transmit_mode': TRANSMIT_CONT
- }
- }
- # set stream option
- hPktgen.config_stream(stream_id_1, stream_option1)
- hPktgen.config_stream(stream_id_3, stream_option1)
-
- # set pcap2 with ip protocol layer field vary configuration
- stream_option2 = {
- 'pcap': pcap2,
- 'fields_config': {
- 'ip': {
- 'dst': {
- 'action': 'dec',
- 'end': '0.0.0.255',
- 'start': '0.0.0.1',
- 'step': 1},
- 'src': {
- 'action': 'random',
- 'end': '0.0.0.64',
- 'start': '0.0.0.1',
- 'step': 1}}},
- 'stream_config': {
- 'rate': 100,
- 'transmit_mode': TRANSMIT_CONT
- }
- }
- # set stream option
- hPktgen.config_stream(stream_id_2, stream_option2)
- hPktgen.config_stream(stream_id_4, stream_option2)
-
- # run testing scenario
- traffic_option = {
- 'method': 'rfc2544',
- 'rate': 100,
- 'pdr': 0.001,
- 'drop_step': 1}
-
- hPktgen.measure(stream_ids, traffic_opt)
diff --git a/doc/dts_gsg/quick_start.rst b/doc/dts_gsg/quick_start.rst
new file mode 100644
index 0000000..b26cf26
--- /dev/null
+++ b/doc/dts_gsg/quick_start.rst
@@ -0,0 +1,310 @@
+=================
+Quick start guide
+=================
+
+Introduction
+============
+
+This document describes how to install and configure the Data Plane Development Kit Test Suite (DTS) in a Linux environment.
+It is designed to get user to set up DTS quickly in their environment without going deeply into detail.
+
+DTS can run on a tester machine or a DUT machine or the third machine to communicate/manage tester/DUT by SSH connection.
+DTS supports different kinds of traffic generators, including Scapy, TRex, IXIA.
+The example set up DTS on as tester machine, and use Scapy as traffic generator to run functional testing.
+
+System Requirements
+===================
+
+This chapter describes the packages required to set up DTS.
+For the DPDK requirements, please consult `Data Plane Development Kit Getting Started Guide <http://dpdk.org/doc/guides>`_.
+
+Hardware Recommendation
+-----------------------
+
+Our regression setups uses Intel x86 platforms with mainstream Intel ethernet cards.
+The following platforms have been tested and are recommended.
+
+.. |reg| unicode:: U+000AE .. REGISTERED SIGN
+.. |trade| unicode:: U+2122 .. TRADE MARK SIGN
+
+* DTS and Tester system
+
+ * CPU
+ * Intel\ |reg| Xeon\ |reg| Platinum 8280M CPU @ 2.70GHz
+ * Intel\ |reg| Xeon\ |reg| Platinum 8180 CPU @ 2.50GHz
+ * Intel\ |reg| Xeon\ |reg| Gold 6252N CPU @ 2.30GHz
+
+ * OS
+ * Ubuntu 20.04
+ * Ubuntu 18.04
+
+* DUT system
+
+ * CPU
+
+ * Intel\ |reg| Atom\ |trade| CPU C3758 @ 2.20GHz
+ * Intel\ |reg| Atom\ |trade| CPU C3858 @ 2.00GHz
+ * Intel\ |reg| Atom\ |trade| CPU C3958 @ 2.00GHz
+ * Intel\ |reg| Xeon\ |reg| CPU D-1541 @ 2.10GHz
+ * Intel\ |reg| Xeon\ |reg| CPU D-1553N @ 2.30GHz
+ * Intel\ |reg| Xeon\ |reg| CPU E5-2680 0 @ 2.70GHz
+ * Intel\ |reg| Xeon\ |reg| CPU E5-2680 v2 @ 2.80GHz
+ * Intel\ |reg| Xeon\ |reg| CPU E5-2699 v3 @ 2.30GHz
+ * Intel\ |reg| Xeon\ |reg| CPU E5-2699 v4 @ 2.20GHz
+ * Intel\ |reg| Xeon\ |reg| Gold 5218N CPU @ 2.30GHz
+ * Intel\ |reg| Xeon\ |reg| Gold 6139 CPU @ 2.30GHz
+ * Intel\ |reg| Xeon\ |reg| Gold 6252N CPU @ 2.30GHz
+ * Intel\ |reg| Xeon\ |reg| Platinum 8180 CPU @ 2.50GHz
+ * Intel\ |reg| Xeon\ |reg| Platinum 8280M CPU @ 2.70GHz
+
+ * OS
+
+ * CentOS 8.3
+ * CentOS Stream 8
+ * Fedora 33
+ * Red Hat Enterprise Linux Server release 8.3
+ * Suse 15 SP2
+ * Ubuntu 20.04
+ * Ubuntu 20.10
+
+ * NICs
+
+ * Intel\ |reg| Ethernet Controller E810-C for SFP (4x25G)
+ * Intel\ |reg| Ethernet Controller E810-C for QSFP (2x100G)
+ * Intel\ |reg| Ethernet Converged Network Adapter X710-DA4 (4x10G)
+ * Intel\ |reg| Ethernet Converged Network Adapter XXV710-DA2 (2x25G)
+ * Intel\ |reg| 82599ES 10 Gigabit Ethernet Controller
+
+Topology Example
+----------------
+
+2 Teseter interfaces connect to 2 DUT interfaces back to back.
+
+Dependencies
+------------
+
+SSH Service
+~~~~~~~~~~~
+
+Tester and DUT should have one interface connected to the same internet, so that they can be accessed by each other from local IP address
+
+.. code-block:: console
+
+ apt-get install sshd # download / install ssh software
+ systemctl enable ssh # start ssh service
+
+.. note::
+
+ Firewall should be disabled that all packets can be accepted by NIC interfaces.
+
+.. code-block:: console
+
+ systemctl disable firewalld.service
+
+Python modules for DTS & Tester
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+The python dependences are recorded in requirements.txt.
+Please install them as the following:
+
+.. code-block:: console
+
+ apt-get install python3
+ python3 -m pip install requirements.txt
+
+BIOS setting for DUT
+~~~~~~~~~~~~~~~~~~~~
+
+DPDK prefer devices bound to ``vfio-pci`` kernel module, therefore, please enable VT-d and VT-x:
+
+.. code-block:: console
+
+ Advanced -> Integrated IO Configuration -> Intel(R) VT for Directed I/O <Enabled>
+ Advanced -> Processor Configuration -> Intel(R) Virtualization Technology <Enabled>
+
+DPDK running Prerequisite
+~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Recommend to use 1G Hugepage for DPDK running, add ``hugepagesz=1G hugepages=40 default_hugepagesz=1G`` in Linux cmdline.
+For more details, please refer to `Data Plane Development Kit Getting Started Guide <http://dpdk.org/doc/guides>`_.
+
+Running DTS
+===========
+
+Getting DTS Code
+----------------
+
+Get DTS code from remote repo.
+
+.. code-block:: console
+
+ [root@tester ~]# git clone http://dpdk.org/git/tools/dts
+ [root@tester ~]# ls dts
+ [root@tester dts]# conf CONTRIBUTING.TXT dep doc dts execution.cfg executions framework nics output requirements.txt test_plans tests tools version.py
+
+Preparing DPDK tarball
+----------------------
+
+DPDK source code should be packed as "dpdk.tar.gz" and moved into dts/dep:
+
+.. code-block:: console
+
+ tar -czvf dpdk.tar.gz dpdk
+ cp dpdk.tar.gz ~/dts/dep
+
+Configuring DTS
+---------------
+
+A few of files should be configured, including execution.cfg, conf/crbs, conf/ports.cfg.
+
+execution.cfg
+~~~~~~~~~~~~~
+
+.. code-block:: console
+
+ [Execution1]
+ crbs=192.168.1.1
+ drivername=vfio-pci
+ build_type=meson
+ test_suites=
+ hello_world,
+ targets=
+ x86_64-default-linuxapp-gcc,
+ parameters=nic_type=cfg:func=true
+
+* crbs: IP address of the DUT system
+* test_suites: a list of test suites to be executed
+
+conf/crbs.cfg
+~~~~~~~~~~~~~
+
+.. code-block:: console
+
+ [192.168.1.1]
+ dut_ip=192.168.1.1
+ dut_user=root
+ dut_passwd=dutpasswd
+ os=linux
+ tester_ip=192.168.1.2
+ tester_passwd=testerpasswd
+ channels=4
+ bypass_core0=True
+
+* dut_ip: IP address of the DUT system, same as crbs in execution.cfg
+* dut_user: User name of DUT linux account
+* dut_passwd: Password of DUT linux account
+* tester_ip: IP address of tester
+* tester_passwd: Password of Tester linux account, user name should same as dut_user
+
+conf/ports.cfg
+~~~~~~~~~~~~~~
+
+.. code-block:: console
+
+ [192.168.1.1]
+ ports =
+ pci=0000:06:00.0,peer=0000:81:00.0;
+ pci=0000:06:00.1,peer=0000:81:00.1;
+
+* [192.168.1.1]: same as crbs in execution.cfg and dut_ip in conf/crbs.cfg
+* pci: pci address of DUT port
+* peer: pci address of Tester port which connected to the DUT port whose pci is `pci`.
+
+The topology for the configuration is:
+
+.. code-block:: console
+
+ DUT port0 (0000:06:00.0) --- Tester port0 (0000:81:00.0)
+ DUT port0 (0000:06:00.1) --- Tester port0 (0000:81:00.1)
+
+Launch DTS
+----------
+
+As we have prepared the zipped dpdk file and configuration file, just type the followed command “./dts”, it will start the validation process.
+
+.. code-block:: console
+
+ [root@tester ~]# ./dts
+
+ dts:
+ DUT 192.168.1.1
+ tester: ssh root@192.168.1.2
+ tester: ssh root@192.168.1.2
+ tester: python3 -V
+ tester_scapy: ssh root@192.168.1.2
+ ...
+ dut.192.168.1.1: ssh root@192.168.1.1
+ dut.192.168.1.1: ssh root@192.168.1.1
+ ...
+ dut.192.168.1.1: scp -v dep/dpdk.tar.gz root@192.168.1.1:/tmp/
+ ...
+ dut.192.168.1.1: DUT PORT MAP: [0, 1]
+ ...
+ dut.192.168.1.1: export RTE_TARGET=x86_64-native-linuxapp-gcc
+ dut.192.168.1.1: export RTE_SDK=`pwd`
+ dut.192.168.1.1: rm -rf x86_64-native-linuxapp-gcc
+ dut.192.168.1.1: CC=gcc meson -Denable_kmods=True -Dlibdir=lib --default-library=static x86_64-native-linuxapp-gcc
+ ...
+ dut.192.168.1.1: usertools/dpdk-devbind.py --force --bind=vfio-pci 0000:af:00.0 0000:af:00.1
+ dts: NIC : fortville_25g
+ dut.192.168.1.1: meson configure -Dexamples=helloworld x86_64-native-linuxapp-gcc
+ dut.192.168.1.1: ninja -C x86_64-native-linuxapp-gcc
+ dut.192.168.1.1: ls x86_64-native-linuxapp-gcc/examples/dpdk-helloworld
+ TestHelloWorld: Test Case test_hello_world_all_cores Begin
+ dut.192.168.1.1: cat config/defconfig_x86_64-native-linuxapp-gcc | sed '/^#/d' | sed '/^\s*$/d'
+ dut.192.168.1.1: ./x86_64-native-linuxapp-gcc/examples/dpdk-helloworld -l 1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71 -n 4 --file-prefix=dpdk_25703_20210311003827
+ TestHelloWorld: Test Case test_hello_world_all_cores Result PASSED:
+ TestHelloWorld: Test Case test_hello_world_single_core Begin
+ dut.192.168.1.1: ./x86_64-native-linuxapp-gcc/examples/dpdk-helloworld -l 1 -n 4 --file-prefix=dpdk_25703_20210311003827
+ TestHelloWorld: Test Case test_hello_world_single_core Result PASSED:
+ dts:
+ TEST SUITE ENDED: TestHelloWorld
+ ...
+ dts: DTS ended
+ [root@tester ~]#
+
+Check Test Result
+==================
+
+The result files are generated in dts/output.
+
+.. code-block:: console
+
+ [root@tester output]# ls
+ rst_report dts.log statistics.txt TestHelloWorld.log test_results.json test_results.xls
+
+* statstics.txt: summary statistics
+
+.. code-block:: console
+
+ [root@tester output]# cat statistics.txt
+ dpdk_version = 21.02.0
+ Passed = 2
+ Failed = 0
+ Blocked = 0
+ Pass rate = 100.0
+
+* test_result.json: json format result file
+
+.. code-block:: console
+
+ [root@tester output]# cat result.json
+ {
+ "192.168.1.1": {
+ "dpdk_version": "21.02.0",
+ "nic": {
+ "driver": "vfio-pci",
+ "firmware": "8.00 0x80008c1a 1.2766.0",
+ "kdriver": "i40e-2.13.10",
+ "name": "fortville_25g"
+ },
+ "x86_64-native-linuxapp-gcc": {
+ "hello_world/test_hello_world_all_core": "passed"
+ "hello_world/test_hello_world_single_core": "passed"
+ }
+ }
+ }
+
+* test_result.xls: excel format result file
+
+.. figure:: image/dts_result.png
diff --git a/doc/dts_gsg/review.rst b/doc/dts_gsg/review.rst
deleted file mode 100644
index b48cd1d..0000000
--- a/doc/dts_gsg/review.rst
+++ /dev/null
@@ -1,104 +0,0 @@
-Review Test Result
-==================
-
-Browse the result files
------------------------
-After DPDK Test Suite finished the validation, we can find the result files as below in output folder. The files in output folder maybe different when change the CRB or choose different suites.
-
-For Example, You can find the following in output folder after execution.
-
-.. code-block:: console
-
- [root@tester output]# ls
- CrownPassCRB1 dts.log statistics.txt TestHelloWorld.log test_results.xls
-
-Please see details about these files:
-
-* CrownPassCRB1: contains the result RST file and graph of performance data
-* dts.log: Full execution log of DPDK Test Suite framework
-* statstics.txt: summary statistics of DPDK Test Suite executed suites
-* TestHelloWorld.log: log message of TestHelloWorld case
-* test_result.xls: excel format result file
-
-Check test result of DPDK Test Suite
-------------------------------------
-
-You can go through the summary of execution result via statistic.txt. This file includes the number of passed test cases, the number of failed case, the number of blocked and pass ratio.
-
-Please see example as the following. You can cat the sample file, then show this information of execution, totally executed two test cases, all cases passed the criterion and no failed or blocked cases.
-
-.. code-block:: console
-
- [root@tester output]# cat statistics.txt
- Passed = 2
- Failed = 0
- Blocked = 0
- Pass rate = 100.0
-
-If you need more detail information of test result, please open excel formatted file test_result.xls. This file contains of both detailed case information and case results. Also you can find description of the failure reason if DPDK Test Suite can track it.
-
-.. figure:: image/dts_result.png
-
-If you want to track more details about the process of each suite, please go to log file which named by this suite, all related information will stored in this file.
-
-DPDK Test Suite log module provides several levels to track event or output in log file. Every message level will have its own scopes. Separated log messages will help us get to known what happening in DPDK Test Suite and what happening in DUT and tester.
-
-
-.. table::
-
- +---------------------+---------------------------------------------------------------------------------------------+
- | Level | description |
- +---------------------+---------------------------------------------------------------------------------------------+
- | INFO | DPDK Test Suite system level log, show start and stop process in this suite |
- +---------------------+---------------------------------------------------------------------------------------------+
- | SUITE_DUT_CMD | Commands send to DUT CRB |
- +---------------------+---------------------------------------------------------------------------------------------+
- | SUITE_DUT_OUTPUT | Output after the send the commands to DUT |
- +---------------------+---------------------------------------------------------------------------------------------+
- | SUITE_TESTER_CMD | Commands send to tester, most of they are Scapy commands which will send packet to DUT port |
- +---------------------+---------------------------------------------------------------------------------------------+
- | SUITE_TESTER_OUTPUT | Output after the send the commands to tester |
- +---------------------+---------------------------------------------------------------------------------------------+
-
-
-Please see example for TestHelloWorld suite log as the following. This log file showed that application helloworld sent hello message from core1, and finally matched the pass criterion.
-
-.. code-block:: console
-
- 22/08/2014 11:04:45 INFO:
- TEST SUITE : TestHelloWorld
- 22/08/2014 11:04:45 INFO: NIC : niantic
- 22/08/2014 11:04:45 SUITE_DUT_CMD: make -j -C examples/helloworld
- 22/08/2014 11:04:45 SUITE_DUT_OUTPUT: make: Entering directory `/root/dpdk/examples/helloworld'^M
- CC main.o^M
- LD helloworld^M
- INSTALL-MAP helloworld.map^M
- INSTALL-APP helloworld^M
- make: Leaving directory `/root/dpdk/examples/helloworld'
- 22/08/2014 11:04:45 INFO: Test Case test_hello_world_single_core Begin
- 22/08/2014 11:04:45 SUITE_DUT_CMD: ./examples/helloworld/build/app/helloworld -n 1 -c 0x1fffffffff
- 22/08/2014 11:04:48 SUITE_DUT_OUTPUT: EAL: Detected lcore 0 as core 0 on socket 0^M
- …
- hello from core 1
- 22/08/2014 11:05:08 INFO: Test Case test_hello_world_single_core Result PASSED:
- 22/08/2014 11:05:09 SUITE_DUT_CMD: uname
- 22/08/2014 11:05:09 SUITE_DUT_OUTPUT:
- 22/08/2014 11:05:09 SUITE_TESTER_CMD: killall scapy 2>/dev/null; echo tester
- 22/08/2014 11:05:09 SUITE_TESTER_OUTPUT: tester
- 22/08/2014 11:05:10 SUITE_TESTER_CMD: uname
- 22/08/2014 11:05:10 SUITE_TESTER_OUTPUT:
- 22/08/2014 11:05:10 INFO:
- TEST SUITE ENDED: TestHelloWorld
-
-Generate PDF doc from RST
--------------------------
-
-Since DPDK Test Suite stores test result as RST by default, you may be want to transfer it to PDF formatted which make it more readable. Firstly, please enter the folder which contained the RST results, then use python tool ``rst2pdf`` to convert RST. If there’s no error return, you can find the pdf file generated with same name.
-
-.. code-block:: console
-
- [root@tester dts]# cd output/CrownPassCRB1/x86_64-native-linuxapp-gcc/Niantic
- [root@tester niantic]# rst2pdf TestResult_hello_world.rst
- [root@tester niantic]# ls
- TestResult_hello_world.pdf TestResult_hello_world.rst
-
diff --git a/doc/dts_gsg/scenario.rst b/doc/dts_gsg/scenario.rst
deleted file mode 100644
index c13fb89..0000000
--- a/doc/dts_gsg/scenario.rst
+++ /dev/null
@@ -1,152 +0,0 @@
-Virtualization Scenario
-=======================
-
-When enable virtualization scenario setting in execution cfg, DTS will load scenario configurations and prepare resource and devices for VMs. After VMs started, scenario module will prepare test suite running environment. After all suites finished, scenario module will stop VMs and then clean up the scene.
-
-Configuration File
-------------------
-
-With below configuration, DTS will create one scenario which created one VM with two VF devices attached. In scene section and according to configurations defined in suite. DUT object in suite will be VM DUT object, tester and DUT port network topology will be discovered automatically. Now DTS only support kvm typed hypervisor to create virtualization scenario.
-
-
-.. code-block:: console
-
- # vm configuration for vf passthrough cases
- # numa 0,1,yes yes mean cpu numa match the first port
- # skipcores list mean those core will not be used by vm
- # dut=vm_dut; mean vm_dut act as dut
- # dut=dut; mean host dut act as dut
- # portmap=cfg; mean vm_dut port map will be load from cfg
- # portmap=auto; mean vm_dut will create portmap automatically
- # devices = dev_gen/host/dev_gen+host not useful now
- [scene]
- suite =
- dut=vm_dut,portmap=auto;
- tester=tester;
- type=kvm;
-
-Virtual machine "vm0" section configured cpu, memory, disk and device settings in VM. As below configurations, VM will not use the first four lcores on DUT. DTS will generate two VF devices from first two host PF devices. These two VF devices will be pass-through into guest and their pci address will be auto assigned by qemu.
-
-.. code-block:: console
-
- [vm0]
- cpu =
- model=host,number=4,numa=auto,skipcores=0 1 2 3;
- mem =
- size=2048,hugepage=no;
- disk =
- file=/storage/vm-image/vm0.img;
- dev_gen =
- pf_idx=0,vf_num=1,driver=default;
- pf_idx=1,vf_num=1,driver=default;
- device =
- vf_idx=0,pf_dev=0,guestpci=auto;
- vf_idx=0,pf_dev=1,guestpci=auto;
- vnc =
- displayNum=1;
-
-All suites will be run in scenario like below picture.
-
-.. figure:: image/scene_pf_passthrough.svg
-
-Scenario Parameters
--------------------
-
-Options for suite:
-
-.. table::
-
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | option | Description | Options | Default value | Must have |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | dut | type of dut for dts suite | vm_dut,dut | dut | No |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | dut->portmap | method to generate dut port maps | auto, cfg | auto | No |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | tester | type of tester for dts suite[Not | N/A | N/A | No |
- | | used by now] | | | |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | type | type of hypervisor | kvm,libvirtd | kvm | No |
- +------------------+----------------------------------+-----------------+---------------+-----------+
-
-Options for cpu:
-
-.. table::
-
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | option | Description | Options | Default value | Must have |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | model | type of dut for dts suite | | host | Yes |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | number | number of cores in virtual | | 4 | Yes |
- | | machine | | | |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | numa_aware | numa id of cores allocated from | 0,1,auto | 0 | Yes |
- | | resource module | | | |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | skipcores | cores should not be used, most | | | No |
- | | time for those cores will be used| | | |
- | | by dpdk on host | | | |
- +------------------+----------------------------------+-----------------+---------------+-----------+
-
-Options for mem:
-
-.. table::
-
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | option | Description | Options | Default value | Must have |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | size | virtual machine memory size in | | 2048 | Yes |
- | | MBs | | | |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | hugepage | whether allocate memory from | | No | No |
- | | hugepages | | | |
- +------------------+----------------------------------+-----------------+---------------+-----------+
-
-Options for dev_gen:
-
-.. table::
-
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | option | Description | Options | Default value | Must have |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | pf_idx | PF device index of host port | | 0 | Yes |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | pf_inx->vf_num | number of VFs created by this PF | | 0 | Yes |
- | | device | | | |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | pf_inx->driver | Allocate VF devices from which PF| igb_uio,default | default | Yes |
- | | host driver | vfio-pci | | |
- +------------------+----------------------------------+-----------------+---------------+-----------+
-
-Options for device:
-
-.. table::
-
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | option | Description | Options | Default value | Must have |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | pf_idx | PF device index of host port | | 0 | Yes |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | pf_idx->guestpci | pci address in virtual machine | | | No |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | vf_idx | VF devices index of all VFs | | | No |
- | | belong to same PF devices | | | |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | vf_idx->pf_dev | PF device index of this VF device| | | Yes |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | vf_idx->guestpci | pci address in virtual machine | | | No |
- +------------------+----------------------------------+-----------------+---------------+-----------+
-
-Options for ports:
-
-.. table::
-
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | option | Description | Options | Default value | Must have |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | dev_idx | device index of virtual machine | | | No |
- | | ports | | | |
- +------------------+----------------------------------+-----------------+---------------+-----------+
- | dev_idx->peer | tester peer port's pci address | | | No |
- +------------------+----------------------------------+-----------------+---------------+-----------+
diff --git a/doc/dts_gsg/support_igb_uio.rst b/doc/dts_gsg/support_igb_uio.rst
deleted file mode 100644
index ca48a8f..0000000
--- a/doc/dts_gsg/support_igb_uio.rst
+++ /dev/null
@@ -1,102 +0,0 @@
-Test DPDK based on igb_uio
-==========================
-
-The kernel module igb_uio is moved to the dpdk-kmods repository in the
-/linux/igb_uio/ directory snice DPDK 20.11 (commit: 56bb5841fd06).
-The most easy way to test DPDK in DTS based on igb_uio is to add igb_uio
-source code back to dpdk.
-
-
-Get Source Code
----------------
-
-Get DPDK::
-
- git clone git://dpdk.org/dpdk
- git clone http://dpdk.org/git/dpdk
-
-Get igb_uio::
-
- git clone http://dpdk.org/git/dpdk-kmods
- git clone git://dpdk.org/dpdk-kmods
-
-Integrate igb_uio into DPDK
----------------------------
-
-Assume you have cloned the dpdk and dpdk-kmods source code
-in ./dpdk and ./dpdk-kmods.
-
-#. Copy dpdk-kmods/linux/igb_uio/ to dpdk/kernel/linux/::
-
- [root@dts linux]# cp -r ./dpdk-kmods/linux/igb_uio /root/dpdk/kernel/linux/
- [root@dts linux]# ls ./dpdk/kernel/linux/
- igb_uio kni meson.build
-
-#. enable igb_uio build in meson:
-
-* add igb_uio in dpdk/kernel/linux/meson.build subdirs as below::
-
- subdirs = ['kni', 'igb_uio']
-
-.. note::
-
- igb_uio will be added into compile list when it is added in subdirs.
-
-
-* create a file of meson.build in dpdk/kernel/linux/igb_uio/ as below::
-
- # SPDX-License-Identifier: BSD-3-Clause
- # Copyright(c) 2017 Intel Corporation
-
- mkfile = custom_target('igb_uio_makefile',
- output: 'Makefile',
- command: ['touch', '@OUTPUT@'])
-
- custom_target('igb_uio',
- input: ['igb_uio.c', 'Kbuild'],
- output: 'igb_uio.ko',
- command: ['make', '-C', kernel_dir + '/build',
- 'M=' + meson.current_build_dir(),
- 'src=' + meson.current_source_dir(),
- 'EXTRA_CFLAGS=-I' + meson.current_source_dir() +
- '/../../../lib/librte_eal/include',
- 'modules'],
- depends: mkfile,
- install: true,
- install_dir: kernel_dir + '/extra/dpdk',
- build_by_default: get_option('enable_kmods'))
-
-.. note::
-
- DPDK is using meson build, create meson.build so that igb_uio can be built.
-
-DTS configuration
------------------
-
-#. Pack the dpdk into dpdk.tar.gz and copy into dts/dep::
-
- tar -zcvf dpdk.tar.gz dpdk
- cp dpdk.tar.gz ~/dts/dep
-
-
-#. config drivername=igb_uio in execution.cfg::
-
- [Execution1]
- crbs=127.0.0.1
- drivername=igb_uio
- build_type=meson
- test_suites=
- checksum_offload,
- targets=
- x86_64-native-linuxapp-gcc
- parameters=nic_type=cfg:func=true
-
-#. configure dts with other requirements (not mentioned here) and now start dts::
-
- ./dts
-
-.. note ..
-
- dts parameter "-s" means skip setup, it won't unpack dep/dpdk.tar.gz
- to the default directory `/root/dpdk`, but use dpdk already there.
- so copy the integrated dpdk to `/root/dpdk` if with `-s`
\ No newline at end of file
diff --git a/doc/dts_gsg/sys_reqs.rst b/doc/dts_gsg/sys_reqs.rst
deleted file mode 100644
index c549646..0000000
--- a/doc/dts_gsg/sys_reqs.rst
+++ /dev/null
@@ -1,202 +0,0 @@
-System Requirements
-===================
-
-The board assigned to be tester should be installed the latest Fedora distribution for easily installed DPDK Test Suite required python modules. Tester board needs plug at least 2 x Intel® 82599 (Niantic) NICs (2x 10GbE full duplex optical ports per NIC) in the PCI express slots, then connect these four Niantic ports to the DUT board and make sure the link has been started up and speed is 10000Mb/s.
-
-Beside the four Niantic ports, tester and DUT should also have one interface connected to the same intranet. So that they can be accessed by each other from local IP address.
-
-.. note::
-
- Firewall should be disabled that all packets can be accepted by Niantic Interface.
-
-.. code-block:: console
-
- systemctl disable firewalld.service
-
-Setup Tester Environment
-------------------------
-
-.. note::
-
- Please install the latest ubuntu distribution on the tester before install DPDK Test Suite on tester. Currently we recommend ubuntu 18.04 for tester. The setup instruction and required packages may be different on different operation systems.
-
-To enable tester environment, you need to install script language, tool chain and third party packet generator, etc.
-
-Please follow the guidance to finish install as the below section.
-
-SSH Service
-~~~~~~~~~~~
-Since DPDK Test Suite Tester communicates with DUT via SSH, please install and start sshd service in your tester.
-
-.. code-block:: console
-
- apt-get install sshd # download / install ssh software
- systemctl enable ssh # start ssh service
-
-For create authorized login session, user needs to generate RSA authentication keys to ssh connection.
-
-Please use the following commands:
-
-.. code-block:: console
-
- ssh-keygen -t rsa
-
-TCL Language Support modules
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-Since some third party tools required TCL (Tool Command Language) supports, please install TCL package to control and connect third party package generator. (For example, third-party professional tester IXIA required TCL support)
-
-.. code-block:: console
-
- apt-get install tcl # download / install tcl software
-
-Install Third Party python modules
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
-With third party module, DPDK Test Suite is able to export test result as MS Excel file or graphs. To support this feature, please install the following modules in the tester.
-Python Module “xlwt”: this module is used to generate spreadsheet files which compatible with MS Excel 97/2000/XP/2003 XLS files.
-Python Module “numpy”: this module provides method to deal with array-processing test results.
-Python Module “pexpect”: this module provides API to automate interactive SSH sessions.
-Python Module “docutils”: Docutils is a modular system for processing documentation into useful formats, such as HTML, XML, and LaTeX.
-Python Module “pcapy”: Pcapy is a Python extension module that interfaces with the libpcap packet capture library. Pcapy enables python scripts to capture packets on the network.
-Python Module “xlrd”: Xlrd is a Python module that extracts data from Excel spreadsheets.
-Python Module “threadpool”: Threadpool is a Python module that maintains a pool of worker threads to perform time consuming operations in parallel.
-
-Please see installation instruction as the following:
-
-
-.. code-block:: console
-
- apt-get install python3-pip
- pip3 install -r ../../requirements.txt
-
-Setup and configure Scapy
-~~~~~~~~~~~~~~~~~~~~~~~~~
-Scapy is a powerful interactive packet manipulation program. It is able to forge or decode packets of a wide number of protocols, send them on the wire, capture them, match requests and replies, and much more. It can easily handle most classical tasks like scanning, tracerouting, probing, unit tests, attacks or network discovery.
-
-DTS uses python module scapy to forge or decode packets of a wide number of protocols, send them over the wire, capture them, and analyse the packets.
-
-.. code-block:: console
-
- pip3 install scapy
-
-scapy 2.4.4: support packet layer PFCP and GTPPDUSessionContainer
-
-.. code-block:: console
-
- pip3 install scapy==2.4.4
-
-.. note::
- There are some differences between scapy 2.4.4 and scapy 2.4.3 about the packet layer, the details refer to the
- table as follows.
-
-.. table::
-
- +------------------------+---------------------------------+-----------------------------------------------+------------------------------------------------------+
- | Compare scapy 2.4.3 with scapy 2.4.4 |
- +------------------------+---------------------------------+-----------------------------------------------+------------------------------------------------------+
- | Layer | packet in scapy 2.4.3 | packet in scapy 2.4.4 | Comments |
- +========================+=================================+===============================================+======================================================+
- | PPP | PPP(proto=0xc021) | PPP(b\'\\xc0\\x21\') | PPP protocol filed length is 1 byte in scapy2.4.4 |
- +------------------------+---------------------------------+-----------------------------------------------+------------------------------------------------------+
- | L2TP | L2TP(\'\\x00\\x00\\x00\\x11\') | L2TP(b\'\\x00\\x00\\x00\\x11\') | L2TP is byte type in scapy2.4.4 |
- +------------------------+---------------------------------+-----------------------------------------------+------------------------------------------------------+
- | PFCP | N/A | PFCP(S=1, seid=1) | PFCP is not supported in scapy2.4.3 |
- +------------------------+---------------------------------+-----------------------------------------------+------------------------------------------------------+
- | GTPPDUSessionContainer | N/A | GTPPDUSessionContainer(type=0, P=1, QFI=0x34) | GTPPDUSessionContainer is not supported in scapy2.4.3|
- +------------------------+---------------------------------+-----------------------------------------------+------------------------------------------------------+
-
-
-Install DPDK Test Suite on tester
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
-After configure environment, we need to install DPDK Test Suite into tester. First of all, download the latest DPDK Test Suite code from remote repo.
-
-.. code-block:: console
-
- [root@tester ~]# git clone http://dpdk.org/git/tools/dts
- [root@tester ~]# cd dts
- [root@tester dts]# ls
- [root@tester dts]# conf dep doc dts executions framework nics output test_plans tests tools
-
-High Precision Timer (HPET) must be enabled in the platform BIOS if the HPET is to be used. Otherwise, the Time Stamp Counter (TSC) is used by default. The user can then navigate to the HPET option. On the Crystal Forest platform BIOS, the path is:
-**Advanced -> PCH-IO Configuration -> High Precision Timer**
-
-The DPDK Test Suite is composed of several file and directories:
-
-* dts: Main module of DPDK Test Suite suite
-* exectution.cfg: configuration file of DPDK Test Suite suite
-* framework: folder with dts framework modules
-* nics: folder with different network device modules
-* output: folder which contain running log files and result files
-* test_plans: folder with rst files which contain the description of test case
-* tests: folder with test case scripts
-
-Setup Target Environment
-------------------------
-
-This section describes how to deploy DPDK Test Suite packages into DUT target.So far, DPDK Test Suite supports the following OS on DUT:
-
-* Fedora 32
-* Ubuntu 16.04/18.04/20.04
-* FreeBSD 12.1
-* RedHat 7.7/8.0
-* SUSE 15
-* Centos 7.7/8.0
-* OpenWRT 19.07
-
-Before run DPDK Test Suite on target, we need to configure target environment, it includes BIOS setting, Network configure, compiler environment, etc.
-
-BIOS setting Prerequisite
-~~~~~~~~~~~~~~~~~~~~~~~~~
-
-In general, enter BIOS Menu by pressing F2 while the platform is starting up.
-
-.. note::
- It is strongly recommended to use DPDK with the latest generation of Intel platforms and processors.
-
-The High Precision Timer (HPET) must be enabled in the platform BIOS if the HPET is to be used. Otherwise, the Time Stamp Counter (TSC) is used by default. The user can then navigate to the HPET option. On the Crystal Forest platform BIOS, the path is:
-
-**Advanced -> PCH-IO Configuration -> High Precision Timer**
-
-Enhanced Intel SpeedStep® Technology must be disabled in the platform BIOS, to ensure the processor voltage and core frequency do not change. This is necessary for consistency of data. On the Crystal Forest platform BIOS the path is:
-
-
-**Advanced -> Processor Configuration -> Enhanced Intel SpeedStep**
-
-Processor state C3 and C6 must be disabled for performance measure too. On the Crystal Forest platform BIOS, the path is:
-
-**Advanced -> Processor Configuration -> Processor C3**
-**Advanced -> Processor Configuration -> Processor C6**
-
-Hyper-Threading Technology must be enabled. On the Crystal Forest platform BIOS, the path is:
-
-**Advanced -> Processor Configuration -> Intel® Hyper-Threading Tech**
-
-If the platform BIOS has any particular performance option, select the settings for best performance.
-
-DPDK running Prerequisite
-~~~~~~~~~~~~~~~~~~~~~~~~~
-Compilation of DPDK need GNU maker, gcc, libc-header, kernel header installed. For 32-bit compilation on 64-bit systems, there’re some additional packages required. For Intel® C++ Compiler (icc) additional libraries may be required. For more detail information of required packets, please refer to Data Plane Development Kit Getting Started Guide.
-
-The DPDK igb_uio kernel module depends on traditional Linux kernel ``uio`` support to operate. Linux traditional ``uio`` support may be compiled as a module, so this module should be loaded using the ``modprobe`` program.
-Kernel must support the allocation of hugepages. Hugepage support is required for the large memory pool allocation used for packet buffers. By using hugepage allocations, performance will be improved since only fewer pages are needed, and therefore less Translation Lookaside Buffers (TLBs, high speed translation caches), which reduce the time it takes to translate a virtual page address to a physical page address. Without hugepages, high TLB miss rates would occur, slowing performance.
-
-For more detail information of system requirements, also refer to `Data Plane Development Kit Getting Started Guide <http://dpdk.org/doc/guides>`_.
-
-Authorized login session
-------------------------
-In DPDK Test Suite, support communication be established based on authorized ssh session. All ssh connection to each other will skip password interactive phase if remote server has been authorized.
-
-In tester, you can use tool ssh-copy-id to save local available keys on DUT, thus create authorise login session between tester and DUT. By the same way, you can create authorise login session between tester and itself.
-
-.. code-block:: console
-
- ssh-copy-id -i “IP of DUT”
- ssh-copy-id -i “IP of tester”
-
-In DUT, You also can use tool ssh-copy-id to save local available keys in tester, thus create authorise login session between DUT and tester.
-
-.. code-block:: console
-
- ssh-copy-id –i “IP of Tester”
-
diff --git a/doc/dts_gsg/trex.rst b/doc/dts_gsg/trex.rst
deleted file mode 100644
index 4676f96..0000000
--- a/doc/dts_gsg/trex.rst
+++ /dev/null
@@ -1,23 +0,0 @@
-Configuring T-Rex for DPDK Test Suite
-=====================================
-
-DPDK can utilize T-Rex as a traffic generator in stateless Layer 2 mode.
-
-An example T-Rex configuration that accomplishes this is shown as follows:
-
-.. code-block:: console
-
- - port_limit: 2
- version: 2
- interfaces: ["03:00.0", "03:00.1"]
- port_info:
- - src_mac: "aa:bb:cc:dd:ee:ff"
- dest_mac: "ff:ee:dd:cc:bb:aa"
- - src_mac: "ff:ee:dd:cc:bb:aa"
- dest_mac: "aa:bb:cc:dd:ee:ff"
-
-DTS may use a standalone T-Rex instance, or can be configured to start T-Rex
-itself using the settings in ``pktgen.conf``.
-
-To read more about T-Rex stateless mode, read the
-`T-Rex stateless support guide <https://trex-tgn.cisco.com/trex/doc/trex_stateless.html>`__.
diff --git a/doc/dts_gsg/trex_known_issue.rst b/doc/dts_gsg/trex_known_issue.rst
deleted file mode 100644
index 8a84e7c..0000000
--- a/doc/dts_gsg/trex_known_issue.rst
+++ /dev/null
@@ -1,113 +0,0 @@
-======================
-How dts work with trex
-======================
-
-dpdk hugepage management conflict issue
-=======================================
-trex use older dpdk version than we release cycle source code. When dpdk change
-the memory management merchanism, trex will meet the following issue.
-
-Trex should run on an independent platform. DUT/Trex should run on two platforms:
-
-* one is used as TESTER and trex server, another one is used as DUT.(dts/pktgen)
-* one is used as trex server, another one is used as DUT/TESTER.(recommended scheme)
- This scheme can make sure that trex run on its full status capability.
-
-When trex run with dts on the same platform, trex server sometimes boot up
-failed for hugepage error.
-
-.. code-block:: console
-
- ./t-rex-64 -i --stl -k 4
-
- Starting Scapy server..... Scapy server is started
- Trying to bind to igb_uio ...
- /usr/bin/python3 dpdk_nic_bind.py --bind=igb_uio 0000:85:00.0 0000:8a:00.1
- The ports are bound/configured.
- Starting TRex v2.41 please wait ...
- EAL: Can only reserve 1766 pages from 4096 requested
- Current CONFIG_RTE_MAX_MEMSEG=256 is not enough
- Please either increase it or request less amount of memory.
- EAL: FATAL: Cannot init memory
-
- EAL: Cannot init memory
-
- You might need to run ./trex-cfg once
- EAL: Error - exiting with code: 1
- Cause: Invalid EAL arguments
-
-trex quit when using NNT
-========================
-when bind dut NNT port to igb_uio, peer port will get a link down status, then
-trex server using NNT nic will quit.
-
-.. code-block:: console
-
- WATCHDOG: task 'master' has not responded for more than 2.00044 seconds - timeout is 2 seconds
-
- *** traceback follows ***
-
- 1 0x55a7c779561a ./_t-rex-64(+0x12761a) [0x55a7c779561a]
- 2 0x7f23da4be1b0 /lib64/libpthread.so.0(+0x121b0) [0x7f23da4be1b0]
- 3 0x55a7c7942d40 rte_delay_us_block + 128
- 4 0x55a7c798d731 ixgbe_setup_mac_link_multispeed_fiber + 337
- 5 0x55a7c79a8f14 ./_t-rex-64(+0x33af14) [0x55a7c79a8f14]
- 6 0x55a7c7954c72 rte_eth_link_get_nowait + 114
- 7 0x55a7c776a988 DpdkTRexPortAttr::update_link_status_nowait() + 24
- 8 0x55a7c77856a6 CGlobalTRex::handle_slow_path() + 118
- 9 0x55a7c7785ad7 CGlobalTRex::run_in_master() + 759
- 10 0x55a7c7785e3c ./_t-rex-64(+0x117e3c) [0x55a7c7785e3c]
- 11 0x55a7c793efba rte_eal_mp_remote_launch + 346
- 12 0x55a7c7789e1e main_test(int, char**) + 1038
- 13 0x7f23d9417f2a __libc_start_main + 234
- 14 0x55a7c7719b9d ./_t-rex-64(+0xabb9d) [0x55a7c7719b9d]
-
-
- *** addr2line information follows ***
-
- ??:0
- ??:0
- ??:0
- ??:0
- ??:0
- ??:0
- ??:0
- ??:0
- ??:0
- ??:0
- ??:0
- ??:0
- ??:0
- ??:0
-
-
- ./t-rex-64: line 80: 25870 Aborted (core dumped) ./_$(
-
-scapy name space conflict
-=========================
-trex scapy lib will be conflict with
-
-resolved scheme
----------------
-
-#. backup your scapy::
- cp -fr /usr/lib/python3/site-packages/scapy /usr/lib/python3/site-packages/scapy_backup
-
-#. unify scapy version with trex::
- cp -fr /opt/trex/v2.41/trex_client/external_libs/scapy-2.3.1/python3/scapy /usr/lib/python3/site-packages/scapy
-
-other issues
-============
-
-#. linux kernel verion should not be too low.
-
-#. Trex only works with even number link peers.
-
-#. Trex only works with nics, which are using the same driver.
-
-#. Before boot up trex, please make sure the peer ports are on up status.
-
-#. If you have ran dpdk on the platform which you want to deploy trex-server,
- reboot the platform to make sure that trex-server can work fine.
-
-#. If using i40e driver, Trex v2.41 version need i40e nic firmware version newer than 5.02.
diff --git a/doc/dts_gsg/tutorial.rst b/doc/dts_gsg/tutorial.rst
deleted file mode 100644
index 543c134..0000000
--- a/doc/dts_gsg/tutorial.rst
+++ /dev/null
@@ -1,139 +0,0 @@
-Tutorial
-========
-
-Functional Test Tutorial
-------------------------
-Tutorial of functional test.
-
-Execution configuration
-~~~~~~~~~~~~~~~~~~~~~~~
-By default, DTS will load execution tasks from execution.cfg. In this file, user can assign multiple tasks to DTS. For each task, DTS will initialize dpdk environment on DUT and run test suites listed. As example below, user assigned one execution task on 127.0.0.1.
-
-Details of the task is defined by some settings like target, NIC type, functional or performance case and foremost the list of suites which will be executed.
-
-.. code-block:: console
-
- [127.0.0.1]
- crbs=127.0.0.1
- drivername=igb_uio
- test_suites=
- vlan
- targets=
- x86_64-native-linuxapp-gcc
- parameters=nic_type=cfg:func=true
-
-DUT&Tester configuration
-~~~~~~~~~~~~~~~~~~~~~~~~
-In previous chapter, we assume that user has assigned some execution task on 127.0.0.1. DTS will create the SSH connections to the DUT and tester which connected to it in the runtime. After session established, DTS will setup kernel modules and hugepages on DUT. The procedures for different OS maybe different, so type of OS is also needed to be configured by manual.
-
-.. code-block:: console
-
- cat ./conf/crbs.cfg
- [127.0.0.1]
- dut_ip=127.0.0.1
- dut_user=root
- dut_passwd=xxx
- os=linux
- tester_ip=192.168.1.1
- tester_passwd=xxx
- ixia_group=None
- channels=4
- bypass_core0=True
-
-Network topology configuration
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-By default DTS will detect network topology automatically, but in certain occasions it can’t be done like no kernel module available for latest NIC or tester’s port need special settings. For resolving those kind of problems, DTS also support manually specify ports connections. The concept is that user only need to specify PCI devices under test and peer PCI address on tester server. In below sample, we defined network topology that DUT pci device (18:00.0) connected to pci device (1b:00.0) on 192.168.1.1.
-
-.. code-block:: console
-
- cat ./conf/ports.cfg
- [127.0.0.1]
- ports =
- pci=0000:18:00.0,peer=0000:1b:00.0;
-
-Running execution
-~~~~~~~~~~~~~~~~~
-Before running real task, DPDK release packet should be saved under dep folder.
-Make sure that files will be extracted to folder name same as default output directory (dpdk).
-
-.. code-block:: console
-
- cp dpdk.tar.gz dep/
- ./dts
-
-
-Performance Test Tutorial
--------------------------
-Turtorial of performance test.
-
-Execution configuration
-~~~~~~~~~~~~~~~~~~~~~~~
-Like functional test, performance execution need configure CRB, target, NIC type and suites. Only difference is that performance option should be true in parameters setting.
-
-.. code-block:: console
-
- [127.0.0.1]
- crbs=127.0.0.1
- drivername=igb_uio
- test_suites=
- l2fwd
- targets=
- x86_64-native-linuxapp-gcc
- parameters=nic_type=cfg:perf=true
-
-DUT&Tester configuration
-~~~~~~~~~~~~~~~~~~~~~~~~
-DTS now support two kinds of packet generators. One is hardware packet generator IXIA, the other is dpdk based packet generator. Here is the sample for IXIA, IXIA's hardware resource like ports will be managed by groups in DTS. User need to assign which group will be used, and therefore IXIA ports in the group will be extended to tester's ports list.
-
-.. code-block:: console
-
- cat ./conf/crbs.cfg
- [127.0.0.1]
- dut_ip=127.0.0.1
- dut_user=root
- dut_passwd=xxx
- os=linux
- tester_ip=192.168.1.1
- tester_passwd=xxx
- ixia_group=IXIA
- channels=4
- bypass_core0=True
-
-.. code-block:: console
-
- cat ./conf/ixia.cfg
- [IXIA]
- ixia_version=6.62
- ixia_ip=xxx.xxx.xxx.xxx
- ixia_ports=
- card=1,port=1;
- card=1,port=2;
- ixia_force100g=disable
-
-When there's none IXIA group configured in CRB's cfg file, DTS will try to use dpdk based packet generator for alternative. Apparently dpdk based packet generator can't meet all the requirements like latency,RFC2544 and random packets. The statistics reported by dpdk pktgen were just for reference.
-
-Dpdk based packet generator will request for dpdk running environment. So that user should prepare required kernel module igb_uio.ko under tester's root directory. Due to packet generator can't support one-time build and run on all platforms, user should also prepare pktgen binary under tester's root directory. By now supported combination is dpdk v18.02 + dpdk-pktgen v3.5.0. Download link: http://dpdk.org/browse/apps/pktgen-dpdk/
-
-.. code-block:: console
-
- cat ./conf/crbs.cfg
- ...
- ixia_group=None
- ...
-
-Network topology configuration
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
-By default network topology of IXIA ports can be detected automatically. DTS also support manually configure network topo.
-
-.. code-block:: console
-
- cat ./conf/ports.cfg
- [127.0.0.1]
- ports =
- pci=0000:18:00.0,peer=IXIA:1.1;
- pci=0000:18:00.1,peer=IXIA:1.2;
-
-Running execution
-~~~~~~~~~~~~~~~~~
-Same as functional test.
diff --git a/doc/dts_gsg/usage_of_create_eal_and_start_testpmd.rst b/doc/dts_gsg/usage_of_create_eal_and_start_testpmd.rst
deleted file mode 100644
index 144f611..0000000
--- a/doc/dts_gsg/usage_of_create_eal_and_start_testpmd.rst
+++ /dev/null
@@ -1,103 +0,0 @@
-How create_eal_parameters and start_testpmd methods use in DPDK Test Suite
-==========================================================================
-
-create_eal_parameters
-----------------------------
-
-This method used to create EAL parameters character string in DPDK Test Suite.
-for example: -l 1,2 -w 0000:88:00.0 -w 0000:88:00.1 --file-prefix=dpdk_1112_20190809143420.
-
-.. code-block:: console
-
- define: create_eal_parameters(self, fixed_prefix=False, socket=-1, **config)
-
- usage and example:
- no user parameters:
- param = self.dut.create_eal_parameters()
- output:
- param = '-l 1,2 -n 4 -w 0000:1a:00.0 -w 0000:1a:00.1 --file-prefix=dpdk_397938_20191105143309'
-
- user parameters:
- 1. usage for port and port options, there are two methods for them.
- param = self.dut.create_eal_parameters(cores='1S/4C/1T', ports=[0,1], port_options={0: "proto_xtr=vlan"})
- or
- param = self.dut.create_eal_parameters(cores='1S/4C/1T', ports=['0000:1a:00.0', '0000:1a:00.1'], port_options={'0000:1a:00.0': "proto_xtr=vlan"})
- output:
- param = '-l 1,2,3,4 -n 4 -w 0000:1a:00.0,proto_xtr=vlan -w 0000:1a:00.1 --file-prefix=dpdk_399214_20191105155446'
-
- 2. usage for b_ports.
- param = self.dut.create_eal_parameters(cores='1S/4C/1T', b_ports=[0])
- or
- param = self.dut.create_eal_parameters(cores='1S/4C/1T', b_ports=['0000:1a:00.0'])
- output:
- param = '-l 1,2,3,4 -n 4 -b 0000:1a:00.0 --file-prefix=dpdk_399214_20191105155446'
-
- 3. usage for no-pci.
- param = self.dut.create_eal_parameters(cores='1S/4C/1T', no_pci=True)
- output:
- param = '-l 1,2,3,4 -n 4 --file-prefix=dpdk_399214_20191105155446 --no-pci'
-
- 4. usage for prefix, if fixed_prefix = True, the file-prefix will use the value of prefix, or the value is dpdk_pid_timestamp.
- param = self.dut.create_eal_parameters(cores='1S/4C/1T', ports=[0, 1], port_options={0: "proto_xtr=vlan"}, fixed_prefix=True, prefix='user_defined')
- output:
- param = '-l 1,2,3,4 -n 4 -w 0000:1a:00.0,proto_xtr=vlan -w 0000:1a:00.1 --file-prefix=user_defined'
-
- 5. usege for vdevs.
- param_vdev = self.dut.create_eal_parameters(cores='1S/4C/1T', no_pci=True, vdevs=[r"net_virtio_user0,mac=%s,path=./vhost-net,queues=1"])
- output:
- param = '-l 1,2,3,4 -n 4 --file-prefix=dpdk_399214_20191105155446 --no-pci --vdev net_virtio_user0,mac=%s,path=./vhost-net,queues=1'
-
-
-create_eal_parameters function supports the following parameters:
-
-.. table::
-
- +---------------------------+---------------------------------------------------+------------------+
- | parameter | description | Default Value |
- +---------------------------+---------------------------------------------------+------------------+
- | fixed_prefix | Indicate use default prefix or user define prefix | False |
- +---------------------------+---------------------------------------------------+------------------+
- | socket | socket of system | -1 |
- +---------------------------+---------------------------------------------------+------------------+
- | cores | set core list | 1S/2C/1T |
- +---------------------------+---------------------------------------------------+------------------+
- | ports | PCI list or PCI ID list | |
- +---------------------------+---------------------------------------------------+------------------+
- | port_options | other port options | |
- +---------------------------+---------------------------------------------------+------------------+
- | b_ports | PCI device in block list | |
- +---------------------------+---------------------------------------------------+------------------+
- | no_pci | Disable PCI bug | |
- +---------------------------+---------------------------------------------------+------------------+
- | prefix | Use a different shared data file prefix for a | |
- | | DPDK process | |
- +---------------------------+---------------------------------------------------+------------------+
- | vdevs | Add a virtual device | |
- +---------------------------+---------------------------------------------------+------------------+
-
-
-start_testpmd
-----------------------------
-
-The method use to start testpmd application.
-
-.. code-block:: console
-
- define: start_testpmd(self, cores='default', param='', eal_param='', socket=0, fixed_prefix=False, **config)
-
- usage and example:
- no user parameters:
- out = self.pmdout.start_testpmd()
- user parameters:
- 1. Those two parameters param and eal_param are used for current test suites.
- for example:
- In current test suite TestSuite_runtime_vf_queue_number, the eal parameters are wrote as a line string as below.
- eal_param = '-w %s,queue-num-per-vf=%d --file-prefix=test1 --socket-mem 1024,1024' % (self.pf_pci, invalid_qn)
- then you can call start_testpmd like this.
- out = self.pmdout.start_testpmd(self.pmdout.default_cores, param='', eal_param=eal_param)
-
- Another usage in current test suite like below:
- self.pmdout.start_testpmd("Default", "--portmask=%s " %(self.portMask) + " --enable-rx-cksum " + "--port-topology=loop", socket=self.ports_socket)
-
- 2. If you will write a new test suite and need to call start_testpmd method,
- The usage of other parameters such as cores, socket, fixed_prefix and **config are the same as create_eal_parameters.
diff --git a/doc/dts_gsg/usr_guide/igb_uio.rst b/doc/dts_gsg/usr_guide/igb_uio.rst
new file mode 100644
index 0000000..13648cd
--- /dev/null
+++ b/doc/dts_gsg/usr_guide/igb_uio.rst
@@ -0,0 +1,102 @@
+Practice for igb_uio
+====================
+
+The kernel module igb_uio is moved to the dpdk-kmods repository in the
+/linux/igb_uio/ directory snice DPDK 20.11 (commit: 56bb5841fd06).
+The most easy way to test DPDK in DTS based on igb_uio is to add igb_uio
+source code back to dpdk.
+
+
+Get Source Code
+---------------
+
+Get DPDK::
+
+ git clone git://dpdk.org/dpdk
+ git clone http://dpdk.org/git/dpdk
+
+Get igb_uio::
+
+ git clone http://dpdk.org/git/dpdk-kmods
+ git clone git://dpdk.org/dpdk-kmods
+
+Integrate igb_uio into DPDK
+---------------------------
+
+Assume you have cloned the dpdk and dpdk-kmods source code
+in ./dpdk and ./dpdk-kmods.
+
+#. Copy dpdk-kmods/linux/igb_uio/ to dpdk/kernel/linux/::
+
+ [root@dts linux]# cp -r ./dpdk-kmods/linux/igb_uio /root/dpdk/kernel/linux/
+ [root@dts linux]# ls ./dpdk/kernel/linux/
+ igb_uio kni meson.build
+
+#. enable igb_uio build in meson:
+
+* add igb_uio in dpdk/kernel/linux/meson.build subdirs as below::
+
+ subdirs = ['kni', 'igb_uio']
+
+.. note::
+
+ igb_uio will be added into compile list when it is added in subdirs.
+
+
+* create a file of meson.build in dpdk/kernel/linux/igb_uio/ as below::
+
+ # SPDX-License-Identifier: BSD-3-Clause
+ # Copyright(c) 2017 Intel Corporation
+
+ mkfile = custom_target('igb_uio_makefile',
+ output: 'Makefile',
+ command: ['touch', '@OUTPUT@'])
+
+ custom_target('igb_uio',
+ input: ['igb_uio.c', 'Kbuild'],
+ output: 'igb_uio.ko',
+ command: ['make', '-C', kernel_dir + '/build',
+ 'M=' + meson.current_build_dir(),
+ 'src=' + meson.current_source_dir(),
+ 'EXTRA_CFLAGS=-I' + meson.current_source_dir() +
+ '/../../../lib/librte_eal/include',
+ 'modules'],
+ depends: mkfile,
+ install: true,
+ install_dir: kernel_dir + '/extra/dpdk',
+ build_by_default: get_option('enable_kmods'))
+
+.. note::
+
+ DPDK is using meson build, create meson.build so that igb_uio can be built.
+
+DTS configuration
+-----------------
+
+#. Pack the dpdk into dpdk.tar.gz and copy into dts/dep::
+
+ tar -zcvf dpdk.tar.gz dpdk
+ cp dpdk.tar.gz ~/dts/dep
+
+
+#. config drivername=igb_uio in execution.cfg::
+
+ [Execution1]
+ crbs=127.0.0.1
+ drivername=igb_uio
+ build_type=meson
+ test_suites=
+ checksum_offload,
+ targets=
+ x86_64-native-linuxapp-gcc
+ parameters=nic_type=cfg:func=true
+
+#. configure dts with other requirements (not mentioned here) and now start dts::
+
+ ./dts
+
+.. note ..
+
+ dts parameter "-s" means skip setup, it won't unpack dep/dpdk.tar.gz
+ to the default directory `/root/dpdk`, but use dpdk already there.
+ so copy the integrated dpdk to `/root/dpdk` if with `-s`
diff --git a/doc/dts_gsg/usr_guide/image/dts_func_deploy.png b/doc/dts_gsg/usr_guide/image/dts_func_deploy.png
new file mode 100644
index 0000000000000000000000000000000000000000..0062ff79f91891d3704dc97116df69489d757e83
GIT binary patch
literal 24729
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.M8j-i$5tjlSkDB6-z?S0IyK#e@)
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
literal 0
Hc$@<O00001
diff --git a/doc/dts_gsg/usr_guide/image/dts_result.png b/doc/dts_gsg/usr_guide/image/dts_result.png
new file mode 100644
index 0000000000000000000000000000000000000000..65e0ada586bfb5264eab02f7a6dedfe898e12849
GIT binary patch
literal 10924
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
HZukEHHd%iB
literal 0
Hc$@<O00001
diff --git a/doc/dts_gsg/usr_guide/index.rst b/doc/dts_gsg/usr_guide/index.rst
new file mode 100644
index 0000000..f4104f8
--- /dev/null
+++ b/doc/dts_gsg/usr_guide/index.rst
@@ -0,0 +1,42 @@
+.. BSD LICENSE
+ Copyright(c) 2010-2014 Intel Corporation. All rights reserved.
+ All rights reserved.
+
+ Redistribution and use in source and binary forms, with or without
+ modification, are permitted provided that the following conditions
+ are met:
+
+ * Redistributions of source code must retain the above copyright
+ notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above copyright
+ notice, this list of conditions and the following disclaimer in
+ the documentation and/or other materials provided with the
+ distribution.
+ * Neither the name of Intel Corporation nor the names of its
+ contributors may be used to endorse or promote products derived
+ from this software without specific prior written permission.
+
+ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+User Guide
+==========
+
+.. toctree::
+
+ intro
+ sys_reqs
+ usage
+ results
+ trex
+ ixia
+ igb_uio
diff --git a/doc/dts_gsg/usr_guide/intro.rst b/doc/dts_gsg/usr_guide/intro.rst
new file mode 100644
index 0000000..dc4c0bf
--- /dev/null
+++ b/doc/dts_gsg/usr_guide/intro.rst
@@ -0,0 +1,90 @@
+Introduction
+============
+
+This document describes how to install and configure the Data Plane Development Kit Test Suite (DTS) in a Linux environment.
+DTS is an automation test tool for DPDK, wrote in `Python3`.
+DTS includes one set of test cases and DPDK generic test framework.
+DTS provides test example, references and framework for open source community.
+Based on DTS, everyone can develop their test plan, automation script and configuration for own features and platform.
+In addition, DTS provides a solution to allow that DPDK developers contribute their function test to certify their patch integration.
+It only requires limited effort to maintain test cases once merged into DPDK Test Suite.
+Everyone can utilize DTS to measure performance and functionality for features.
+
+As a generic test framework, DTS provides the following functions:
+
+* Communicate/manage DUT and Tester by SSH connection.
+* Able to work with DUT (Device Under Test), which installed Fedora, Ubuntu, CentOS, RHEL, etc.
+* Support virtualization hypervisor Qemu.
+* Support both software and hardware traffic generators, including Scapy, TRex and IXIA®.
+* Provide configure files to customize test suite and test cases to run under DUT.
+* Provide debug and log functionalities for tracking test cases execution process.
+* Support to output test result by excel, json, log text file, etc.
+
+DTS environment includes DUT (Device under Test), Tester and Traffic generator. DPDK are deployed on DUT and DTS can run on the Tester or DUT or the third machine.
+
+.. note::
+
+ * If run with functional testing, DTS uses `Scapy` as traffic generator, recommend installing DTS on Tester.
+ * If run with performance testing, DTS can use `TRex` or IXIA as traffic gengerator based on your deployment and configuration, recommend installing DTS on DUT.
+ * If use `TRex`, recommend deploying `TRex` and DUT on the same machine with different sockets.
+
+Please see a functional deployment example in the following figure:
+
+.. figure:: image/dts_func_deploy.png
+
+This architecture provides automatically mechanism to manage tester, DUT and packet generators, and remove dependency between test script and test environment/hardware.
+It defines one abstraction layer for DPDK Test Suite, and provides extensibility to add more test script.
+In the DPDK Test Suite Test Framework, it provides the following modules to help to manage device, platform, configure and test results.
+
+.. table::
+
+ +---------------------+------------------------------------------------------------------------------+
+ | File Name/Directory | Description |
+ +=====================+==============================================================================+
+ | dts | Main Application for DTS |
+ +---------------------+------------------------------------------------------------------------------+
+ | framework | Folder with dts framework modules |
+ +---------------------+------------------------------------------------------------------------------+
+ | nics | Folder with different network device modules |
+ +---------------------+------------------------------------------------------------------------------+
+ | conf | Folder with different config files |
+ +---------------------+------------------------------------------------------------------------------+
+ | execution.cfg | Default execution file |
+ +---------------------+------------------------------------------------------------------------------+
+ | executions | Folder with several execution file samples |
+ +---------------------+------------------------------------------------------------------------------+
+ | output | Folder which contain running log files and result files |
+ +---------------------+------------------------------------------------------------------------------+
+ | dep | Folder with dependence scripts |
+ +---------------------+------------------------------------------------------------------------------+
+ | test_plans | Folder with rst files which contain the description of test suites and cases |
+ +---------------------+------------------------------------------------------------------------------+
+ | tests | Folder with test scripts for test suites and cases |
+ +---------------------+------------------------------------------------------------------------------+
+ | doc | Folder with DTS related documents |
+ +---------------------+------------------------------------------------------------------------------+
+ | requirements.txt | DTS required Python packages |
+ +---------------------+------------------------------------------------------------------------------+
+
+These test script provides example and reference. Everyone can develop their test cases, verify their features functionality, and commit generic test report to maintainer.
+, user-defined test cases, test plans and scripts must follow DPDK Test Suite standard including code standard, naming conventions, configure format, rst test plan, API.
+
+Please see test cases, which are included in the DPDK compliance test suites:
+
+.. table::
+
+ +---------------------+----------------------------------------------------------------------------------------------------------------------------+
+ | Test Suite | Descriptions |
+ +=====================+============================================================================================================================+
+ | hello_world | Print a ``helloworld`` message on every enabled logic core. |
+ +---------------------+----------------------------------------------------------------------------------------------------------------------------+
+ | Timer | Shows how timer can be used in a RTE application. |
+ +---------------------+----------------------------------------------------------------------------------------------------------------------------+
+ | checksum_offload | Tests RX/TX L3/L4 Checksum offload features by Poll Mode Drivers |
+ +---------------------+----------------------------------------------------------------------------------------------------------------------------+
+ | jumbo_frame | Tests jumbo frames features by Poll Mode Drivers |
+ +---------------------+----------------------------------------------------------------------------------------------------------------------------+
+ | testpmd | Provides benchmark tests for the Intel Ethernet Controller (Niantic) Poll Mode Driver. |
+ +---------------------+----------------------------------------------------------------------------------------------------------------------------+
+ | L3fwd | Verifies Layer-3 Forwarding results using ``l3fwd`` application. |
+ +---------------------+----------------------------------------------------------------------------------------------------------------------------+
diff --git a/doc/dts_gsg/usr_guide/ixia.rst b/doc/dts_gsg/usr_guide/ixia.rst
new file mode 100644
index 0000000..2ad754e
--- /dev/null
+++ b/doc/dts_gsg/usr_guide/ixia.rst
@@ -0,0 +1,248 @@
+Practice with IxExplorer
+========================
+
+This chapter describes a DTS practice with IXIA IxExplorer, which mainly used for performance testing.
+Here we take the performance case nic_single_core as an example.
+
+Configuring your own execution file
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+First of all, you must configure execution.cfg as below:
+
+.. code-block:: console
+
+ [Execution1]
+ crbs=192.168.1.1
+ drivername=vfio-pci
+ test_suites=
+ nic_single_core_perf,
+ targets=
+ x86_64-native-linuxapp-gcc
+ parameters=nic_type=cfg:perf=true
+ build_type=meson
+ rx_mode=avx512
+
+Configure CRB information
+~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Then please add the detail information about your CRB in conf/crbs.conf as following:
+
+.. code-block:: console
+
+ [192.168.1.1]
+ dut_ip=192.168.1.1
+ dut_user=root
+ dut_passwd=passwd
+ os=linux
+ dut_arch=
+ tester_ip=192.168.1.1
+ tester_passwd=passwd
+ pktgen_group=IXIA
+ channels=4
+ bypass_core0=True
+ dut_cores=
+
+Configure port information
+~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+ports topology as below:
+
+.. code-block:: console
+
+ IXIA port 0 <---------> DUT port 0
+ IXIA port 1 <---------> DUT port 1
+
+please add port configuration in conf/ports.cfg as following:
+
+.. code-block:: console
+
+ [192.168.1.1]
+ ports =
+ pci=0000:af:00.0,peer=IXIA:3.1;
+ pci=0000:b1:00.0,peer=IXIA:3.2;
+
+Configure pktgen information
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+please configure Pktgen information in conf/pktgen.cfg
+
+.. code-block:: console
+
+ [IXIA]
+ ixia_version=9.00
+ ixia_ip=192.168.2.1
+ ixia_ports=
+ card=3,port=1;
+ card=3,port=2;
+ ixia_force100g=disable
+
+.. note::
+
+ The version of ixia must be consistent with your version of IxExplorer.
+
+
+Configure your own suites
+~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Performance tests generally have configuration files.
+it's name corresponds to the suite.
+Below is the conf/nic_single_core_perf.cfg configuration file.
+You can set the test parameters according to your test needs.
+
+
+.. code-block:: console
+
+ [suite]
+ update_expected = True
+ test_parameters = {'1C/1T': {64: [512, 2048]},
+ '1C/2T': {64: [512, 2048]}}
+ rx_desc_16byte = 'y'
+ test_duration = 60
+ accepted_tolerance = 1
+ expected_throughput = {
+ 'fortville_spirit': {
+ '1C/1T': {64: {512: 0.00, 2048: 0.00}},
+ '1C/2T': {64: {512: 0.00, 2048: 0.00}}}}
+
+* accepted_tolerance: defines the accepted tolerance between real pps and expected pps.
+* test_parameters: defines the combination of frame size and descriptor numbers,
+ and the pattern is {'frame size': ['descriptor number #1', 'descriptor number #2']}.
+* rx_desc_16byte: 16byte configuration and default by enabled.
+* test_duration: how many seconds each combination performance will be recorded.
+* expected_throughput: it's a dictionary defining expected throughput numbers based on NIC,
+ and the pattern is {'NIC': {'frame size': {'descriptor number': 'excepted throughput'}}}
+ Every user should fill it out with your actual numbers.
+* update_expected: if update_expected==True, and add argument "--update-expected" in bash command,
+ all objects in this file will changed after the run::
+
+ ./dts --update-expected
+
+At the beginning, please change test_parameters according to your requirements,
+then run ./dts --update-expected to get the absolute results which will replace
+the default numbers 0.00 in this configuration.
+So you will have your own private configuration, and could start your tests as usual.
+
+
+Run DTS performance test with IXIA
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Now you can start DTS performance test with IXIA:
+
+.. code-block:: console
+
+ root@test1:~/dts# ./dts
+ dts:
+ DUT 192.168.1.1
+ tester: ssh root@192.168.1.1
+ ...
+ pktgen: ssh root@192.168.1.1
+ pktgen: tclsh
+ pktgen: source ./IxiaWish.tcl
+ pktgen: set ::env(IXIA_VERSION) 9.00
+ pktgen: package req IxTclHal
+ pktgen: ixConnectToTclServer 192.168.2.1
+ pktgen: ixLogin IxiaTclUser
+ pktgen: ixConnectToChassis 192.168.2.1
+ pktgen: set chasId [ixGetChassisID 192.168.2.1]
+ pktgen: ixClearOwnership [list [list 1 3 1] [list 1 3 2]]
+ pktgen: ixTakeOwnership [list [list 1 3 1] [list 1 3 2]] force
+ pktgen: stat getLineSpeed 1 3 1
+ pktgen: stat getLineSpeed 1 3 2
+ ...
+
+ TestNicSingleCorePerf: Test Case test_perf_nic_single_core Begin
+ TestNicSingleCorePerf: Executing Test Using cores: ['28', '29'] of config 1C/1T
+ TestNicSingleCorePerf: Test running at parameters: framesize: 64, rxd/txd: 512
+ dut.192.168.1.1: x86_64-native-linuxapp-gcc/app/dpdk-testpmd -l 28,29 -n 6 -a 0000:af:00.0 -a 0000:b1:00.0 -- -i --portmask=0x3 --rxq=2 --txq=2 --txd=512 --rxd=512 --nb-cores=1
+ dut.192.168.1.1: start
+ pktgen: stat getLineSpeed 1 1 1
+ pktgen: stat getLineSpeed 1 1 2
+ pktgen: scp -v dumppcap.py root@192.168.1.1:~/
+ pktgen: scapy -c dumppcap.py 2>/dev/null
+ pktgen: scp -v dumppcap.py root@192.168.1.1:~/
+ pktgen: scapy -c dumppcap.py 2>/dev/null
+ pktgen: scp -v dumppcap.py root@192.168.1.1:~/
+ pktgen: scapy -c dumppcap.py 2>/dev/null
+ pktgen: scp -v dumppcap.py root@192.168.1.1:~/
+ pktgen: scapy -c dumppcap.py 2>/dev/null
+ pktgen: begin traffic ......
+ tester: scp -v ixiaConfig.tcl root@192.168.1.1:~/
+ pktgen: source ixiaConfig.tcl
+ pktgen: begin get port statistic ...
+ pktgen: stat getRate statAllStats 1 3 2
+ pktgen: stat cget -framesReceived
+ pktgen: stat cget -bitsReceived
+ pktgen: stat cget -oversize
+ pktgen: stat getRate statAllStats 1 3 1
+ pktgen: stat cget -framesReceived
+ pktgen: stat cget -bitsReceived
+ pktgen: stat cget -oversize
+ pktgen: stat getRate statAllStats 1 3 2
+ pktgen: stat cget -framesReceived
+ pktgen: stat cget -bitsReceived
+ pktgen: stat cget -oversize
+ pktgen: stat getRate statAllStats 1 3 1
+ pktgen: stat cget -framesReceived
+ pktgen: stat cget -bitsReceived
+ pktgen: stat cget -oversize
+ pktgen: throughput: pps_rx 69504677.000000, bps_rx 35586394625.000000
+ pktgen: ixStopTransmit portList
+ pktgen: traffic completed.
+ dut.192.168.1.1: stop
+ dut.192.168.1.1: quit
+ TestNicSingleCorePerf: Trouthput of framesize: 64, rxd/txd: 512 is :69.504677 Mpps
+ ...
+
+ TestNicSingleCorePerf:
+ +----------+------------+---------+-------------+---------+---------------------+-----------------------+
+ | Fwd_core | Frame Size | TXD/RXD | Throughput | Rate | Expected Throughput | Throughput Difference |
+ +==========+============+=========+=============+=========+=====================+=======================+
+ | 1C/1T | 64 | 512 | 69.505 Mpps | 93.414% | 0.000 Mpps | 69.505 Mpps |
+ +----------+------------+---------+-------------+---------+---------------------+-----------------------+
+ | 1C/1T | 64 | 2048 | 51.078 Mpps | 68.649% | 0.000 Mpps | 51.078 Mpps |
+ +----------+------------+---------+-------------+---------+---------------------+-----------------------+
+ | 1C/2T | 64 | 512 | 74.404 Mpps | 99.999% | 0.000 Mpps | 74.404 Mpps |
+ +----------+------------+---------+-------------+---------+---------------------+-----------------------+
+ | 1C/2T | 64 | 2048 | 67.851 Mpps | 91.192% | 0.000 Mpps | 67.851 Mpps |
+ +----------+------------+---------+-------------+---------+---------------------+-----------------------+
+ TestNicSingleCorePerf: Test Case test_perf_nic_single_core Result PASSED:
+
+
+Test result
+~~~~~~~~~~~
+
+After the Test Suite finished the validation, we can find the result files as below in output folder.
+
+.. code-block:: console
+
+ fortville_25g_single_core_perf.json dts.log TestNicSingleCorePerf.log test_results.json
+
+The performance case will save the data results in the jison file.
+And the pattern is "nic name + suite name.json".
+Below is the json file of nic_single_core:
+
+.. code-block:: console
+
+ vim fortville_25g_single_core_perf.json
+
+ {"test_perf_nic_single_core": [{
+ "performance": [{"name": "Throughput", "value": 69.505, "unit": "Mpps", "delta": 69.505}],
+ "parameters": [{"name": "Txd/Rxd", "value": 512, "unit": "descriptor"},
+ {"name": "frame_size", "value": 64, "unit": "bytes"},
+ {"name": "Fwd_core", "value": "1C/1T"}], "status": "PASS"},
+ {"performance": [{"name": "Throughput", "value": 51.078, "unit": "Mpps", "delta": 51.078}],
+ "parameters": [{"name": "Txd/Rxd", "value": 2048, "unit": "descriptor"},
+ {"name": "frame_size", "value": 64, "unit": "bytes"},
+ {"name": "Fwd_core", "value": "1C/1T"}], "status": "PASS"},
+ {"performance": [{"name": "Throughput", "value": 74.404, "unit": "Mpps", "delta": 74.404}],
+ "parameters": [{"name": "Txd/Rxd", "value": 512, "unit": "descriptor"},
+ {"name": "frame_size", "value": 64, "unit": "bytes"},
+ {"name": "Fwd_core", "value": "1C/2T"}], "status": "PASS"},
+ {"performance": [{"name": "Throughput", "value": 67.851, "unit": "Mpps", "delta": 67.851}],
+ "parameters": [{"name": "Txd/Rxd", "value": 2048, "unit": "descriptor"},
+ {"name": "frame_size", "value": 64, "unit": "bytes"},
+ {"name": "Fwd_core", "value": "1C/2T"}], "status": "PASS"}]}
+
+
+You can set your own expectations in con/suite.cfg based on the json data.
+If the actual data differs too much from the expected data, the case fails.
diff --git a/doc/dts_gsg/usr_guide/results.rst b/doc/dts_gsg/usr_guide/results.rst
new file mode 100644
index 0000000..3ec08d8
--- /dev/null
+++ b/doc/dts_gsg/usr_guide/results.rst
@@ -0,0 +1,101 @@
+Test Result
+===========
+
+Overview
+--------
+
+After DTS finished the validation, we can find the result files similar as below in output folder.
+
+.. code-block:: console
+
+ rst_report dts.log statistics.txt TestHelloWorld.log test_results.json test_results.xls
+
+* rst_report: contains the result RST file of performance data
+* dts.log: Full execution log of DTS framework
+* statstics.txt: summary statistics of DTS executed suites
+* TestHelloWorld.log: log message of Test suite: HelloWorld
+* test_result.json: json format result file
+* test_result.xls: excel format result file
+
+Statistics
+----------
+
+You can go through the summary of execution result via statistic.txt. This file includes the number of passed test cases, the number of failed case, the number of blocked and pass ratio.
+
+Please see example as the following. You can cat the sample file, then show this information of execution, totally executed two test cases, all cases passed the criterion and no failed or blocked cases.
+
+.. code-block:: console
+
+ [root@tester output]# cat statistics.txt
+ dpdk_version = 21.02.0
+ Passed = 2
+ Failed = 0
+ Blocked = 0
+ Pass rate = 100.0
+
+Details
+-------
+
+DTS provides 2 formats for test results, one is json, and the other is excel.
+If you need more detail information of test result, either of them is good to check.
+Both of them contain case names and results, also the failure reasons.
+
+* JSON result: result.json
+
+.. code-block:: console
+
+ {
+ "192.168.1.1": {
+ "dpdk_version": "21.02.0",
+ "nic": {
+ "driver": "vfio-pci",
+ "firmware": "8.00 0x80008c1a 1.2766.0",
+ "kdriver": "i40e-2.13.10",
+ "name": "fortville_25g"
+ },
+ "x86_64-native-linuxapp-gcc": {
+ "hello_world/test_hello_world_all_core": "passed"
+ "hello_world/test_hello_world_single_core": "passed"
+ }
+ }
+ }
+
+
+* Excel result: test_result.xls
+
+.. figure:: image/dts_result.png
+
+Logs
+----
+
+If you want to track more details about the process of each suite, please go to log file which named by this suite, all related information will stored in this file.
+
+Please see example for TestHelloWorld suite log as the following. This log file showed that application helloworld sent hello message from core1, and finally matched the pass criterion.
+
+.. code-block:: console
+
+ 31/12/2020 11:04:00 INFO:
+ TEST SUITE : TestHelloWorld
+ 31/12/2020 11:04:00 INFO: NIC : fortville_25g
+ 31/12/2020 11:04:00 SUITE_DUT_CMD: meson configure -Dexamples=helloworld x86_64-native-linuxapp-gcc
+ 31/12/2020 11:04:01 SUITE_DUT_CMD: ninja -C x86_64-native-linuxapp-gcc
+ 31/12/2020 11:04:07 SUITE_DUT_OUTPUT: ninja: Entering directory `x86_64-native-linuxapp-gcc'^M
+ [0/1] Regenerating build files.^M
+ The Meson build system^M
+ Version: 0.55.3^M
+ Source dir: /root/dpdk^M
+ Build dir: /root/dpdk/x86_64-native-linuxapp-gcc^M
+ Build type: native build^
+ …
+ Build targets in project: 998^M
+ Found ninja-1.10.0.git.kitware.jobserver-1 at /usr/local/bin/ninja^M
+ [1/2] Compiling C object examples/dpdk-helloworld.p/helloworld_main.c.o^M
+ [2/2] Linking target examples/dpdk-helloworld
+ 31/12/2020 11:04:09 INFO: Test Case test_hello_world_single_core Begin
+ 31/12/2020 11:04:13 SUITE_DUT_CMD: ./x86_64-native-linuxapp-gcc/examples/dpdk-helloworld -l 1 -n 4 --file-prefix=dpdk_10243_20201231110241
+ SUITE_DUT_OUTPUT: EAL: Detected 72 lcore(s)^M
+ …
+ hello from core 1
+ 31/12/2020 11:04:15 INFO: Test Case test_hello_world_single_core Result PASSED:
+ 31/12/2020 11:04:25 INFO:
+ TEST SUITE ENDED: TestHelloWorld
diff --git a/doc/dts_gsg/usr_guide/sys_reqs.rst b/doc/dts_gsg/usr_guide/sys_reqs.rst
new file mode 100644
index 0000000..8b70abb
--- /dev/null
+++ b/doc/dts_gsg/usr_guide/sys_reqs.rst
@@ -0,0 +1,131 @@
+System Requirements
+===================
+
+This chapter describes the packages required to deploy DTS, including Tester and DUT.
+Tester and DUT should have one interface connected to the same internet, so that they can be accessed by each other from local IP address.
+The tester and DUT are recommended to install the latest Centos, Redhat or Ubuntu for easily installing DTS(DPDK Test Suite) or DPDK required modules.
+
+.. note::
+
+ Uubuntu 20.04 are installed for Tester and DUT, and The setup instruction and required packages may be different on different operation systems.
+
+Firewall should be disabled on Tester and DUT so that all packets can be accepted by NIC Interface.
+
+.. code-block:: console
+
+ systemctl disable firewalld.service
+
+
+SSH Service
+-----------
+
+Since DPDK Test Suite Tester communicates with DUT via SSH, please install and start sshd service in your Tester and DUT.
+
+.. code-block:: console
+
+ apt-get install sshd
+ systemctl enable ssh
+
+Generally DTS use Linux username and password to login, but it also supports to use authorized login.
+For create authorized login session, user needs to generate RSA authentication keys to ssh connectioni:
+
+.. code-block:: console
+
+ ssh-keygen -t rsa
+
+Python modules
+--------------
+
+To run DTS, `Python3` must be installed, and it uses the following packages:
+
+* xlwt: it is used to generate spreadsheet files which compatible with MS Excel 97/2000/XP/2003 XLS files。
+* numpy: it provides method to deal with array-processing test results.
+* pexpect: it provides API to automate interactive SSH sessions.
+* docutils:it is a modular system for processing documentation into useful formats, such as HTML, XML, and LaTeX
+* pcapy: it is a Python extension module that interfaces with the libpcap packet capture library. Pcapy enables python scripts to capture packets on the network.
+* xlrd: it is a Python module that extracts data from Excel spreadsheets.
+* threadpool: it is a Python module that maintains a pool of worker threads to perform time consuming operations in parallel.
+* scapy: it is a Python program that enables the user to send, sniff and dissect and forge network packets.
+
+They are recorded in `requirements.txt`.
+
+.. code-block:: console
+
+ [root@tester ~]# cat requirements.txt
+ ...
+ xlwt==1.3.0
+ pexpect==4.7.0
+ numpy==1.18.5
+ docutils
+ pcapy
+ xlrd
+ scapy==2.4.4
+ threadpool
+
+Recommend installing them quickly with following commands:
+
+.. code-block:: console
+
+ apt-get install python3-pip
+ pip3 install -r ../requirements.txt
+
+DTS uses python module scapy to forge or decode packets of a wide number of protocols, send them over the wire, capture them, and analyse the packets.
+We recommend installing scapy-2.4.4, as some protocol such as PFCP, GTPPDUSessionContainer are supported from this version.
+
+.. code-block:: console
+
+ pip3 install scapy # install default version
+ pip3 install scapy==2.4.4 # install specific version
+
+Here are some differences between scapy 2.4.4 and scapy 2.4.3 about the packet layer:
+
+.. table:: Differences between scapy 2.4.3 with scapy 2.4.4
+
+ +------------------------+---------------------------------+-----------------------------------------------+-------------------------------------------------------+
+ | Layer | packet in scapy 2.4.3 | packet in scapy 2.4.4 | Comments |
+ +========================+=================================+===============================================+=======================================================+
+ | PPP | PPP(proto=0xc021) | PPP(b\'\\xc0\\x21\') | PPP protocol filed length is 1 byte in scapy2.4.4 |
+ +------------------------+---------------------------------+-----------------------------------------------+-------------------------------------------------------+
+ | L2TP | L2TP(\'\\x00\\x00\\x00\\x11\') | L2TP(b\'\\x00\\x00\\x00\\x11\') | L2TP is byte type in scapy2.4.4 |
+ +------------------------+---------------------------------+-----------------------------------------------+-------------------------------------------------------+
+ | PFCP | N/A | PFCP(S=1, seid=1) | PFCP is not supported in scapy2.4.3 |
+ +------------------------+---------------------------------+-----------------------------------------------+-------------------------------------------------------+
+ | GTPPDUSessionContainer | N/A | GTPPDUSessionContainer(type=0, P=1, QFI=0x34) | GTPPDUSessionContainer is not supported in scapy2.4.3 |
+ +------------------------+---------------------------------+-----------------------------------------------+-------------------------------------------------------+
+
+BIOS Setting Prerequisite on x86
+--------------------------------
+
+For the majority of platforms, no special BIOS settings for Tester and DUT.
+DPDK prefers devices bound to ``vfio-pci`` kernel module, therefore, `VT-x` and `VT-d` should be enabled.
+
+.. code-block:: console
+
+ Advanced -> Integrated IO Configuration -> Intel(R) VT for Directed I/O <Enabled>
+ Advanced -> Processor Configuration -> Intel(R) Virtualization Technology <Enabled>
+
+DPDK running Prerequisite
+-------------------------
+
+Hugepage support is required for the large memory pool allocation used for packet buffers.
+DPDK performance will be imporved more with 1G page size than 2M, therefore, recommend to use 1G pages for DPDK.
+The following options should be passed to Linux Cmdline:
+
+.. code-block:: console
+
+ hugepagesz=1G hugepages=16 default_hugepagesz=1G
+
+For more detail information of DPDK requirements, please refer to `Data Plane Development Kit Getting Started Guide <http://dpdk.org/doc/guides>`_.
+
+Performance testing requirements
+--------------------------------
+
+DTS supports three kinds of traffic generators: `Scapy`, `TRex` and `Ixia IxExplorer`. Scapy is for functional testing, TRex and `Ixia IxExplorer` are for performance testing. The mechanism in DTS that mananges traffic generators for performance is called `Pktgen`.
+
+`Ixia IxExplorer` is the principal means used to program Ixia hardware and to perform testing on network devices. Ixia is a hardware traffic generator product of `keysight <https://www.keysight.com>`_ company. DTS requires to install TCL (Tool Command Language) package to connect and control `Ixia IxExplorer`:
+
+.. code-block:: console
+
+ apt-get install tcl
+
+`TRex <https://trex-tgn.cisco.com>`_ is an open source software traffic generator fuelled by DPDK. It generates L3-7 traffic and provides in one tool capabilities. DTS requires to install `Trex` and configure it before lunching DTS.
diff --git a/doc/dts_gsg/usr_guide/trex.rst b/doc/dts_gsg/usr_guide/trex.rst
new file mode 100644
index 0000000..e8b1fe9
--- /dev/null
+++ b/doc/dts_gsg/usr_guide/trex.rst
@@ -0,0 +1,377 @@
+Practice with TRex
+==================
+
+Download TREX
+-------------
+TREX should be installed in Tester, it could be downloaded from http://trex-tgn.cisco.com/trex/release/.
+We recommend to use the latest version v2.88.
+
+.. code-block:: console
+
+ wget http://trex-tgn.cisco.com/trex/release/v2.88.tar.gz
+
+To read more about T-Rex stateless mode, read the
+`T-Rex stateless support guide <https://trex-tgn.cisco.com/trex/doc/trex_stateless.html>`__.
+
+Configure TREX
+--------------
+
+Extract the downloaded TREX tarball
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+Extract the downloaded TREX file to /opt/trex/::
+
+ root@tester:/opt# mkdir trex
+ root@tester:/opt# cd trex
+ root@tester:/opt/trex# tar -zxvf v2.88.tar.gz
+ v2.88/
+ v2.88/_t-rex-64-debug
+ v2.88/t-rex-64-debug
+ ...
+ v2.88/trex_client_v2.88.tar.gz
+
+Generate Configure File
+~~~~~~~~~~~~~~~~~~~~~~~~
+
+Identify the performance test ports in tester
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+execute the command like below to list the ports::
+
+ root@tester:/opt/trex/v2.88# ./dpdk_setup_ports.py -s
+
+ Network devices using DPDK-compatible driver
+ ============================================
+ <none>
+
+ Network devices using kernel driver
+ ===================================
+ 0000:03:00.0 'VMXNET3 Ethernet Controller' if=ens160 drv=vmxnet3 unused=igb_uio,vfio-pci,uio_pci_generic *Active*
+ 0000:0b:00.0 'Device 1592' if=ens192f0 drv=ice unused=igb_uio,vfio-pci,uio_pci_generic
+ 0000:0b:00.1 'Device 1592' if=ens192f1 drv=ice unused=igb_uio,vfio-pci,uio_pci_generic
+ Other network devices
+ =====================
+ <none>
+
+Generate Configure File
+^^^^^^^^^^^^^^^^^^^^^^^
+Assume that we use 0000:0b:00.0, 0000:0b:00.1 to connect to DUT port.
+And the ports topology as below::
+
+ trex.0 (0b:00.0/40:a6:b7:0b:55:78) <-------> DUT port 0 (05:00.0/b4:96:91:9f:63:68)
+ trex.1 (0b:00.1/40:a6:b7:0b:55:79) <-------> DUT port 1 (05:00.1/b4:96:91:9f:63:69)
+
+We need to generate the trex config file as below::
+
+ root@tester:/opt/v2.88# ./dpdk_setup_ports.py -i
+ By default, IP based configuration file will be created. Do you want to use MAC based config? (y/N)y
+ +----+------+---------+-------------------+--------------------------------------------+---------+----------+----------+
+ | ID | NUMA | PCI | MAC | Name | Driver | Linux IF | Active |
+ +====+======+=========+===================+============================================+=========+==========+==========+
+ | 0 | -1 | 03:00.0 | 00:0c:29:29:30:80 | VMXNET3 Ethernet Controller | vmxnet3 | ens160 | *Active* |
+ +----+------+---------+-------------------+--------------------------------------------+---------+----------+----------+
+ | 1 | -1 | 0b:00.0 | 40:a6:b7:0b:55:78 | Device 1592 | ice | ens192f0 | |
+ +----+------+---------+-------------------+--------------------------------------------+---------+----------+----------+
+ | 2 | -1 | 0b:00.1 | 40:a6:b7:0b:55:79 | Device 1592 | ice | ens192f1 | |
+ +----+------+---------+-------------------+--------------------------------------------+---------+----------+----------+
+ Please choose an even number of interfaces from the list above, either by ID, PCI or Linux IF
+ Stateful will use order of interfaces: Client1 Server1 Client2 Server2 etc. for flows.
+ Stateless can be in any order.
+ Enter list of interfaces separated by space (for example: 1 3) : 1 2
+ For interface 1, assuming loopback to its dual interface 2.
+ Destination MAC is 40:a6:b7:0b:55:79. Change it to MAC of DUT? (y/N).y
+ Please enter a new destination MAC of interface 1: b4:96:91:9f:63:68
+ For interface 2, assuming loopback to its dual interface 1.
+ Destination MAC is 40:a6:b7:0b:55:78. Change it to MAC of DUT? (y/N).y
+ Please enter a new destination MAC of interface 2: b4:96:91:9f:63:69
+ Print preview of generated config? (Y/n)Y
+ ### Config file generated by dpdk_setup_ports.py ###
+
+ - version: 2
+ interfaces: ['0b:00.0', '0b:00.1']
+ port_info:
+ - dest_mac: b4:96:91:9f:63:68
+ src_mac: 40:a6:b7:0b:55:78
+ - dest_mac: b4:96:91:9f:63:69
+ src_mac: 40:a6:b7:0b:55:79
+
+ platform:
+ master_thread_id: 0
+ latency_thread_id: 1
+ dual_if:
+ - socket: 0
+ threads: [2,3,4,5,6,7]
+
+ Save the config to file? (Y/n)Y
+ Default filename is /etc/trex_cfg.yaml
+ Press ENTER to confirm or enter new file:
+ File /etc/trex_cfg.yaml already exist, overwrite? (y/N)Y
+ Saved to /etc/trex_cfg.yaml.
+ root@tester:/opt/trex/v2.88#
+
+We could not modify the DUT mac during the configuration and modify it in the generated file /etc/trex_cfg.yaml.
+
+Modify Configure File
+^^^^^^^^^^^^^^^^^^^^^
+Make sure the DUT mac of the generated TREX file is correct, and add prefix and limit_memory is better::
+
+ root@tester:/opt/trex/v2.88# cat /etc/trex_cfg.yaml
+ ### Config file generated by dpdk_setup_ports.py ###
+
+ - version: 2
+ interfaces: ['0b:00.0', '0b:00.1']
+ prefix: TREX
+ limit_memory: 4096
+ port_info:
+ - dest_mac: b4:96:91:9f:63:68
+ src_mac: 40:a6:b7:0b:55:78
+ - dest_mac: b4:96:91:9f:63:69
+ src_mac: 40:a6:b7:0b:55:79
+
+ platform:
+ master_thread_id: 0
+ latency_thread_id: 1
+ dual_if:
+ - socket: 0
+ threads: [2,3,4,5,6,7]
+
+ root@tester:/opt/trex/v2.88#
+
+Replace system scapy with TREX scapy
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+As the know trex issue -- trex scapy lib will be conflict with scapy installed in OS, we need the replace the scapy
+in system with trex scapy.
+
+#. backup your scapy::
+
+ cp -rf /usr/local/lib/python3.6/dist-packages/scapy /usr/local/lib/python3.6/dist-packages/scapy_backup
+
+#. unify scapy version with trex::
+
+ cp -rf /opt/trex/v2.88/external_libs/scapy-2.4.3/scapy/ /usr/local/lib/python3.6/dist-packages/scapy
+
+Configure DTS
+--------------
+
+Configure execution.cfg
+~~~~~~~~~~~~~~~~~~~~~~~
+Add the performance test suite and set perf=true::
+
+ root@tester:dts# cat execution.cfg
+ [Execution1]
+ crbs=192.168.1.1
+ drivername=vfio-pci
+ build_type=meson
+ test_suites=
+ tso,
+ targets=
+ x86_64-native-linuxapp-gcc
+ parameters=nic_type=cfg:perf=true
+ root@tester:dts#
+
+Configure conf/crbs.cfg
+~~~~~~~~~~~~~~~~~~~~~~~
+Set the pktgen_group=trex or pktgen_group=TREX, this item is case insensitive::
+
+ root@tester:dts# cat conf/crbs.cfg
+ [192.168.1.1]
+ dut_ip=192.168.1.1
+ dut_user=root
+ dut_passwd=dutpwd
+ os=linux
+ dut_arch=
+ tester_ip=192.168.1.2
+ tester_passwd=testerpwd
+ ixia_group=
+ pktgen_group=trex
+ channels=4
+ bypass_core0=True
+
+Configure conf/ports.cfg
+~~~~~~~~~~~~~~~~~~~~~~~~~
+This configuration is just same with PF function test, so if you have completed some functional test,
+you have no need to modify the conf/ports.cfg, just like below::
+
+ root@tester:dts# cat conf/ports.cfg
+ [192.168.1.1]
+ ports =
+ pci=0000:05:00.0,peer=0000:0b:00.0;
+ pci=0000:05:00.1,peer=0000:0b:00.1;
+
+In addition, it could be configured as below::
+
+ root@tester:dts# cat conf/ports.cfg
+ [192.168.1.1]
+ ports =
+ pci=0000:05:00.0,peer=TREX:0;
+ pci=0000:05:00.1,peer=TREX:1;
+
+We recommend to use the first format configuration, as it has no need to do modification when we do functional test.
+
+Configure conf/pktgen.cfg
+~~~~~~~~~~~~~~~~~~~~~~~~~~
+Fill in the conf/pktgen.cfg with your TREX setting, for the first time, you should set start_trex=yes.
+Set the IP address of the device which you installed TREX into item ‘server=’, it should be the tester IP.
+The configuration should as below::
+
+ root@tester:dts# cat conf/pktgen.cfg
+ [TREX]
+ trex_root_path=/opt/trex/v2.88
+ trex_lib_path=/opt/trex/v2.88/automation/trex_control_plane/interactive
+ config_file=/etc/trex_cfg.yaml
+ server=192.168.1.1
+ pcap_file=/opt/trex/v2.88/stl/sample.pcap
+ core_num=4
+ #core_mask=0x3
+ ip_src=16.0.0.1
+ ip_dst=10.0.0.1
+ warmup=15
+ duration=-1
+ start_trex=yes
+
+As the trex_lib_path may be different in different versions, you could find the correct path as blow command::
+
+ root@tester:/opt/trex/v2.88# find . -name trex_stl_lib
+ ./automation/trex_control_plane/interactive/trex_stl_lib
+ root@tester:/opt/trex/v2.88#
+
+
+Run DTS performance test with TREX
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Now you can start DTS performance test with TREX::
+
+ root@tester:/home/zhaohy/dts# ./dts
+ dts:
+ DUT 192.168.1.1
+ tester: ssh root@192.168.1.1
+ ...
+ pktgen: ssh root@192.168.1.1
+ pktgen: cd /opt/trex/v2.88;./t-rex-64 -i --cfg /etc/trex_cfg.yaml -c 4
+ pktgen: Starting Scapy server..... Scapy server is started
+ Trying to bind to igb_uio ...
+ /usr/bin/python3 dpdk_nic_bind.py --bind=igb_uio 0000:0b:00.0 0000:0b:00.1
+ ...
+ TestTSO: Test Case test_perf_TSO_2ports Begin
+ dut.10.240.183.72:
+ tester:
+ TestTSO: Executing PMD using 1S/1C/2T
+ dut.10.240.183.72: x86_64-native-linuxapp-gcc/app/dpdk-testpmd -l 1,45 -n 4 -a 0000:05:00.0 -a 0000:05:00.1 --file-prefix=dpdk_31529_20210324143008 -- -i --rxd=512 --txd=512 --burst=32 --rxfreet=64 --mbcache=128 --portmask=0x3 --max-pkt-len=9000 --txpt=36 --txht=0 --txwt=0 --txfreet=32 --txrst=32
+ dut.10.240.183.72: EAL: Detected 88 lcore(s)
+ ...
+ pktgen: Rx Port 0 stats:
+ rx_port: 0, rx_bps: 25354096640.000000, rx_pps: 1239130.250000
+ pktgen: throughput: pps_rx 5463897.750000, bps_rx 50961129472.000000
+ pktgen: traffic completed.
+ ...
+ TestTSO:
+ +------------+---------------+------------+
+ | Frame Size | 1S/1C/2T Mpps | % linerate |
+ +============+===============+============+
+ | 128 | 5.371 | 4 |
+ +------------+---------------+------------+
+ | 2500 | 5.464 | 56 |
+ +------------+---------------+------------+
+ TestTSO: Test Case test_perf_TSO_2ports Result PASSED
+
+FAQ
+---
+
+dpdk hugepage management conflict issue
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+trex use older dpdk version than we release cycle source code. When dpdk change
+the memory management merchanism, trex will meet the following issue.
+
+Trex should run on an independent platform. DUT/Trex should run on two platforms:
+
+* one is used as TESTER and trex server, another one is used as DUT.(dts/pktgen)
+* one is used as trex server, another one is used as DUT/TESTER.(recommended scheme)
+ This scheme can make sure that trex run on its full status capability.
+
+When trex run with dts on the same platform, trex server sometimes boot up
+failed for hugepage error.
+
+.. code-block:: console
+
+ ./t-rex-64 -i --stl -k 4
+
+ Starting Scapy server..... Scapy server is started
+ Trying to bind to igb_uio ...
+ /usr/bin/python3 dpdk_nic_bind.py --bind=igb_uio 0000:85:00.0 0000:8a:00.1
+ The ports are bound/configured.
+ Starting TRex v2.41 please wait ...
+ EAL: Can only reserve 1766 pages from 4096 requested
+ Current CONFIG_RTE_MAX_MEMSEG=256 is not enough
+ Please either increase it or request less amount of memory.
+ EAL: FATAL: Cannot init memory
+
+ EAL: Cannot init memory
+
+ You might need to run ./trex-cfg once
+ EAL: Error - exiting with code: 1
+ Cause: Invalid EAL arguments
+
+trex quit when using Niantic
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+when bind dut NNT port to igb_uio, peer port will get a link down status, then
+trex server using NNT nic will quit.
+
+.. code-block:: console
+
+ WATCHDOG: task 'master' has not responded for more than 2.00044 seconds - timeout is 2 seconds
+
+ *** traceback follows ***
+
+ 1 0x55a7c779561a ./_t-rex-64(+0x12761a) [0x55a7c779561a]
+ 2 0x7f23da4be1b0 /lib64/libpthread.so.0(+0x121b0) [0x7f23da4be1b0]
+ 3 0x55a7c7942d40 rte_delay_us_block + 128
+ 4 0x55a7c798d731 ixgbe_setup_mac_link_multispeed_fiber + 337
+ 5 0x55a7c79a8f14 ./_t-rex-64(+0x33af14) [0x55a7c79a8f14]
+ 6 0x55a7c7954c72 rte_eth_link_get_nowait + 114
+ 7 0x55a7c776a988 DpdkTRexPortAttr::update_link_status_nowait() + 24
+ 8 0x55a7c77856a6 CGlobalTRex::handle_slow_path() + 118
+ 9 0x55a7c7785ad7 CGlobalTRex::run_in_master() + 759
+ 10 0x55a7c7785e3c ./_t-rex-64(+0x117e3c) [0x55a7c7785e3c]
+ 11 0x55a7c793efba rte_eal_mp_remote_launch + 346
+ 12 0x55a7c7789e1e main_test(int, char**) + 1038
+ 13 0x7f23d9417f2a __libc_start_main + 234
+ 14 0x55a7c7719b9d ./_t-rex-64(+0xabb9d) [0x55a7c7719b9d]
+
+
+ *** addr2line information follows ***
+
+ ??:0
+ ??:0
+ ??:0
+ ??:0
+ ??:0
+ ??:0
+ ??:0
+ ??:0
+ ??:0
+ ??:0
+ ??:0
+ ??:0
+ ??:0
+ ??:0
+
+
+ ./t-rex-64: line 80: 25870 Aborted (core dumped) ./_$(
+
+other issues
+~~~~~~~~~~~~
+
+#. linux kernel version should not be too low.
+
+#. Trex only works with even number link peers.
+
+#. Trex only works with nics, which are using the same driver.
+
+#. Before boot up trex, please make sure the peer ports are on up status.
+
+#. If you have ran dpdk on the platform which you want to deploy trex-server,
+ reboot the platform to make sure that trex-server can work fine.
+
+#. If using i40e driver, Trex v2.41 version need i40e nic firmware version newer than 5.02.
+
+#. trex will drop the received packet, which dst mac is the port mac address.
diff --git a/doc/dts_gsg/usr_guide/usage.rst b/doc/dts_gsg/usr_guide/usage.rst
new file mode 100644
index 0000000..ef729a9
--- /dev/null
+++ b/doc/dts_gsg/usr_guide/usage.rst
@@ -0,0 +1,350 @@
+Usage
+=====
+
+Configuration
+-------------
+
+Configuring your own execution file
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+First of all, you must configure execution.cfg as below:
+
+.. code-block:: console
+
+ [Execution1]
+ crbs=<CRB IP Address>
+ drivername=vfio-pci
+ build_type=meson
+ rx_mode=avx512
+ test_suites=
+ hello_world,
+ targets=
+ x86_64-native-linuxapp-gcc
+ parameters=nic_type=cfg:func=true
+
+* crbs: IP address of the DUT. The detail information is defined in file conf/crbs.cfg.
+* drivername: the driver devices used by DPDK bound to.
+* build_type: the tool for building DPDK, it can be meson and makefile. DPDK 20.11+ only uses meson and ninja.
+* rx_mode: vector instructions used in tests, it can be novector/sse/avx2/avx512. it is optional, if not set, dpdk uses avx2 by default.
+* test_suites: test suites and cases that to be executed. use ``:`` to separate suite and it's cases and use ``\`` to separate different cases.
+* targets: DPDK targets to be tested.
+* parameters: multiple keywords as following:
+
+ * nic_type: it is the type of the NIC to use. The types are defined in the file settings.py.
+ There's a special type named as **cfg**, which mean network information will be loaded from file conf/ports.cfg.
+ If use NIC type such as niantic, fortville_25g, it requires all DUT are the same types and no any same devices connected to Tester,
+ as DTS will test all devices connected to Tester. Therefore, recommend using **cfg**.
+ * func=true: run only functional test.
+ * perf=true: run only performance test.
+
+.. note::
+
+ The two options ``func=true`` and ``perf=true`` are mutually exclusive, as the traffic generators for functional and performance are mutually exclusive.
+
+Here are an example for functional testing:
+
+.. code-block:: console
+
+ [Execution1]
+ crbs=192.168.1.1
+ drivername=vfio-pci
+ build_type=meson
+ test_suites=
+ unit_tests_eal:test_version\test_common,
+ targets=
+ x86_64-default-linuxapp-gcc,
+ parameters=nic_type=cfg:func=true
+
+
+Configure CRB information
+~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Then please add the detail information about your CRB in conf/crbs.conf as following:
+
+.. code-block:: console
+
+ [DUT IP]
+ dut_ip=xxx.xxx.xxx.xxx
+ dut_user=root
+ dut_passwd=
+ os=linux
+ dut_arch=
+ tester_ip=xxx.xxx.xxx.xxx
+ tester_passwd=
+ pktgen_group=
+ channels=4
+ bypass_core0=True
+ dut_cores=
+
+* DUT IP: section name, same as ``crbs`` in execution.cfg.
+* dut_ip: IP address of the DUT, same as ``crbs`` in execution.cfg.
+* dut_user: User name of DUT linux account
+* dut_passwd: Password of DUT linux account
+* tester_ip: IP address of tester
+* tester_passwd: Password of Tester linux account, user name should same as dut_user
+* pktgen_group: traffic generator name, it can be ``trex`` or ``ixia``, it is optional, if not set, DTS can't do performance tests.
+* channels: number of memory channels for DPDK EAL
+* bypass_core0: skip the first core when initialize DPDK
+* dut_cores: DUT core list, eg: 1,2,3,4,5,18-22, it is optional, if it is ``None`` or not set, all core list will be used.
+
+Here are an example for functional testing:
+
+.. code-block:: console
+
+ [192.168.1.1]
+ dut_ip=192.168.1.1
+ dut_user=root
+ dut_passwd=dutpasswd
+ os=linux
+ tester_ip=192.168.1.2
+ tester_passwd=testerpasswd
+ channels=4
+ bypass_core0=True
+
+
+Configure port information
+~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+If set ``nic_type=cfg`` in execution.cfg, please add port configuration in conf/ports.cfg as following:
+
+.. code-block:: console
+
+ [DUT IP]
+ ports =
+ pci=<Pci BDF>,peer=<Pci BDF>;
+ pci=<Pci BDF>,peer=IXIA:X.Y;
+ pci=<Pci BDF>,peer=TREX:X;
+
+It supports three patterns, the first one is for functional testing, the second one is for ``IXIA``, the third one is for ``TRex``:
+
+* pci: Device pci address of DUT
+* peer: info of Tester port which connected to the DUT device:
+
+ * if it is func testing, it is pci address
+ * if pktgen is ``TRex``, the `X` in ``TREX:X`` is port id in TRex configuration file, e.g. /etc/trex_cfg.yaml.
+ * if pktgen is ``IXIA``, the `X` is card id ,and the `Y` is port id, which configured in ./conf/pktgen.cfg.
+
+Here are an example for functional testing:
+
+.. code-block:: console
+
+ [192.168.1.1]
+ ports =
+ pci=0000:06:00.0,peer=0000:81:00.0;
+ pci=0000:06:00.1,peer=0000:81:00.1;
+
+Here are an example for IXIA:
+
+.. code-block:: console
+
+ [192.168.1.1]
+ ports =
+ pci=0000:18:00.0,peer=IXIA:1.1;
+ pci=0000:18:00.1,peer=IXIA:1.2;
+
+Here are an example for TRex:
+
+.. code-block:: console
+
+ [192.168.1.1]
+ ports =
+ pci=0000:18:00.0,peer=TREX:1;
+ pci=0000:18:00.1,peer=TREX:1;
+
+
+Configure all test suites
+~~~~~~~~~~~~~~~~~~~~~~~~~
+
+conf/global_suite.cfg is a global suite configure file which is shared by all suites.
+
+.. code-block:: console
+
+ [global]
+ vf_driver=vfio-pci
+
+* vf_driver: VF driver that for VF testing, recommend keep the default value ``vfio-pci``.
+
+
+Configure your own suites
+~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Not all test suites have it's own configuration file which depended on script. If it has, the configuration file is conf/[suite_name].cfg
+For example, suite metrics has its suite configure file conf/metric.cfg:
+
+.. code-block:: console
+
+ [suite]
+ frames_cfg = { 64: 0.07, 128: 0.04, 256: 0.02, 512: 0.01, 1024: 0.01 }
+ duration = 60
+ sample_number = 3
+ rates = [100, 80, 40, 20]
+
+
+Configure your pktgen
+~~~~~~~~~~~~~~~~~~~~~
+
+Pktgen information are configured in conf/pktgen.cfg, pktgen_group must be configured too:
+
+* traffic generator is ``TRex``, set ``pktgen_group=trex`` in crbs.cfg.
+* traffic generator is ``IXIA``, set ``pktgen_group=ixia`` in crbs.cfg.
+
+Then configure conf/pktgen.cfg as following:
+
+.. code-block:: console
+
+ [TREX]
+ trex_root_path=/opt/trex/v2.84/
+ trex_lib_path=/opt/trex/v2.84/automation/trex_control_plane/interactive
+ config_file=/etc/trex_cfg.yaml
+ server=192.168.1.1 # equal to tester IP, TREX should be installed in tester
+ pcap_file=/opt/trex/v2.84/stl/sample.pacp
+ core_num=16
+ ip_src=16.0.0.1
+ ip_dst=10.0.0.1
+ warmup=15
+ duration=-1
+ start_trex=yes
+
+ [IXIA]
+ ixia_version=6.62
+ ixia_ip=xxx.xxx.xxx.xxx
+ ixia_ports=
+ card=1,port=1;
+ card=1,port=2;
+ card=1,port=3;
+ card=1,port=4;
+
+* TREX: section name for TRex.
+* trex_root_path: source code path for TRex
+* trex_lib_path: the director where dts can import Trex API
+* start_trex: whether DTS start TRex server, suggest 'yes' for one-time test, and 'no' for CI integration
+
+* IXIA: section name for IXIA.
+* ixia_version: the version of IxExplorer.
+* ixia_ip: IP of ixia
+* ixia_ports: ixia ports connected to DUT.
+
+Here are an example for TRex:
+
+.. code-block:: console
+
+ [TREX]
+ trex_root_path=/opt/trex/v2.84/
+ trex_lib_path=/opt/trex/v2.84/automation/trex_control_plane/interactive
+ config_file=/etc/trex_cfg.yaml
+ server=192.168.1.1 # equal to tester IP, TREX should be installed in tester
+ pcap_file=/opt/trex/v2.84/stl/sample.pacp
+ core_num=16
+ ip_src=16.0.0.1
+ ip_dst=10.0.0.1
+ warmup=15
+ duration=-1
+ start_trex=yes
+
+Here are an example for IXIA:
+
+.. code-block:: console
+
+ [IXIA]
+ ixia_version=9.00
+ ixia_ip=192.168.2.1
+ ixia_ports=
+ card=3,port=1;
+ card=3,port=2;
+ ixia_force100g=disable
+
+
+Running the Application
+-----------------------
+
+DTS supports multiple parameters which will select different of working mode of test framework.
+In the meantime, DTS can work with none parameter, then every parameter will set to its default value:
+
+.. code-block:: console
+
+ usage: main.py [-h] [--config-file CONFIG_FILE] [--snapshot SNAPSHOT] [--output OUTPUT] [-s]
+ [-t TEST_CASES] [-d DIR] [-v] [--debug] [--debugcase] [--re_run RE_RUN]
+ [--commands COMMANDS] [--update-expected]
+
+DTS supports the following parameters:
+
+* ``-h, --help``
+
+ Display a help message and quit.
+
+* ``--config-file CONFIG_FILE``
+
+ Execution file which contains test suites, DPDK target information and so on.
+ The default value is `execution.cfg`.
+
+* ``--snapshot SNAPSHOT``
+
+ Snapshot .tgz file to use as input。
+ The deault value is `./dep/dpdk.tar.gz`.
+
+* ``--output OUTPUT``
+
+ Output directory where dts log and result saved.
+ The default value is `./output`.
+
+* ``-s, --skip-setup``
+
+ Skip all possible setup steps done on both DUT and tester.
+
+* ``-t TEST_CASES, --test-cases TEST_CASES``
+
+ Execute only the specific test cases.
+ The default value is all test cases.
+
+* ``-d DIR``
+
+ Output directory where dpdk package is extracted.
+
+* ``-v, --verbose``
+
+ Enable verbose output, all message output on screen.
+
+* ``--debug``
+
+ Enable debug mode, user can enter debug mode in process with `ctrl+c`
+ User can do further debug by attached to sessions or call pdb module by interact interface:
+
+.. code-block:: console
+
+ help(): show help message
+ list(): list all connected sessions
+ connect(name): connect to session directly
+ exit(): exit dts
+ quit(): quit debug mode and into normal mode
+ debug(): call python debug module
+
+* ``--debugcase``
+
+ Enable debug mode with test cases.
+ DTS will hang and wait for user command before executing each test case:
+
+.. code-block:: console
+
+ rerun(): rerun current case
+ ctrl + d: exit current case
+
+* ``--re_run RE_RUN``
+
+ Times that will re-run when case failed.
+ The default value is 0, and it must be >=0.
+
+* ``--update-expected``
+
+ Enable write-back expected value of performance.
+ It requires test scripts support.
+
+Here are examples:
+
+.. code-block:: console
+
+ ./dts
+ ./dts -s
+ ./dts -s -d /home/dpdk
+ ./dts --debug
+ ./dts --debug --debugcase
+ ./dts --output test1
diff --git a/doc/dts_gsg/virtualization.rst b/doc/dts_gsg/virtualization.rst
deleted file mode 100755
index 15d7967..0000000
--- a/doc/dts_gsg/virtualization.rst
+++ /dev/null
@@ -1,617 +0,0 @@
-Virtualization Framework
-========================
-
-Design Concept
---------------
-DTS virtualization framework is based on extendible design which can support different types of hypervisors and their parameters.
-
-Suite for virtual feature should handle virtual machine creation and destruction. It only need to execute some most basic operations on guest like start, stop. There're two ways to configure virtual machine. One is configuration file, the other one is to call hypervisor internal API. Suite can choose anyway of them based on its implementation.
-
-.. note::
- If VM configurations are different between test cases, those configurations shared with all cases should be defined in suite local configuration file. Those dynamical configurations should be set by hypervisor module's API.
-
-Virtual machine DUT class is inherited from host DUT class. This mean that for vm DUT, can call the same API as DUT object.
-
-Flow Chart
-~~~~~~~~~~
-
-Below picture show the virtualization related modules working flow.
-
-.. figure:: image/virt_flow.svg
-
-System Requirements
--------------------
-
-Host Preparation
-~~~~~~~~~~~~~~~~
-
-Kernel should enable KVM. In bios feature Intel(R) Virtualization Technology should be enabled. Emulator qemu must be installed in host.
-
-.. note::
- Some features like virtio cuse request higher version than default qemu release with linux distribution. For those features, qemu should be updated to version later than 2.1.
-
-
-Guest Preparation
-~~~~~~~~~~~~~~~~~
-
-SSH connection
-""""""""""""""
-
-DTS create ssh connection to guest based on redirect guest ssh port to host port. Ssh connection will require one interface in guest which can connect to host. User should setup one default interface (e1000) in guest and make sure it can be up after guest boot up.
-
-.. note::
- Qemu process contained with one virtual DHCP server on 10.0.2.2 and will be allocated an address starting from 10.0.2.15. For more information about qemu network, please reference to https://en.wikibooks.org/wiki/QEMU/Networking.
-
-
-In qemu module, the default e1000 device's pci address is assigned to 00:1f.0 which is the very end of guest pci address. In guest, we configure udev rule and assign the default interface named as "host_connect".
-
-Add udev rule for default e1000 device:
-
-.. code-block:: console
-
- vim /etc/udev/rules.d/70-persistent-net.rules
- KERNELS=="0000:00:1f.0",SUBSYSTEMS=="pci", ACTION=="add", DRIVERS=="?*" ,KERNEL=="eth*", NAME="host_connect"
-
-Enable dhcp on default host_connect interface.
-
-.. code-block:: console
-
- vim /etc/sysconfig/network-scripts/ifcfg-host_connect
- TYPE="Ethernet"
- BOOTPROTO="dhcp"
- DEFROUTE="yes"
- DEVICE="host_connect"
- NAME="host_connect"
- ONBOOT="yes"
- PEERDNS="yes"
- PEERROUTES="yes"
- IPV6_PEERDNS="yes"
- IPV6_PEERROUTES="yes"
-
-.. code-block:: console
-
- chkconfig --level 2345 network on
-
-For network access, should disable guest firewall service.
-
-.. code-block:: console
-
- systemctl disable firewalld.service
-
-QGA connection
-""""""""""""""
-
-Install qemu guest agent, DTS will manage virtual machine through QGA if control type is 'qga'.
-
-.. code-block:: console
-
- yum install qemu-guest-agent.x86_64
-
-Console connection
-""""""""""""""""""
-
-Enable virtual machine serial console in kernel command line, DTS will manage virtual machine through serial port if control type is 'telnet' or 'socket'.
-
-.. code-block:: console
-
- console=ttyS0,115200
-
-Suite Programing
-----------------
-
-Add Configuration File
-~~~~~~~~~~~~~~~~~~~~~~
-
-Configuration file should be placed in conf/{suite_name}.cfg and in test suite this file will be loaded for VM configurations. Below is one sample for virtualization suite configuration file.
-
-The section name between [] is the VM name. Here we changed default cpu, mem, disk, UEFI configurations. And add two local configurations login and vnc into configuration file.
-For cpu parameter, we changed core number to 2 and pin these two cores to socket 1 cores for performance concern. For mem parameter, we changed guest using with hugepage backend memory. It also concerned about performance. For disk parameter, we should change it local disk image absolute path.
-For pflash parameter, we changed UEFI CODE and UEFI VARs file, which you specified when you created the VM.
-
-Login parameter should be added when guest login username and password not same as host. VNC parameter should be added when need debug guest with vnc display.
-
-.. code-block:: console
-
- # vm configuration for vhost sample case
- [vm0]
- cpu =
- model=host,number=2,cpupin=24 25;
- mem =
- size=4096,hugepage=yes;
- disk =
- file=/home/img/vm0.img,opt_format=raw,opt_if=virtio,opt_index=0,opt_media=disk;
- pflash =
- file=/home/img/flash_code.img;
- file=/home/img/flash_vars.img;
- login =
- user=root,password=tester;
- vnc =
- displayNum=1;
-
-
-Add Parameters
-~~~~~~~~~~~~~~
-Below is the brief view of the qemu parameters of vxlan sample virtual machine. These parameters are gathered into one list of python dictionary.
-
-.. code-block:: console
-
- [{'name': [{'name': 'vm0'}]},
- {'enable_kvm': [{'enable': 'yes'}]},
- {'control': [{'type': 'telnet'}]},
- {'daemon': [{'enable': 'yes'}]},
- {'monitor': [{'path': '/tmp/vm0_monitor.sock'}]},
- {'net': [{'opt_addr': '1f', 'type': 'nic', 'opt_vlan': '0'}, {'type': 'user', 'opt_vlan': '0'}]},
- {'device': [{'opt_mac': '00:00:20:00:00:20', 'opt_path': './vhost-net', 'driver': 'vhost-user'}, {'opt_mac': '00:00:20:00:00:21', 'opt_path': './vhost-net', 'driver': 'vhost-user'}]},
- {'cpu': [{'model': 'host', 'number': '4', 'cpupin': '24 25 26 27'}]},
- {'mem': [{'hugepage': 'yes', 'size': '4096'}]},
- {'disk': [{'file': '/storage/vm-image/vm0.img', 'opt_format': 'raw', 'opt_if': 'virtio', 'opt_index': '0', 'opt_media': 'disk'}]},
- {'pflash': [{'file': '/storage/vm-image/flash_code.img'}]},
- {'pflash': [{'file': '/storage/vm-image/flash_vars.img'}]},
- {'login': [{'password': 'tester', 'user': 'root'}]},
- {'vnc': [{'displayNum': '1'}]}]
-
-
-In vxlan sample suite, we need to support socket based vhost-user network devices. Qemu command for vhost-user device will like as below.
-
-.. code-block:: console
-
- -chardev socket,path=/path/to/socket,id=chr0 \
- -netdev type=vhost-user,id=net0,chardev=chr0 \
- -device virtio-net-pci,netdev=net0,mac=00:00:20:00:00:20
-
-For user configuration, we should only care about socket path and mac address. Configuration of vhost-user device should like below.
-
-.. code-block:: console
-
- device =
- driver=vhost-user,opt_path=./vhost-net,opt_mac=00:00:20:00:00:20
- driver=vhost-user,opt_path=./vhost-net,opt_mac=00:00:20:00:00:21
-
-Python code should like below, vxlan_sample suite chosen this way.
-
-.. code-block:: console
-
- vm_params = {}
- vm_params['driver'] = 'vhost-user'
- vm_params['opt_path'] = './vhost-net'
- vm_params['opt_mac'] = "00:00:20:00:00:20"
- self.vm.set_vm_device(**vm_params)
- vm_params['opt_mac'] = "00:00:20:00:00:21"
- self.vm.set_vm_device(**vm_params)
-
-If parameter is device, function add_vm_{device} will be called and device options will passed as arguments. The options will be formatted into python dictionary.
-
-.. code-block:: console
-
- {'opt_mac': '00:00:20:00:00:20', 'opt_path': './vhost-net', 'driver': 'vhost-user'}
-
- def add_vm_device(self, **options):
- if options['driver'] == 'vhost-user':
- self.__add_vm_virtio_user_pci(**options)
-
-
-In internal add virtio user device function, qemu module will generate chardev, netdev and virtio-net-pci command line in sequence.
-
-.. code-block:: console
-
- def __add_vm_virtio_user_pci(self, **options):
- if 'opt_path' in options.keys() and options['opt_path']:
- # add socket char device command line
- dev_boot_line = '-chardev socket'
- char_id = 'char%d' % self.char_idx
- dev_boot_line += separator + 'id=%s' % char_id + separator + 'path=%s' % options['opt_path']
- self.char_idx += 1
- self.__add_boot_line(dev_boot_line)
-
- # add netdev command line
- netdev_id = 'netdev%d' % self.netdev_idx
- self.netdev_idx += 1
- dev_boot_line = '-netdev type=vhost-user,id=%s,chardev=%s,vhostforce' % (netdev_id, char_id)
- self.__add_boot_line(dev_boot_line)
-
- # add virtio-net-pci command line
- opts = {'opt_netdev': '%s' % netdev_id}
- if 'opt_mac' in options.keys() and \
- options['opt_mac']:
- opts['opt_mac'] = options['opt_mac']
- self.__add_vm_virtio_net_pci(**opts)
-
-
-VM Management
-~~~~~~~~~~~~~
-
-Suite should have known that which hypervisor type based on. With virtual machine instance, suite can start, stop and check status of the guest. All infrastructures required have been made up by virtualization module, suite should not handle that.
-
-.. note::
- Test case should focus in feature validation. VM management related codes recommended to be placed in set_up_all or set_up functions.
-
-
-In vxlan sample suite, all test cases request to restart virtual machine. The backend application will be started with different parameters. So VM start up code is placed in set_up function.
-
-.. code-block:: console
-
- def set_up(self):
- """
- Run before each test case.
- """
- tep_cmd = tep_cmd_temp % {
- 'COREMASK': self.coremask,
- 'CHANNELS': self.dut.get_memory_channels(),
- 'VXLAN_PORT': self.vxlan_port, 'NB_DEVS': vm_num * 2,
- 'FILTERS': self.OUTER_INNER_VNI, 'TX_CHKS': chksum,
- 'ENCAP': encap, 'DECAP': decap}
- self.prepare_vxlan_sample_env(tep_cmd)
-
-Before VM operations, vxlan sample feature request to start tep_termination application first. To initialized hypervisor kvm instance, there're three parameters required. The first is DUT object, the second is VM name and the third is suite name.
-
-.. code-block:: console
-
- def prepare_vxlan_sample_env(self, tep_cmd):
- # remove unexpected socket
- self.dut.send_expect("rm -rf vhost-net", "# ")
-
- # start tep_termination first
- self.dut.send_expect(tep_cmd, "VHOST_CONFIG: bind to vhost-net")
-
- # start one vm
- self.vm = QEMUKvm(self.dut, 'vm0', 'vxlan_sample')
-
-Before VM start up, suite still can change VM parameters and in this case suite will add two vhost-user devices.
-
-.. code-block:: console
-
- # add two virtio user netdevices
- vm_params = {}
- vm_params['driver'] = 'vhost-user'
- vm_params['opt_path'] = './vhost-net'
- vm_params['opt_mac'] = "00:00:20:00:00:20"
- self.vm.set_vm_device(**vm_params)
- vm_params['opt_mac'] = "00:00:20:00:00:21"
- self.vm.set_vm_device(**vm_params)
-
-Add exception handler in VM start, it is critical function and better to handle the exception.
-
-.. code-block:: console
-
- try:
- self.vm_dut = self.vm.start()
- if self.vm_dut is None:
- raise Exception("Set up VM ENV failed!")
- except Exception as e:
- print dts.RED("Failure for %s" % str(e))
-
- return True
-
-VM start function will just return VM DUT object and support all DUT APIs.
-
-.. code-block:: console
-
- def vm_testpmd_start(self, vm_id=0):
- """
- Start testpmd in virtual machine
- """
- if vm_id == 0 and self.vm_dut is not None:
- # start testpmd
- self.vm_dut.send_expect(self.vm_testpmd, "testpmd>", 20)
- # set fwd mac
- self.vm_dut.send_expect("set fwd io", "testpmd>")
- # start tx_first
- self.vm_dut.send_expect("start tx_first", "testpmd>")
-
-When case has been run, need kill guest dpdk application and stop VM.
-
-.. code-block:: console
-
- def clear_vxlan_sample_env(self):
- if self.vm_dut:
- self.vm_dut.kill_all()
- time.sleep(1)
-
- if self.vm:
- self.vm.stop()
- self.vm = None
-
-KVM Module
-----------
-
-Default Parameters
-~~~~~~~~~~~~~~~~~~
-
-Enable KVM
-""""""""""
-
-DTS enable KVM full virtualization support as default. This option will significant improve the speed of virtual machine.
-
-Control (Qemu Guest Agent)
-"""""""""""""""""""""""""""
-
-Qemu monitor supply one method to interact with qemu process. DTS can monitor guest status by command supplied by qemu guest agent. Qemu guest agent is based on virtio-serial devices.
-
-.. code-block:: console
-
- -device virtio-serial -device virtserialport,chardev=vm_qga0,name=org.qemu.guest_agent.0
- -daemonize -monitor unix:/tmp/vm_monitor.sock,server,nowait
-
-Check whether guest os has been started up.
-
-.. code-block:: console
-
- qemu-ga-client address=/tmp/{vm_name}_qga0.sock ping 120
-
-.. note::
-
- We only wait two minutes for guest os start up. For guest os only has few hardware and we has disabled most services, so 2 minutes is enough.
- This command will be return when guest os is ready, so DTS will not wait 2 minutes for each time.
-
-Check whether guest os default interface has been up.
-
-.. code-block:: console
-
- qemu-ga-client address=/tmp/{vm_name}_qga0.sock ifconfig
-
-DTS will wait for guest os default interface upped and get auto dhcp address. After that DTS can connect to guest by ssh connections.
-
-.. code-block:: console
-
- lo:
- inet 127.0.0.1 netmask 255.0.0.0
- inet6 ::1 prefixlen 128
- host_connect:
- inet 10.0.2.15 netmask 255.255.255.0
- inet6 fe80::200:ff:feb9:fed7 prefixlen 64
- ether 00:00:00:b9:fe:d7
-
-Power down guest os.
-
-.. code-block:: console
-
- qemu-ga-client address=/tmp/{vm_name}_qga0.sock powerdown
-
-.. note::
-
- For more information about qemu guest agent, please refer to https://wiki.qemu.org/Features/GuestAgent.
-
-Control (Qemu Serial Port)
-""""""""""""""""""""""""""
-
-Qemu serial port is the default method to interact with guest OS. DTS can monitor guest status/manage guest network by serial port.
-
-.. code-block:: console
-
- -serial telnet::7000,server,nowait
-
-DTS will check the output from serial port and determine whether guest os has been started up. The prompt string for guest login session can be configured by parameter "start".
-
-.. code-block:: console
-
- start =
- wait_seconds=120,login_timeout=60,login_prompt=login:,password_prompt=Password:;
-
-.. note::
-
- Default timeout for guest OS start up is 2 minutes. For guest os only has few hardware and we has disabled most services, so 2 minutes is enough. If guest OS can't start up in 2 minutes, DTS will try to restart it once.
-
-DTS will check default interface upped and utilize dhcp to retrieve address. After that DTS can connect to guest by ssh connections.
-
-.. code-block:: console
-
- lo:
- inet 127.0.0.1 netmask 255.0.0.0
- inet6 ::1 prefixlen 128
- host_connect:
- inet 10.0.2.15 netmask 255.255.255.0
- inet6 fe80::200:ff:feb9:fed7 prefixlen 64
- ether 00:00:00:b9:fe:d7
-
-Power down guest os by serial port.
-
-.. code-block:: console
-
- init 0
-
-.. note::
-
- For more information about qemu serial port, please reference to https://qemu.weilnetz.de/doc/qemu-doc.html.
-
-Qemu Monitor
-""""""""""""
-
-After guest started, there's no way to known that host pci devices assigned-into guest.
-When assign host pci device into guest, we also add "id" string for this device.
-
-.. code-block:: console
-
- -device pci-assign,host=07:10.0,id=pt_0
-
-With this command, we assign host VF device 07:10.0 into guest and it is named as "pt_0". "pt_0" means it's the first device pass through into guest os.
-After guest os started, we use the QEMU/Monitor "info pci" command to dump PCI information and generate guest and host pci mapping by "id".
-
-.. code-block:: console
-
- Bus 0, device 4, function 0:
- Ethernet controller: PCI device 8086:10ed
- BAR0: 64 bit memory at 0xfebb0000 [0xfebb3fff].
- BAR3: 64 bit memory at 0xfebb4000 [0xfebb7fff].
- id "pt_0"
- Bus 0, device 5, function 0:
- Ethernet controller: PCI device 8086:10ed
- BAR0: 64 bit memory at 0xfebb8000 [0xfebbbfff].
- BAR3: 64 bit memory at 0xfebbc000 [0xfebbffff].
- id "pt_1"
-
-Connection to monitor socket on DUT.
-
-.. code-block:: console
-
- nc -U /tmp/{vm_name}_monitor.sock
-
-.. note::
-
- For More detail information about qemu monitor. https://en.wikibooks.org/wiki/QEMU/Monitor#info
-
-Qemu Machine (Aarch64)
-""""""""""""""""""""""
-
-DTS need set default qemu machine type as virt for Aarch64. This option is mandatory for qemu-system-aarch64.
-
-Configured Parameters
-~~~~~~~~~~~~~~~~~~~~~
-
-Net
-"""
-
-Net parameter is used to create one new Network Interface. There're few types of network interface supported by net parameter.
-
-Type supported:
- nic: Network Interface Card
- user: connect the user mode network stack
- tap: connect the host TAP network interface
- bridge: connects a host TAP network interface to a host bridge device
-
-Each type has different options, detail information shown in below tables.
-
-Options for nic:
-
-.. table::
-
- +-----------------+----------------------------------+----------------+-----------+
- | Option of nic | Description | Default value | Must have |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_vlan | vlan of virtual nic | 0 | No |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_macaddr | If not assign, nic will generate | N/A | No |
- | | random mac | | |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_model | model of virtual nic | e1000 | No |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_name | name be assigned for use in | N/A | No |
- | | monitor command | | |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_addr | pci address in virtual machine | N/A | No |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_vectors | number v of MSI-X vectors | N/A | No |
- +-----------------+----------------------------------+----------------+-----------+
-
-Options for user:
-
-.. table::
-
- +-----------------+----------------------------------+----------------+-----------+
- | Option of user | Description | Default value | Must have |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_vlan | vlan of virtual nic | 0 | No |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_hostfwd | Redirect incoming TCP or UDP | N/A | No |
- | | connections to the host port | | |
- +-----------------+----------------------------------+----------------+-----------+
-
-Options for tap:
-
-.. table::
-
- +-----------------+----------------------------------+----------------+-----------+
- | Option of tap | Description | Default value | Must have |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_vlan | vlan of virtual nic | 0 | No |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_br | bridge which tap device bound to | br0 | Yes |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_script | script for tap device network | /etc/qemu-ifup | No |
- | | configure | | |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_downscript | script for tap device network | /etc/ | No |
- | | deconfigure | qemu-ifdown | |
- +-----------------+----------------------------------+----------------+-----------+
-
-Device
-""""""
-
-Device parameter is used to add one emulated device into guest. Now DTS support few types of driver based devices.
-
-Driver supported:
- pci-assign: pci passthrough host devices into vm
- virtio-net-pci: virtio devices
- vhost-user: vhost-user network device based on socket
- vhost-cuse: vhost-user network device based on tap
-
-
-Options for pci-assign:
-
-.. table::
-
- +-----------------+----------------------------------+----------------+-----------+
- | Options of | Description | Default value | Must have |
- | pci-assign | | | |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_host | host pci device address | N/A | Yes |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_addr | pci address in virtual machine | N/A | No |
- +-----------------+----------------------------------+----------------+-----------+
-
-Options for virtio-net-pci:
-
-.. table::
-
- +-----------------+----------------------------------+----------------+-----------+
- | Option of | Description | Default value | Must have |
- | virtio-net-pci | | | |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_netdev | name for virtio netdev | N/A | Yes |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_id | netdevice id for virtio | N/A | Yes |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_mac | mac address on virtio-net device | N/A | No |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_bus | pci bus of virtio-net device in | N/A | No |
- | | vm | | |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_addr | pci address of virtio-net-pci | N/A | Yes |
- | | device in vm | | |
- +-----------------+----------------------------------+----------------+-----------+
-
-Options for vhost-user:
-
-.. table::
-
- +-----------------+----------------------------------+----------------+-----------+
- | Option of | Description | Default value | Must have |
- | vhost-user | | | |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_path | unix socket path of character | N/A | Yes |
- | | device | | |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_mac | mac address on virtio-net-pci | N/A | Yes |
- | | device | | |
- +-----------------+----------------------------------+----------------+-----------+
-
-Options for vhost-cuse:
-
-.. table::
-
- +-----------------+----------------------------------+----------------+-----------+
- | Option of | Description | Default value | Must have |
- | vhost-cuse | | | |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_mac | mac address on virtio-net-pci | N/A | No |
- | | device | | |
- +-----------------+----------------------------------+----------------+-----------+
- | opt_settings | virtio device settings | N/A | No |
- +-----------------+----------------------------------+----------------+-----------+
-
-VNC
-"""
-
-Vnc parameter is used for add vnc display in qemu process. There's only one option "displayNum" supported by this parameter. This parameter is added for user debug.
-
-.. note::
- Display number should be different between virtual machines.
-
-User Command
-""""""""""""
-
-User command parameter is used for add one special command for qemu. Some qemu command lines are so unique, there's no value to add certain parameter support for them. Those command lines can be implemented by this parameter.
-
-Login
-"""""
-
-Login parameter is used for specify guest login username and password.
--
1.8.3.1
^ permalink raw reply [flat|nested] 2+ messages in thread
end of thread, other threads:[~2021-04-13 2:05 UTC | newest]
Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-04-13 9:13 [dts] [v2] doc/dts_gsg: refresh dts guides Lijuan Tu
2021-04-13 2:05 ` Tu, Lijuan
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).