aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--docs/release/results/euphrates_fraser_comparison.rst602
-rw-r--r--docs/release/results/euphrates_fraser_comparsion.rst8
-rw-r--r--docs/release/results/images/tc002_pod_fraser.pngbin0 -> 22935 bytes
-rw-r--r--docs/release/results/images/tc002_scenario_fraser.pngbin0 -> 25892 bytes
-rw-r--r--docs/release/results/images/tc010_pod_fraser.pngbin0 -> 37525 bytes
-rw-r--r--docs/release/results/images/tc010_scenario_fraser.pngbin0 -> 45190 bytes
-rw-r--r--docs/release/results/images/tc011_pod_fraser.pngbin0 -> 25593 bytes
-rw-r--r--docs/release/results/images/tc011_scenario_fraser.pngbin0 -> 28152 bytes
-rw-r--r--docs/release/results/images/tc012_pod_fraser.pngbin0 -> 36168 bytes
-rw-r--r--docs/release/results/images/tc012_scenario_fraser.pngbin0 -> 41289 bytes
-rw-r--r--docs/release/results/images/tc014_pod_fraseer.pngbin0 -> 29513 bytes
-rw-r--r--docs/release/results/images/tc014_scenario_fraser.pngbin0 -> 36018 bytes
-rw-r--r--docs/release/results/images/tc069_pod_fraser.pngbin0 -> 36041 bytes
-rw-r--r--docs/release/results/images/tc069_scenario_fraser.pngbin0 -> 43834 bytes
-rw-r--r--docs/release/results/images/tc082_pod_fraser.pngbin0 -> 25078 bytes
-rw-r--r--docs/release/results/images/tc083_pod_fraser.pngbin0 -> 25476 bytes
-rw-r--r--docs/release/results/index.rst2
-rw-r--r--docs/release/results/results.rst2
-rw-r--r--docs/release/results/tc002-network-latency.rst208
-rw-r--r--docs/release/results/tc010-memory-read-latency.rst211
-rw-r--r--docs/release/results/tc011-packet-delay-variation.rst170
-rw-r--r--docs/release/results/tc012-memory-read-write-bandwidth.rst214
-rw-r--r--docs/release/results/tc014-cpu-processing-speed.rst214
-rw-r--r--docs/release/results/tc069-memory-write-bandwidth.rst216
-rw-r--r--docs/release/results/tc082-context-switches-under-load.rst66
-rw-r--r--docs/release/results/tc083-network-throughput-between-vm.rst66
-rw-r--r--docs/testing/user/userguide/14-nsb-operation.rst112
-rwxr-xr-xnsb_setup.sh2
-rw-r--r--samples/vnf_samples/nsut/prox/prox-tg-topology-scale-out.yaml53
-rw-r--r--samples/vnf_samples/nsut/prox/tc_prox_heat_context_l2fwd_multiflow-2-scale-out.yaml113
-rw-r--r--samples/vnf_samples/nsut/vfw/tc_heat_rfc2544_ipv4_1rule_1flow_64B_trex_scale_out.yaml114
-rw-r--r--samples/vnf_samples/nsut/vfw/vfw_tg_topology_scale_out.yaml53
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput-10.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput-2.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput-3.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput-4.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput-cgnapt-ixia-scale-out.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput-cgnapt-scale-out.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput-ixia-correlated-scale-out.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput-ixia-scale-out.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput-scale-out.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput-scale-up.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-10.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-2.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-4.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-scale-out.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput_scale_out.yaml102
-rw-r--r--samples/vnf_samples/traffic_profiles/ipv4_throughput_vpe.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ixia_ipv4_latency.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ixia_ipv4_latency_cgnapt.yaml3
-rw-r--r--samples/vnf_samples/traffic_profiles/ixia_ipv4_latency_vpe.yaml2
-rw-r--r--yardstick/benchmark/scenarios/networking/vnf_generic.py20
-rw-r--r--yardstick/common/utils.py26
-rw-r--r--yardstick/network_services/traffic_profile/base.py26
-rw-r--r--yardstick/network_services/traffic_profile/ixia_rfc2544.py1
-rw-r--r--yardstick/network_services/traffic_profile/rfc2544.py398
-rw-r--r--yardstick/network_services/traffic_profile/trex_traffic_profile.py122
-rw-r--r--yardstick/network_services/vnf_generic/vnf/sample_vnf.py36
-rw-r--r--yardstick/network_services/vnf_generic/vnf/tg_rfc2544_trex.py87
-rw-r--r--yardstick/network_services/vnf_generic/vnf/tg_trex.py26
-rw-r--r--yardstick/tests/unit/benchmark/contexts/standalone/test_model.py4
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/networking/test_vnf_generic.py3
-rw-r--r--yardstick/tests/unit/common/test_utils.py11
-rw-r--r--yardstick/tests/unit/network_services/traffic_profile/test_base.py17
-rw-r--r--yardstick/tests/unit/network_services/traffic_profile/test_fixed.py3
-rw-r--r--yardstick/tests/unit/network_services/traffic_profile/test_http.py29
-rw-r--r--yardstick/tests/unit/network_services/traffic_profile/test_rfc2544.py463
-rw-r--r--yardstick/tests/unit/network_services/traffic_profile/test_trex_traffic_profile.py154
-rw-r--r--yardstick/tests/unit/network_services/vnf_generic/vnf/test_sample_vnf.py221
-rw-r--r--yardstick/tests/unit/network_services/vnf_generic/vnf/test_tg_rfc2544_trex.py121
-rw-r--r--yardstick/tests/unit/network_services/vnf_generic/vnf/test_tg_trex.py196
-rw-r--r--yardstick/tests/unit/test_cmd/commands/test_env.py70
74 files changed, 3463 insertions, 1158 deletions
diff --git a/docs/release/results/euphrates_fraser_comparison.rst b/docs/release/results/euphrates_fraser_comparison.rst
new file mode 100644
index 000000000..53dfb994f
--- /dev/null
+++ b/docs/release/results/euphrates_fraser_comparison.rst
@@ -0,0 +1,602 @@
+.. This work is licensed under a Creative Commons Attribution 4.0 International
+.. License.
+.. http://creativecommons.org/licenses/by/4.0
+
+=======================================================
+Test results analysis for Euphrates and Fraser releases
+=======================================================
+
+TC002
+-----
+
+The round-trip-time (RTT) between 2 VMs on different blades is measured using
+ping.
+
+Most test run measurements result on average between 0.39 and 4.00 ms.
+Compared with Euphrates release, the average RTT result of the same pod experiences
+a slight decline in Fraser release. For example, the average RTT of arm-pod5 is
+1.518 in Ehphrates and 1.714 in Fraser. The average RTT of intel-pod18 is 1.6575
+ms in Ehphrates and 1.856 ms in Fraser.
+
+{
+
+ "huawei-pod2:stable/euphrates": [0.3925],
+
+ "lf-pod2:stable/euphrates": [0.5315],
+
+ "lf-pod1:stable/euphrates": [0.62],
+
+ "huawei-pod2:stable/fraser": [0.677],
+
+ "lf-pod1:stable/fraser": [0.725],
+
+ "flex-pod2:stable/euphrates": [0.795],
+
+ "huawei-pod12:stable/euphrates": [0.87],
+
+ "ericsson-pod1:stable/fraser": [0.9165],
+
+ "huawei-pod12:stable/fraser": [1.0465],
+
+ "lf-pod2:stable/fraser": [1.2325],
+
+ "intel-pod5:stable/euphrates": [1.25],
+
+ "ericsson-virtual3:stable/euphrates": [1.2655],
+
+ "ericsson-pod1:stable/euphrates": [1.372],
+
+ "zte-pod2:stable/fraser": [1.395],
+
+ "arm-pod5:stable/euphrates": [1.518],
+
+ "huawei-virtual4:stable/euphrates": [1.5355],
+
+ "ericsson-virtual4:stable/fraser": [1.582],
+
+ "huawei-virtual3:stable/euphrates": [1.606],
+
+ "intel-pod18:stable/euphrates": [1.6575],
+
+ "huawei-virtual4:stable/fraser": [1.697],
+
+ "huawei-virtual8:stable/euphrates": [1.709],
+
+ "arm-pod5:stable/fraser": [1.714],
+
+ "huawei-virtual3:stable/fraser": [1.716],
+
+ "intel-pod18:stable/fraser": [1.856],
+
+ "huawei-virtual2:stable/euphrates": [1.872],
+
+ "arm-pod6:stable/euphrates": [1.895],
+
+ "huawei-virtual2:stable/fraser": [1.964],
+
+ "huawei-virtual1:stable/fraser": [1.9765],
+
+ "huawei-virtual9:stable/euphrates": [2.0745],
+
+ "arm-pod6:stable/fraser": [2.209],
+
+ "huawei-virtual1:stable/euphrates": [2.495],
+
+ "ericsson-virtual2:stable/euphrates": [2.7895],
+
+ "ericsson-virtual4:stable/euphrates": [3.768],
+
+ "ericsson-virtual1:stable/euphrates": [3.8035],
+
+ "ericsson-virtual3:stable/fraser": [3.9175],
+
+ "ericsson-virtual2:stable/fraser": [4.004]
+
+}
+
+TC010
+-----
+
+The tool we use to measure memory read latency is lmbench, which is a series of
+micro benchmarks intended to measure basic operating system and hardware system
+metrics. Compared with Euphrates release, the memory read latency of the same pod
+also experience a slight decline. Virtual pods seem to have a higher memory read
+latency than physical pods. Compared with X86 pods, the memory read latency of
+arm pods is significant higher.
+
+{
+
+ "ericsson-pod1:stable/euphrates": [5.7785],
+
+ "flex-pod2:stable/euphrates": [5.908],
+
+ "ericsson-virtual1:stable/euphrates": [6.412],
+
+ "intel-pod18:stable/euphrates": [6.5905],
+
+ "intel-pod5:stable/euphrates": [6.6975],
+
+ "ericsson-pod1:stable/fraser": [7.0645],
+
+ "ericsson-virtual4:stable/euphrates": [7.183],
+
+ "intel-pod18:stable/fraser": [7.4465],
+
+ "zte-pod2:stable/fraser": [8.1865],
+
+ "ericsson-virtual2:stable/euphrates": [8.4985],
+
+ "huawei-pod2:stable/euphrates": [8.877],
+
+ "huawei-pod12:stable/euphrates": [9.091],
+
+ "huawei-pod2:stable/fraser": [9.236],
+
+ "huawei-pod12:stable/fraser": [9.615],
+
+ "ericsson-virtual3:stable/euphrates": [9.719],
+
+ "ericsson-virtual2:stable/fraser": [9.8925],
+
+ "huawei-virtual4:stable/euphrates": [10.1195],
+
+ "huawei-virtual3:stable/euphrates": [10.19],
+
+ "huawei-virtual2:stable/fraser": [10.22],
+
+ "huawei-virtual1:stable/euphrates": [10.3045],
+
+ "huawei-virtual9:stable/euphrates": [10.318],
+
+ "ericsson-virtual4:stable/fraser": [10.5465],
+
+ "ericsson-virtual3:stable/fraser": [10.9355],
+
+ "huawei-virtual3:stable/fraser": [10.95],
+
+ "huawei-virtual2:stable/euphrates": [11.274],
+
+ "huawei-virtual4:stable/fraser": [11.557],
+
+ "lf-pod1:stable/euphrates": [15.7025],
+
+ "lf-pod2:stable/euphrates": [15.8495],
+
+ "lf-pod2:stable/fraser": [16.5595],
+
+ "lf-pod1:stable/fraser": [16.8395],
+
+ "arm-pod5:stable/euphrates": [18.092],
+
+ "arm-pod5:stable/fraser": [18.744],
+
+ "huawei-virtual1:stable/fraser": [19.8235],
+
+ "huawei-virtual8:stable/euphrates": [33.999],
+
+ "arm-pod6:stable/euphrates": [41.5605],
+
+ "arm-pod6:stable/fraser": [55.804]
+
+}
+
+TC011
+-----
+
+Iperf3 is a tool for evaluating the packet delay variation between 2 VMs on
+different blades. In general, the packet delay variation of the two releases
+look similar.
+
+{
+
+ "arm-pod6:stable/fraser": [1],
+
+ "ericsson-pod1:stable/fraser": [1],
+
+ "ericsson-virtual2:stable/fraser": [1],
+
+ "ericsson-virtual3:stable/fraser": [1],
+
+ "lf-pod2:stable/fraser": [1],
+
+ "huawei-virtual1:stable/fraser": [2997],
+
+ "huawei-virtual2:stable/euphrates": [2997],
+
+ "flex-pod2:stable/euphrates": [2997.5],
+
+ "huawei-virtual3:stable/euphrates": [2998],
+
+ "huawei-virtual3:stable/fraser": [2999],
+
+ "huawei-virtual9:stable/euphrates": [3000],
+
+ "huawei-virtual8:stable/euphrates": [3001],
+
+ "huawei-virtual4:stable/euphrates": [3002],
+
+ "huawei-virtual4:stable/fraser": [3002],
+
+ "ericsson-virtual3:stable/euphrates": [3006],
+
+ "huawei-virtual1:stable/euphrates": [3007],
+
+ "ericsson-virtual2:stable/euphrates": [3009],
+
+ "intel-pod18:stable/euphrates": [3010],
+
+ "ericsson-virtual4:stable/euphrates": [3017],
+
+ "lf-pod2:stable/euphrates": [3021],
+
+ "arm-pod5:stable/euphrates": [3022],
+
+ "arm-pod6:stable/euphrates": [3022],
+
+ "ericsson-pod1:stable/euphrates": [3022],
+
+ "huawei-pod12:stable/euphrates": [3022],
+
+ "huawei-pod12:stable/fraser": [3022],
+
+ "huawei-pod2:stable/euphrates": [3022],
+
+ "huawei-pod2:stable/fraser": [3022],
+
+ "intel-pod18:stable/fraser": [3022],
+
+ "intel-pod5:stable/euphrates": [3022],
+
+ "lf-pod1:stable/euphrates": [3022],
+
+ "lf-pod1:stable/fraser": [3022],
+
+ "zte-pod2:stable/fraser": [3022],
+
+ "huawei-virtual2:stable/fraser": [3025]
+
+}
+
+TC012
+-----
+
+Lmbench is also used to measure the memory read and write bandwidth.
+Like TC010, compared with Euphrates release, the memory read and write bandwidth
+of the same pod also experience a slight decline. And compared with X86 pods, the memory
+read and write bandwidth of arm pods is significant lower.
+
+{
+
+ "lf-pod1:stable/euphrates": [22912.39],
+
+ "lf-pod2:stable/euphrates": [22637.67],
+
+ "lf-pod1:stable/fraser": [20552.9],
+
+ "flex-pod2:stable/euphrates": [20229.99],
+
+ "lf-pod2:stable/fraser": [20058.925],
+
+ "ericsson-pod1:stable/fraser": [18930.78],
+
+ "intel-pod18:stable/fraser": [18757.545],
+
+ "ericsson-virtual1:stable/euphrates": [17474.965],
+
+ "ericsson-pod1:stable/euphrates": [17127.38],
+
+ "ericsson-virtual4:stable/euphrates": [16219.97],
+
+ "ericsson-virtual2:stable/euphrates": [15652.28],
+
+ "ericsson-virtual3:stable/euphrates": [15551.26],
+
+ "ericsson-virtual4:stable/fraser": [15389.465],
+
+ "ericsson-virtual2:stable/fraser": [15343.79],
+
+ "huawei-pod2:stable/euphrates": [15017.2],
+
+ "huawei-pod2:stable/fraser": [14870.78],
+
+ "huawei-virtual4:stable/euphrates": [14266.34],
+
+ "huawei-virtual1:stable/euphrates": [14233.035],
+
+ "huawei-virtual3:stable/euphrates": [14227.63],
+
+ "zte-pod2:stable/fraser": [14157.99],
+
+ "huawei-pod12:stable/euphrates": [14147.245],
+
+ "huawei-pod12:stable/fraser": [14126.99],
+
+ "intel-pod18:stable/euphrates": [14058.33],
+
+ "huawei-virtual3:stable/fraser": [13929.67],
+
+ "huawei-virtual2:stable/euphrates": [13862.85],
+
+ "huawei-virtual4:stable/fraser": [13847.155],
+
+ "huawei-virtual2:stable/fraser": [13702.92],
+
+ "huawei-virtual1:stable/fraser": [13496.45],
+
+ "intel-pod5:stable/euphrates": [13280.32],
+
+ "ericsson-virtual3:stable/fraser": [12733.19],
+
+ "huawei-virtual9:stable/euphrates": [12559.445],
+
+ "huawei-virtual8:stable/euphrates": [8998.02],
+
+ "arm-pod5:stable/euphrates": [4388.875],
+
+ "arm-pod5:stable/fraser": [4326.11],
+
+ "arm-pod6:stable/euphrates": [4260.2],
+
+ "arm-pod6:stable/fraser": [3809.885]
+
+}
+
+TC014
+-----
+
+The Unixbench is used to evaluate the IaaS processing speed with regards to
+score of single CPU running and parallel running. Below are the single CPU running
+scores. It can be seen that the processing test results vary from scores 715 to 3737.
+In general, the single CPU score of the two releases look similar.
+
+{
+
+ "lf-pod2:stable/fraser": [3737.6],
+
+ "lf-pod2:stable/euphrates": [3723.95],
+
+ "lf-pod1:stable/fraser": [3702.7],
+
+ "lf-pod1:stable/euphrates": [3669],
+
+ "intel-pod5:stable/euphrates": [3388.6],
+
+ "intel-pod18:stable/euphrates": [3298.4],
+
+ "flex-pod2:stable/euphrates": [3208.6],
+
+ "ericsson-pod1:stable/fraser": [3131.6],
+
+ "intel-pod18:stable/fraser": [3098.1],
+
+ "ericsson-virtual1:stable/euphrates": [2988.9],
+
+ "zte-pod2:stable/fraser": [2831.4],
+
+ "ericsson-pod1:stable/euphrates": [2669.1],
+
+ "ericsson-virtual4:stable/euphrates": [2598.5],
+
+ "ericsson-virtual2:stable/fraser": [2559.7],
+
+ "ericsson-virtual3:stable/euphrates": [2553.15],
+
+ "huawei-pod2:stable/euphrates": [2531.2],
+
+ "huawei-pod2:stable/fraser": [2528.9],
+
+ "ericsson-virtual4:stable/fraser": [2527.8],
+
+ "ericsson-virtual2:stable/euphrates": [2526.9],
+
+ "huawei-virtual4:stable/euphrates": [2407.4],
+
+ "huawei-virtual3:stable/fraser": [2379.1],
+
+ "huawei-virtual3:stable/euphrates": [2374.6],
+
+ "huawei-virtual4:stable/fraser": [2362.1],
+
+ "huawei-virtual2:stable/euphrates": [2326.4],
+
+ "huawei-virtual9:stable/euphrates": [2324.95],
+
+ "huawei-virtual1:stable/euphrates": [2302.6],
+
+ "huawei-virtual2:stable/fraser": [2299.3],
+
+ "huawei-pod12:stable/euphrates": [2232.2],
+
+ "huawei-pod12:stable/fraser": [2229],
+
+ "huawei-virtual1:stable/fraser": [2171.3],
+
+ "ericsson-virtual3:stable/fraser": [2104.8],
+
+ "huawei-virtual8:stable/euphrates": [2085.3],
+
+ "arm-pod5:stable/fraser": [1764.2],
+
+ "arm-pod5:stable/euphrates": [1754.4],
+
+ "arm-pod6:stable/euphrates": [716.15],
+
+ "arm-pod6:stable/fraser": [715.4]
+
+}
+
+TC069
+-----
+
+With the block size changing from 1 kb to 512 kb, the memory write bandwidth
+tends to become larger first and then smaller within every run test. Below are
+the scores for 32mb block array.
+
+{
+
+ "intel-pod18:stable/euphrates": [18871.79],
+
+ "intel-pod18:stable/fraser": [16939.24],
+
+ "intel-pod5:stable/euphrates": [16055.79],
+
+ "arm-pod6:stable/euphrates": [13327.02],
+
+ "arm-pod6:stable/fraser": [11895.71],
+
+ "flex-pod2:stable/euphrates": [9384.585],
+
+ "zte-pod2:stable/fraser": [9375.33],
+
+ "ericsson-pod1:stable/euphrates": [9331.535],
+
+ "huawei-pod12:stable/euphrates": [9164.88],
+
+ "ericsson-pod1:stable/fraser": [9140.42],
+
+ "huawei-pod2:stable/euphrates": [9026.52],
+
+ "huawei-pod12:stable/fraser": [8993.37],
+
+ "huawei-virtual9:stable/euphrates": [8825.805],
+
+ "huawei-pod2:stable/fraser": [8794.01],
+
+ "huawei-virtual2:stable/fraser": [7670.21],
+
+ "ericsson-virtual1:stable/euphrates": [7615.97],
+
+ "ericsson-virtual4:stable/euphrates": [7539.23],
+
+ "arm-pod5:stable/fraser": [7479.32],
+
+ "arm-pod5:stable/euphrates": [7403.38],
+
+ "huawei-virtual3:stable/euphrates": [7247.89],
+
+ "ericsson-virtual2:stable/fraser": [7219.21],
+
+ "huawei-virtual2:stable/euphrates": [7205.35],
+
+ "huawei-virtual1:stable/euphrates": [7196.405],
+
+ "ericsson-virtual3:stable/euphrates": [7173.72],
+
+ "huawei-virtual4:stable/euphrates": [7131.47],
+
+ "ericsson-virtual2:stable/euphrates": [7129.08],
+
+ "huawei-virtual4:stable/fraser": [7059.045],
+
+ "huawei-virtual3:stable/fraser": [7023.57],
+
+ "lf-pod1:stable/euphrates": [6928.18],
+
+ "lf-pod2:stable/euphrates": [6875.88],
+
+ "lf-pod2:stable/fraser": [6834.7],
+
+ "lf-pod1:stable/fraser": [6775.27],
+
+ "ericsson-virtual4:stable/fraser": [6522.86],
+
+ "ericsson-virtual3:stable/fraser": [5835.59],
+
+ "huawei-virtual8:stable/euphrates": [5729.705],
+
+ "huawei-virtual1:stable/fraser": [5617.12]
+
+}
+
+TC082
+-----
+
+For this test case, we use perf to measure context-switches under load.
+High context switch rates are not themselves an issue, but they may point the
+way to a more significant problem.
+
+{
+
+ "zte-pod2:stable/fraser": [306.5],
+
+ "huawei-pod12:stable/euphrates": [316],
+
+ "lf-pod2:stable/fraser": [337.5],
+
+ "intel-pod18:stable/euphrates": [340],
+
+ "intel-pod18:stable/fraser": [343.5],
+
+ "intel-pod5:stable/euphrates": [357.5],
+
+ "ericsson-pod1:stable/euphrates": [384],
+
+ "lf-pod2:stable/euphrates": [394.5],
+
+ "huawei-pod12:stable/fraser": [399],
+
+ "lf-pod1:stable/euphrates": [435],
+
+ "lf-pod1:stable/fraser": [454],
+
+ "flex-pod2:stable/euphrates": [476],
+
+ "huawei-pod2:stable/euphrates": [518],
+
+ "huawei-pod2:stable/fraser": [544.5],
+
+ "arm-pod5:stable/euphrates": [869.5],
+
+ "huawei-virtual9:stable/euphrates": [1002],
+
+ "huawei-virtual4:stable/fraser": [1138],
+
+ "huawei-virtual4:stable/euphrates": [1174],
+
+ "huawei-virtual3:stable/euphrates": [1239],
+
+ "ericsson-pod1:stable/fraser": [1305],
+
+ "huawei-virtual2:stable/euphrates": [1430],
+
+ "huawei-virtual3:stable/fraser": [1433],
+
+ "huawei-virtual1:stable/fraser": [1470],
+
+ "huawei-virtual1:stable/euphrates": [1489],
+
+ "arm-pod6:stable/fraser": [1738.5],
+
+ "arm-pod6:stable/euphrates": [1883.5]
+
+}
+
+TC083
+-----
+
+TC083 measures network latency and throughput between VMs using netperf.
+The test results shown below are for UDP throughout.
+
+{
+
+ "lf-pod1:stable/euphrates": [2204.42],
+
+ "lf-pod2:stable/fraser": [1893.39],
+
+ "intel-pod18:stable/euphrates": [1835.55],
+
+ "lf-pod2:stable/euphrates": [1676.705],
+
+ "intel-pod5:stable/euphrates": [1612.555],
+
+ "zte-pod2:stable/fraser": [1543.995],
+
+ "lf-pod1:stable/fraser": [1480.86],
+
+ "intel-pod18:stable/fraser": [1417.015],
+
+ "flex-pod2:stable/euphrates": [1370.23],
+
+ "huawei-pod12:stable/euphrates": [1300.12]
+
+}
diff --git a/docs/release/results/euphrates_fraser_comparsion.rst b/docs/release/results/euphrates_fraser_comparsion.rst
deleted file mode 100644
index 222dc8bb0..000000000
--- a/docs/release/results/euphrates_fraser_comparsion.rst
+++ /dev/null
@@ -1,8 +0,0 @@
-.. This work is licensed under a Creative Commons Attribution 4.0 International
-.. License.
-.. http://creativecommons.org/licenses/by/4.0
-
-=======================================================
-Test results analysis for Euphrates and Fraser releases
-=======================================================
-
diff --git a/docs/release/results/images/tc002_pod_fraser.png b/docs/release/results/images/tc002_pod_fraser.png
new file mode 100644
index 000000000..797dc3136
--- /dev/null
+++ b/docs/release/results/images/tc002_pod_fraser.png
Binary files differ
diff --git a/docs/release/results/images/tc002_scenario_fraser.png b/docs/release/results/images/tc002_scenario_fraser.png
new file mode 100644
index 000000000..ff42e6516
--- /dev/null
+++ b/docs/release/results/images/tc002_scenario_fraser.png
Binary files differ
diff --git a/docs/release/results/images/tc010_pod_fraser.png b/docs/release/results/images/tc010_pod_fraser.png
new file mode 100644
index 000000000..23367d34a
--- /dev/null
+++ b/docs/release/results/images/tc010_pod_fraser.png
Binary files differ
diff --git a/docs/release/results/images/tc010_scenario_fraser.png b/docs/release/results/images/tc010_scenario_fraser.png
new file mode 100644
index 000000000..a481a595f
--- /dev/null
+++ b/docs/release/results/images/tc010_scenario_fraser.png
Binary files differ
diff --git a/docs/release/results/images/tc011_pod_fraser.png b/docs/release/results/images/tc011_pod_fraser.png
new file mode 100644
index 000000000..82dc9c763
--- /dev/null
+++ b/docs/release/results/images/tc011_pod_fraser.png
Binary files differ
diff --git a/docs/release/results/images/tc011_scenario_fraser.png b/docs/release/results/images/tc011_scenario_fraser.png
new file mode 100644
index 000000000..226d0b856
--- /dev/null
+++ b/docs/release/results/images/tc011_scenario_fraser.png
Binary files differ
diff --git a/docs/release/results/images/tc012_pod_fraser.png b/docs/release/results/images/tc012_pod_fraser.png
new file mode 100644
index 000000000..66e79be85
--- /dev/null
+++ b/docs/release/results/images/tc012_pod_fraser.png
Binary files differ
diff --git a/docs/release/results/images/tc012_scenario_fraser.png b/docs/release/results/images/tc012_scenario_fraser.png
new file mode 100644
index 000000000..4ef44119a
--- /dev/null
+++ b/docs/release/results/images/tc012_scenario_fraser.png
Binary files differ
diff --git a/docs/release/results/images/tc014_pod_fraseer.png b/docs/release/results/images/tc014_pod_fraseer.png
new file mode 100644
index 000000000..697201d76
--- /dev/null
+++ b/docs/release/results/images/tc014_pod_fraseer.png
Binary files differ
diff --git a/docs/release/results/images/tc014_scenario_fraser.png b/docs/release/results/images/tc014_scenario_fraser.png
new file mode 100644
index 000000000..f7865dcdc
--- /dev/null
+++ b/docs/release/results/images/tc014_scenario_fraser.png
Binary files differ
diff --git a/docs/release/results/images/tc069_pod_fraser.png b/docs/release/results/images/tc069_pod_fraser.png
new file mode 100644
index 000000000..1cba192d7
--- /dev/null
+++ b/docs/release/results/images/tc069_pod_fraser.png
Binary files differ
diff --git a/docs/release/results/images/tc069_scenario_fraser.png b/docs/release/results/images/tc069_scenario_fraser.png
new file mode 100644
index 000000000..f988b90c6
--- /dev/null
+++ b/docs/release/results/images/tc069_scenario_fraser.png
Binary files differ
diff --git a/docs/release/results/images/tc082_pod_fraser.png b/docs/release/results/images/tc082_pod_fraser.png
new file mode 100644
index 000000000..d54ab901a
--- /dev/null
+++ b/docs/release/results/images/tc082_pod_fraser.png
Binary files differ
diff --git a/docs/release/results/images/tc083_pod_fraser.png b/docs/release/results/images/tc083_pod_fraser.png
new file mode 100644
index 000000000..942cc2074
--- /dev/null
+++ b/docs/release/results/images/tc083_pod_fraser.png
Binary files differ
diff --git a/docs/release/results/index.rst b/docs/release/results/index.rst
index 3ec9e1cff..63445fd1a 100644
--- a/docs/release/results/index.rst
+++ b/docs/release/results/index.rst
@@ -14,4 +14,4 @@ Yardstick test results
.. include:: ./overview.rst
.. include:: ./results.rst
-.. include:: ./euphrates_fraser_comparsion.rst
+.. include:: ./euphrates_fraser_comparison.rst
diff --git a/docs/release/results/results.rst b/docs/release/results/results.rst
index c75f5ae94..0ed92f867 100644
--- a/docs/release/results/results.rst
+++ b/docs/release/results/results.rst
@@ -23,6 +23,7 @@ Scenario Results
The following documents contain results of Yardstick test cases executed on
OPNFV labs, triggered by OPNFV CI pipeline, documented per test case.
+For hardware details of OPNFV labs, please visit: https://wiki.opnfv.org/display/pharos/Community+Labs
.. toctree::
:maxdepth: 1
@@ -38,6 +39,7 @@ OPNFV labs, triggered by OPNFV CI pipeline, documented per test case.
Test results of executed tests are avilable in Dashboard_ and logs in Jenkins_.
+Test results for Fraser release are collected from April 10, 2018 to May 13, 2018.
Feature Test Results
====================
diff --git a/docs/release/results/tc002-network-latency.rst b/docs/release/results/tc002-network-latency.rst
index 722423473..064983bec 100644
--- a/docs/release/results/tc002-network-latency.rst
+++ b/docs/release/results/tc002-network-latency.rst
@@ -315,3 +315,211 @@ The influence of the POD
Fraser release
--------------
+
+Test results per scenario and pod (lower is better):
+
+{
+
+ "os-odl_l3-nofeature-ha:huawei-pod2:compass": [0.42],
+
+ "os-odl-sfc-ha:huawei-pod2:compass": [0.557],
+
+ "os-nosdn-ovs-ha:ericsson-pod1:fuel": [0.5765],
+
+ "os-nosdn-kvm-ha:huawei-pod2:compass": [0.582],
+
+ "os-odl-bgpvpn-ha:lf-pod1:apex": [0.678],
+
+ "os-nosdn-nofeature-ha:lf-pod1:apex": [0.7075],
+
+ "os-nosdn-calipso-noha:lf-pod1:apex": [0.713],
+
+ "os-nosdn-nofeature-noha:lf-pod1:apex": [0.7155],
+
+ "os-nosdn-bar-ha:lf-pod1:apex": [0.732],
+
+ "os-nosdn-bar-noha:lf-pod1:apex": [0.7415],
+
+ "os-odl-nofeature-noha:lf-pod1:apex": [0.7565],
+
+ "os-nosdn-ovs-ha:arm-pod6:fuel": [0.8015],
+
+ "os-nosdn-nofeature-ha:huawei-pod2:compass": [0.908],
+
+ "os-odl-nofeature-ha:ericsson-pod1:fuel": [0.9165],
+
+ "os-nosdn-bar-ha:huawei-pod2:compass": [0.969],
+
+ "os-nosdn-ovs-noha:ericsson-virtual2:fuel": [0.9765],
+
+ "os-nosdn-nofeature-noha:huawei-pod12:joid": [1.0245],
+
+ "os-nosdn-nofeature-ha:huawei-pod12:joid": [1.0495],
+
+ "os-odl-sfc-noha:huawei-virtual4:compass": [1.1645],
+
+ "os-nosdn-nofeature-ha:lf-pod2:fuel": [1.206],
+
+ "os-odl-sfc-noha:huawei-virtual3:compass": [1.236],
+
+ "os-nosdn-ovs-noha:ericsson-virtual4:fuel": [1.241],
+
+ "os-nosdn-nofeature-ha:zte-pod2:daisy": [1.2805],
+
+ "os-odl-nofeature-ha:lf-pod2:fuel": [1.286],
+
+ "os-odl_l3-nofeature-noha:huawei-virtual3:compass": [1.299],
+
+ "os-odl-sfc-ha:huawei-virtual4:compass": [1.305],
+
+ "os-odl_l3-nofeature-noha:huawei-virtual4:compass": [1.309],
+
+ "os-nosdn-kvm-noha:huawei-virtual4:compass": [1.314],
+
+ "os-nosdn-nofeature-noha:huawei-virtual4:compass": [1.431],
+
+ "os-nosdn-nofeature-ha:ericsson-pod1:fuel": [1.457],
+
+ "os-odl-nofeature-ha:zte-pod2:daisy": [1.517],
+
+ "os-nosdn-kvm-noha:huawei-virtual3:compass": [1.576],
+
+ "os-nosdn-nofeature-noha:huawei-virtual3:compass": [1.592],
+
+ "os-odl-nofeature-ha:arm-pod5:fuel": [1.714],
+
+ "os-nosdn-nofeature-noha:intel-pod18:joid": [1.809],
+
+ "os-nosdn-bar-noha:huawei-virtual4:compass": [1.81],
+
+ "os-nosdn-nofeature-ha:intel-pod18:joid": [1.8505],
+
+ "os-nosdn-nofeature-ha:huawei-virtual4:compass": [1.8895],
+
+ "os-nosdn-nofeature-ha:huawei-virtual3:compass": [1.909],
+
+ "os-odl_l3-nofeature-ha:huawei-virtual4:compass": [1.925],
+
+ "os-nosdn-nofeature-noha:huawei-virtual2:compass": [1.964],
+
+ "os-nosdn-openbaton-ha:intel-pod18:joid": [1.9755],
+
+ "os-nosdn-nofeature-ha:huawei-virtual1:compass": [1.9765],
+
+ "os-nosdn-bar-noha:huawei-virtual3:compass": [1.9915],
+
+ "os-odl_l3-nofeature-ha:huawei-virtual3:compass": [1.9925],
+
+ "os-nosdn-kvm-ha:huawei-virtual4:compass": [2.0265],
+
+ "os-odl-nofeature-ha:arm-pod6:fuel": [2.106],
+
+ "os-odl-sfc-ha:huawei-virtual3:compass": [2.124],
+
+ "os-nosdn-kvm-ha:huawei-virtual3:compass": [2.185],
+
+ "os-nosdn-nofeature-ha:arm-pod6:fuel": [2.281],
+
+ "os-nosdn-bar-ha:huawei-virtual4:compass": [2.432],
+
+ "os-odl-nofeature-noha:ericsson-virtual4:fuel": [2.483],
+
+ "os-nosdn-bar-ha:huawei-virtual3:compass": [2.524],
+
+ "os-nosdn-nofeature-noha:ericsson-virtual3:fuel": [3.9175],
+
+ "os-odl-nofeature-noha:ericsson-virtual2:fuel": [4.338],
+
+ "os-nosdn-nofeature-noha:ericsson-virtual2:fuel": [4.641]
+
+}
+
+
+The influence of the scenario
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc002_scenario_fraser.png
+ :width: 800px
+ :alt: TC002 influence of scenario
+
+{
+
+ "os-odl-bgpvpn-ha": [0.678],
+
+ "os-nosdn-calipso-noha": [0.713],
+
+ "os-nosdn-ovs-ha": [0.7245],
+
+ "os-odl_l3-nofeature-ha": [0.7435],
+
+ "os-odl-sfc-ha": [0.796],
+
+ "os-nosdn-kvm-ha": [1.059],
+
+ "os-nosdn-bar-ha": [1.083],
+
+ "os-nosdn-ovs-noha": [1.09],
+
+ "os-odl-sfc-noha": [1.196],
+
+ "os-nosdn-nofeature-noha": [1.26],
+
+ "os-nosdn-nofeature-ha": [1.291],
+
+ "os-odl_l3-nofeature-noha": [1.308],
+
+ "os-nosdn-bar-noha": [1.4125],
+
+ "os-nosdn-kvm-noha": [1.4475],
+
+ "os-odl-nofeature-ha": [1.508],
+
+ "os-odl-nofeature-noha": [1.914],
+
+ "os-nosdn-openbaton-ha": [1.9755]
+
+}
+
+
+The influence of the POD
+^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc002_pod_fraser.png
+ :width: 800px
+ :alt: TC002 influence of the POD
+
+{
+
+ "huawei-pod2": [0.677],
+
+ "lf-pod1": [0.725],
+
+ "ericsson-pod1": [0.9165],
+
+ "huawei-pod12": [1.0465],
+
+ "lf-pod2": [1.2325],
+
+ "zte-pod2": [1.395],
+
+ "ericsson-virtual4": [1.582],
+
+ "huawei-virtual4": [1.697],
+
+ "arm-pod5": [1.714],
+
+ "huawei-virtual3": [1.716],
+
+ "intel-pod18": [1.856],
+
+ "huawei-virtual2": [1.964],
+
+ "huawei-virtual1": [1.9765],
+
+ "arm-pod6": [2.209],
+
+ "ericsson-virtual3": [3.9175],
+
+ "ericsson-virtual2": [4.004]
+
+}
diff --git a/docs/release/results/tc010-memory-read-latency.rst b/docs/release/results/tc010-memory-read-latency.rst
index 9a296b7a0..81559d647 100644
--- a/docs/release/results/tc010-memory-read-latency.rst
+++ b/docs/release/results/tc010-memory-read-latency.rst
@@ -297,3 +297,214 @@ The influence of the POD
Fraser release
--------------
+
+Test results per scenario and pod (lower is better):
+
+{
+
+ "os-odl-nofeature-ha:ericsson-pod1:fuel": [6.8675],
+
+ "os-nosdn-nofeature-noha:intel-pod18:joid": [6.991],
+
+ "os-nosdn-openbaton-ha:intel-pod18:joid": [7.5535],
+
+ "os-nosdn-nofeature-ha:intel-pod18:joid": [7.571],
+ "os-nosdn-ovs-ha:ericsson-pod1:fuel": [7.635],
+
+ "os-nosdn-nofeature-ha:zte-pod2:daisy": [8.153],
+
+ "os-odl-nofeature-ha:zte-pod2:daisy": [8.1935],
+
+ "os-nosdn-bar-ha:huawei-pod2:compass": [9.1715],
+
+ "os-odl-sfc-ha:huawei-pod2:compass": [9.1875],
+
+ "os-odl_l3-nofeature-ha:huawei-pod2:compass": [9.241],
+
+ "os-nosdn-nofeature-ha:huawei-pod2:compass": [9.255],
+
+ "os-nosdn-kvm-ha:huawei-pod2:compass": [9.388],
+
+ "os-nosdn-nofeature-noha:huawei-virtual4:compass": [9.5825],
+
+ "os-nosdn-nofeature-noha:huawei-pod12:joid": [9.5875],
+
+ "os-nosdn-nofeature-ha:huawei-pod12:joid": [9.6345],
+
+ "os-odl-sfc-noha:huawei-virtual4:compass": [9.6535],
+
+ "os-nosdn-nofeature-noha:ericsson-virtual2:fuel": [9.743],
+
+ "os-odl-sfc-noha:huawei-virtual3:compass": [9.82],
+
+ "os-odl-nofeature-noha:ericsson-virtual2:fuel": [9.8715],
+
+ "os-odl_l3-nofeature-noha:huawei-virtual3:compass": [9.982],
+
+ "os-nosdn-bar-noha:huawei-virtual4:compass": [10.0195],
+
+ "os-odl_l3-nofeature-noha:huawei-virtual4:compass": [10.1285],
+
+ "os-nosdn-nofeature-noha:huawei-virtual3:compass": [10.1335],
+
+ "os-nosdn-nofeature-noha:huawei-virtual2:compass": [10.22],
+
+ "os-nosdn-bar-noha:huawei-virtual3:compass": [10.2845],
+
+ "os-nosdn-ovs-noha:ericsson-virtual4:fuel": [10.4185],
+
+ "os-nosdn-ovs-noha:ericsson-virtual2:fuel": [10.4555],
+
+ "os-nosdn-kvm-noha:huawei-virtual3:compass": [10.5635],
+
+ "os-nosdn-kvm-noha:huawei-virtual4:compass": [10.6515],
+
+ "os-nosdn-nofeature-noha:ericsson-virtual3:fuel": [10.9355],
+
+ "os-odl-nofeature-noha:ericsson-virtual4:fuel": [11.2015],
+
+ "os-odl_l3-nofeature-ha:huawei-virtual3:compass": [12.984],
+
+ "os-nosdn-bar-ha:huawei-virtual3:compass": [13.306],
+
+ "os-nosdn-nofeature-ha:huawei-virtual3:compass": [13.721],
+
+ "os-nosdn-bar-ha:huawei-virtual4:compass": [14.133],
+
+ "os-nosdn-nofeature-ha:ericsson-pod1:fuel": [14.158],
+
+ "os-odl_l3-nofeature-ha:huawei-virtual4:compass": [14.375],
+
+ "os-nosdn-nofeature-ha:huawei-virtual4:compass": [14.396],
+
+ "os-nosdn-kvm-ha:huawei-virtual4:compass": [14.9375],
+
+ "os-odl-sfc-ha:huawei-virtual3:compass": [14.957],
+
+ "os-nosdn-calipso-noha:lf-pod1:apex": [16.3445],
+
+ "os-nosdn-ovs-ha:lf-pod2:fuel": [16.478],
+
+ "os-nosdn-nofeature-ha:lf-pod2:fuel": [16.4895],
+
+ "os-odl-nofeature-noha:lf-pod1:apex": [16.55],
+
+ "os-nosdn-nofeature-noha:lf-pod1:apex": [16.5665],
+
+ "os-odl-sfc-noha:lf-pod1:apex": [16.598],
+
+ "os-ovn-nofeature-noha:lf-pod1:apex": [16.805],
+
+ "os-odl-nofeature-ha:lf-pod1:apex": [16.9095],
+
+ "os-nosdn-bar-ha:lf-pod1:apex": [17.494],
+
+ "os-nosdn-bar-noha:lf-pod1:apex": [17.4995],
+
+ "os-nosdn-nofeature-ha:lf-pod1:apex": [18.094],
+
+ "os-odl-nofeature-ha:arm-pod5:fuel": [18.744],
+
+ "os-nosdn-nofeature-ha:huawei-virtual1:compass": [19.8235],
+
+ "os-odl-nofeature-ha:lf-pod2:fuel": [20.758],
+
+ "os-nosdn-kvm-ha:huawei-virtual3:compass": [26.5245],
+
+ "os-nosdn-nofeature-ha:arm-pod6:fuel": [55.667],
+
+ "os-odl-nofeature-ha:arm-pod6:fuel": [56.175],
+
+ "os-nosdn-ovs-ha:arm-pod6:fuel": [57.86]
+
+}
+
+
+The influence of the scenario
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc010_scenario_fraser.png
+ :width: 800px
+ :alt: TC010 influence of scenario
+
+{
+
+ "os-nosdn-openbaton-ha": [7.5535],
+
+ "os-odl-nofeature-ha": [8.2535],
+
+ "os-odl-sfc-ha": [9.251],
+
+ "os-nosdn-nofeature-ha": [9.464],
+
+ "os-odl-sfc-noha": [9.8265],
+
+ "os-odl_l3-nofeature-ha": [9.836],
+
+ "os-odl_l3-nofeature-noha": [10.0565],
+
+ "os-nosdn-nofeature-noha": [10.079],
+
+ "os-nosdn-kvm-ha": [10.418],
+
+ "os-nosdn-ovs-noha": [10.43],
+
+ "os-nosdn-kvm-noha": [10.603],
+
+ "os-nosdn-bar-noha": [11.067],
+
+ "os-nosdn-bar-ha": [13.911],
+
+ "os-odl-nofeature-noha": [14.046],
+
+ "os-nosdn-calipso-noha": [16.3445],
+
+ "os-nosdn-ovs-ha": [16.478],
+
+ "os-ovn-nofeature-noha": [16.805]
+
+}
+
+
+The influence of the POD
+^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc010_pod_fraser.png
+ :width: 800px
+ :alt: TC010 influence of the POD
+
+{
+
+ "ericsson-pod1": [7.0645],
+
+ "intel-pod18": [7.4465],
+
+ "zte-pod2": [8.1865],
+
+ "huawei-pod2": [9.236],
+
+ "huawei-pod12": [9.615],
+
+ "ericsson-virtual2": [9.8925],
+
+ "huawei-virtual2": [10.22],
+
+ "ericsson-virtual4": [10.5465],
+
+ "ericsson-virtual3": [10.9355],
+
+ "huawei-virtual3": [10.95],
+
+ "huawei-virtual4": [11.557],
+
+ "lf-pod2": [16.5595],
+
+ "lf-pod1": [16.8395],
+
+ "arm-pod5": [18.744],
+
+ "huawei-virtual1": [19.8235],
+
+ "arm-pod6": [55.804]
+
+}
diff --git a/docs/release/results/tc011-packet-delay-variation.rst b/docs/release/results/tc011-packet-delay-variation.rst
index b07ea8980..f255b50ca 100644
--- a/docs/release/results/tc011-packet-delay-variation.rst
+++ b/docs/release/results/tc011-packet-delay-variation.rst
@@ -260,3 +260,173 @@ The influence of the POD
Fraser release
--------------
+
+Test results per scenario and pod (lower is better):
+
+{
+
+ "os-nosdn-nofeature-ha:arm-pod6:fuel": [1],
+
+ "os-nosdn-nofeature-ha:ericsson-pod1:fuel": [1],
+
+ "os-nosdn-nofeature-ha:lf-pod2:fuel": [1],
+
+ "os-nosdn-nofeature-noha:ericsson-virtual2:fuel": [1],
+
+ "os-nosdn-nofeature-noha:ericsson-virtual3:fuel": [1],
+
+ "os-ovn-nofeature-noha:lf-pod1:apex": [1511.5],
+
+ "os-nosdn-kvm-noha:huawei-virtual3:compass": [2996],
+
+ "os-nosdn-bar-ha:huawei-virtual4:compass": [2997],
+
+ "os-nosdn-bar-noha:huawei-virtual4:compass": [2997],
+
+ "os-nosdn-kvm-ha:huawei-virtual4:compass": [2997],
+
+ "os-nosdn-nofeature-ha:huawei-virtual1:compass": [2997],
+
+ "os-nosdn-nofeature-ha:huawei-virtual3:compass": [2997],
+
+ "os-nosdn-nofeature-ha:huawei-virtual4:compass": [2997],
+
+ "os-odl-sfc-ha:huawei-virtual3:compass": [2997],
+
+ "os-odl_l3-nofeature-ha:huawei-virtual3:compass": [2997],
+
+ "os-odl_l3-nofeature-noha:huawei-virtual3:compass": [3000],
+
+ "os-odl_l3-nofeature-ha:huawei-virtual4:compass": [3003],
+
+ "os-nosdn-bar-noha:huawei-virtual3:compass": [3011],
+
+ "os-nosdn-bar-ha:huawei-virtual3:compass": [3015.5],
+
+ "os-nosdn-kvm-noha:huawei-virtual4:compass": [3019],
+
+ "os-nosdn-nofeature-noha:huawei-virtual4:compass": [3021],
+
+ "os-odl-sfc-ha:huawei-virtual4:compass": [3021],
+
+ "os-nosdn-bar-ha:huawei-pod2:compass": [3022],
+
+ "os-nosdn-bar-ha:lf-pod1:apex": [3022],
+
+ "os-nosdn-bar-noha:lf-pod1:apex": [3022],
+
+ "os-nosdn-calipso-noha:lf-pod1:apex": [3022],
+
+ "os-nosdn-kvm-ha:huawei-pod2:compass": [3022],
+
+ "os-nosdn-nofeature-ha:huawei-pod12:joid": [3022],
+
+ "os-nosdn-nofeature-ha:huawei-pod2:compass": [3022],
+
+ "os-nosdn-nofeature-ha:intel-pod18:joid": [3022],
+
+ "os-nosdn-nofeature-ha:lf-pod1:apex": [3022],
+
+ "os-nosdn-nofeature-ha:zte-pod2:daisy": [3022],
+
+ "os-nosdn-nofeature-noha:huawei-pod12:joid": [3022],
+
+ "os-nosdn-nofeature-noha:intel-pod18:joid": [3022],
+
+ "os-nosdn-nofeature-noha:lf-pod1:apex": [3022],
+
+ "os-nosdn-openbaton-ha:intel-pod18:joid": [3022],
+
+ "os-odl-sfc-ha:huawei-pod2:compass": [3022],
+
+ "os-odl_l3-nofeature-ha:huawei-pod2:compass": [3022],
+
+ "os-odl_l3-nofeature-noha:huawei-virtual4:compass": [3022],
+
+ "os-odl-sfc-noha:huawei-virtual4:compass": [3022.5],
+
+ "os-nosdn-nofeature-noha:huawei-virtual3:compass": [3023],
+
+ "os-odl-sfc-noha:huawei-virtual3:compass": [3023],
+
+ "os-nosdn-nofeature-noha:huawei-virtual2:compass": [3025]
+
+}
+
+
+The influence of the scenario
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc011_scenario_fraser.png
+ :width: 800px
+ :alt: TC011 influence of scenario
+
+{
+
+ "os-ovn-nofeature-noha": [1511.5],
+
+ "os-nosdn-kvm-noha": [2997],
+
+ "os-odl-sfc-ha": [3021],
+
+ "os-nosdn-bar-ha": [3022],
+
+ "os-nosdn-bar-noha": [3022],
+
+ "os-nosdn-calipso-noha": [3022],
+
+ "os-nosdn-kvm-ha": [3022],
+
+ "os-nosdn-nofeature-ha": [3022],
+
+ "os-nosdn-nofeature-noha": [3022],
+
+ "os-nosdn-openbaton-ha": [3022],
+
+ "os-odl_l3-nofeature-ha": [3022],
+
+ "os-odl_l3-nofeature-noha": [3022],
+
+ "os-odl-sfc-noha": [3023]
+
+}
+
+
+The influence of the POD
+^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc011_pod_fraser.png
+ :width: 800px
+ :alt: TC011 influence of the POD
+
+{
+
+ "arm-pod6": [1],
+
+ "ericsson-pod1": [1],
+
+ "ericsson-virtual2": [1],
+
+ "ericsson-virtual3": [1],
+
+ "lf-pod2": [1],
+
+ "huawei-virtual1": [2997],
+
+ "huawei-virtual3": [2999],
+
+ "huawei-virtual4": [3002],
+
+ "huawei-pod12": [3022],
+
+ "huawei-pod2": [3022],
+
+ "intel-pod18": [3022],
+
+ "lf-pod1": [3022],
+
+ "zte-pod2": [3022],
+
+ "huawei-virtual2": [3025]
+
+}
diff --git a/docs/release/results/tc012-memory-read-write-bandwidth.rst b/docs/release/results/tc012-memory-read-write-bandwidth.rst
index c28eb1f3c..71d69cde9 100644
--- a/docs/release/results/tc012-memory-read-write-bandwidth.rst
+++ b/docs/release/results/tc012-memory-read-write-bandwidth.rst
@@ -297,3 +297,217 @@ The influence of the POD
Fraser release
--------------
+
+Test results per scenario and pod (higher is better):
+
+{
+
+ "os-nosdn-nofeature-ha:lf-pod2:fuel": [21421.795],
+
+ "os-odl-sfc-noha:lf-pod1:apex": [21075],
+
+ "os-odl-sfc-ha:lf-pod1:apex": [21017.44],
+
+ "os-nosdn-bar-noha:lf-pod1:apex": [20991.46],
+
+ "os-nosdn-bar-ha:lf-pod1:apex": [20812.405],
+
+ "os-ovn-nofeature-noha:lf-pod1:apex": [20694.035],
+
+ "os-nosdn-nofeature-noha:lf-pod1:apex": [20672.765],
+
+ "os-odl-nofeature-ha:lf-pod2:fuel": [20269.65],
+
+ "os-nosdn-calipso-noha:lf-pod1:apex": [20186.32],
+
+ "os-odl-nofeature-noha:lf-pod1:apex": [19959.915],
+
+ "os-nosdn-ovs-ha:lf-pod2:fuel": [19719.38],
+
+ "os-odl-nofeature-ha:lf-pod1:apex": [19654.505],
+
+ "os-nosdn-nofeature-ha:lf-pod1:apex": [19391.145],
+
+ "os-nosdn-nofeature-noha:intel-pod18:joid": [19378.64],
+
+ "os-odl-nofeature-ha:ericsson-pod1:fuel": [19103.43],
+
+ "os-nosdn-nofeature-ha:intel-pod18:joid": [18688.695],
+
+ "os-nosdn-openbaton-ha:intel-pod18:joid": [18557.95],
+
+ "os-nosdn-nofeature-ha:ericsson-pod1:fuel": [17088.61],
+
+ "os-nosdn-ovs-ha:ericsson-pod1:fuel": [17040.78],
+
+ "os-nosdn-ovs-noha:ericsson-virtual2:fuel": [16057.235],
+
+ "os-odl-nofeature-noha:ericsson-virtual4:fuel": [15622.355],
+
+ "os-nosdn-nofeature-noha:ericsson-virtual2:fuel": [15422.235],
+
+ "os-odl-sfc-ha:huawei-pod2:compass": [15403.09],
+
+ "os-odl-nofeature-noha:ericsson-virtual2:fuel": [15141.58],
+
+ "os-nosdn-bar-ha:huawei-pod2:compass": [14922.37],
+
+ "os-odl_l3-nofeature-ha:huawei-pod2:compass": [14864.195],
+
+ "os-nosdn-nofeature-ha:huawei-pod2:compass": [14856.295],
+
+ "os-nosdn-kvm-ha:huawei-pod2:compass": [14796.035],
+
+ "os-odl-sfc-noha:huawei-virtual4:compass": [14484.375],
+
+ "os-nosdn-nofeature-ha:huawei-pod12:joid": [14441.955],
+
+ "os-odl-sfc-noha:huawei-virtual3:compass": [14373],
+
+ "os-nosdn-nofeature-noha:huawei-virtual4:compass": [14330.44],
+
+ "os-nosdn-ovs-noha:ericsson-virtual4:fuel": [14320.305],
+
+ "os-odl_l3-nofeature-noha:huawei-virtual3:compass": [14253.715],
+
+ "os-nosdn-nofeature-ha:huawei-virtual4:compass": [14203.655],
+
+ "os-nosdn-nofeature-noha:huawei-virtual3:compass": [14179.93],
+
+ "os-odl-nofeature-ha:zte-pod2:daisy": [14177.135],
+
+ "os-nosdn-nofeature-ha:zte-pod2:daisy": [14150.825],
+
+ "os-nosdn-nofeature-noha:huawei-pod12:joid": [14100.87],
+
+ "os-nosdn-bar-noha:huawei-virtual4:compass": [14033.36],
+
+ "os-odl_l3-nofeature-noha:huawei-virtual4:compass": [13963.73],
+
+ "os-nosdn-kvm-noha:huawei-virtual3:compass": [13874.775],
+
+ "os-nosdn-kvm-noha:huawei-virtual4:compass": [13805.65],
+
+ "os-odl_l3-nofeature-ha:huawei-virtual3:compass": [13754.63],
+
+ "os-nosdn-nofeature-noha:huawei-virtual2:compass": [13702.92],
+
+ "os-nosdn-bar-ha:huawei-virtual3:compass": [13638.115],
+
+ "os-odl-sfc-ha:huawei-virtual3:compass": [13637.83],
+
+ "os-odl_l3-nofeature-ha:huawei-virtual4:compass": [13635.66],
+
+ "os-nosdn-bar-noha:huawei-virtual3:compass": [13635.58],
+
+ "os-nosdn-bar-ha:huawei-virtual4:compass": [13544.95],
+
+ "os-nosdn-nofeature-ha:huawei-virtual3:compass": [13514.27],
+
+ "os-nosdn-nofeature-ha:huawei-virtual1:compass": [13496.45],
+
+ "os-odl-sfc-ha:huawei-virtual4:compass": [13475.38],
+
+ "os-nosdn-nofeature-noha:ericsson-virtual3:fuel": [12733.19],
+
+ "os-nosdn-kvm-ha:huawei-virtual4:compass": [12682.805],
+
+ "os-odl-nofeature-ha:arm-pod5:fuel": [4326.11],
+
+ "os-nosdn-nofeature-ha:arm-pod6:fuel": [3824.13],
+
+ "os-odl-nofeature-ha:arm-pod6:fuel": [3797.795],
+
+ "os-nosdn-ovs-ha:arm-pod6:fuel": [3749.91]
+
+}
+
+
+The influence of the scenario
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc012_scenario_fraser.png
+ :width: 800px
+ :alt: TC012 influence of scenario
+
+{
+
+ "os-ovn-nofeature-noha": [20694.035],
+
+ "os-nosdn-calipso-noha": [20186.32],
+
+ "os-nosdn-openbaton-ha": [18557.95],
+
+ "os-nosdn-ovs-ha": [17048.17],
+
+ "os-odl-nofeature-noha": [16191.125],
+
+ "os-nosdn-ovs-noha": [15790.32],
+
+ "os-nosdn-bar-ha": [14833.97],
+
+ "os-odl-sfc-ha": [14828.72],
+
+ "os-odl_l3-nofeature-ha": [14801.25],
+
+ "os-nosdn-kvm-ha": [14700.1],
+
+ "os-nosdn-nofeature-ha": [14610.48],
+
+ "os-nosdn-nofeature-noha": [14555.975],
+
+ "os-odl-sfc-noha": [14508.14],
+
+ "os-nosdn-bar-noha": [14395.22],
+
+ "os-odl-nofeature-ha": [14231.245],
+
+ "os-odl_l3-nofeature-noha": [14161.58],
+
+ "os-nosdn-kvm-noha": [13845.685]
+
+}
+
+
+The influence of the POD
+^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc012_pod_fraser.png
+ :width: 800px
+ :alt: TC012 influence of the POD
+
+{
+
+ "lf-pod1": [20552.9],
+
+ "lf-pod2": [20058.925],
+
+ "ericsson-pod1": [18930.78],
+
+ "intel-pod18": [18757.545],
+
+ "ericsson-virtual4": [15389.465],
+
+ "ericsson-virtual2": [15343.79],
+
+ "huawei-pod2": [14870.78],
+
+ "zte-pod2": [14157.99],
+
+ "huawei-pod12": [14126.99],
+
+ "huawei-virtual3": [13929.67],
+
+ "huawei-virtual4": [13847.155],
+
+ "huawei-virtual2": [13702.92],
+
+ "huawei-virtual1": [13496.45],
+
+ "ericsson-virtual3": [12733.19],
+
+ "arm-pod5": [4326.11],
+
+ "arm-pod6": [3809.885]
+
+}
diff --git a/docs/release/results/tc014-cpu-processing-speed.rst b/docs/release/results/tc014-cpu-processing-speed.rst
index 34d4ad0f9..a2eeb6302 100644
--- a/docs/release/results/tc014-cpu-processing-speed.rst
+++ b/docs/release/results/tc014-cpu-processing-speed.rst
@@ -296,3 +296,217 @@ The influence of the POD
Fraser release
--------------
+
+Test results per scenario and pod (higher is better):
+
+{
+
+ "os-nosdn-nofeature-ha:lf-pod2:fuel": [3747.3],
+
+ "os-nosdn-calipso-noha:lf-pod1:apex": [3727.2],
+
+ "os-odl-nofeature-ha:lf-pod1:apex": [3726.5],
+
+ "os-ovn-nofeature-noha:lf-pod1:apex": [3723.8],
+
+ "os-odl-nofeature-noha:lf-pod1:apex": [3718.9],
+
+ "os-nosdn-nofeature-noha:lf-pod1:apex": [3717.75],
+
+ "os-nosdn-nofeature-ha:lf-pod1:apex": [3706.5],
+
+ "os-odl-nofeature-ha:lf-pod2:fuel": [3704.9],
+
+ "os-nosdn-ovs-ha:lf-pod2:fuel": [3687.7],
+
+ "os-nosdn-bar-noha:lf-pod1:apex": [3635.4],
+
+ "os-nosdn-bar-ha:lf-pod1:apex": [3632.55],
+
+ "os-odl-sfc-noha:lf-pod1:apex": [3569],
+
+ "os-nosdn-nofeature-noha:intel-pod18:joid": [3432.1],
+
+ "os-odl-nofeature-ha:ericsson-pod1:fuel": [3133.85],
+
+ "os-nosdn-ovs-ha:ericsson-pod1:fuel": [3079.8],
+
+ "os-nosdn-nofeature-ha:intel-pod18:joid": [3074.75],
+
+ "os-nosdn-openbaton-ha:intel-pod18:joid": [2976.2],
+
+ "os-nosdn-nofeature-ha:zte-pod2:daisy": [2910.95],
+
+ "os-odl-nofeature-ha:zte-pod2:daisy": [2801.1],
+
+ "os-nosdn-ovs-noha:ericsson-virtual2:fuel": [2603],
+
+ "os-odl-nofeature-noha:ericsson-virtual2:fuel": [2559.7],
+
+ "os-nosdn-nofeature-noha:ericsson-virtual2:fuel": [2539.1],
+
+ "os-odl_l3-nofeature-ha:huawei-pod2:compass": [2530.5],
+
+ "os-nosdn-nofeature-ha:huawei-pod2:compass": [2529.4],
+
+ "os-odl-sfc-ha:huawei-pod2:compass": [2528.9],
+
+ "os-odl-nofeature-noha:ericsson-virtual4:fuel": [2527.8],
+
+ "os-nosdn-bar-ha:huawei-pod2:compass": [2527.4],
+
+ "os-nosdn-kvm-ha:huawei-pod2:compass": [2517.8],
+
+ "os-nosdn-nofeature-noha:huawei-virtual4:compass": [2472.4],
+
+ "os-nosdn-nofeature-ha:huawei-virtual4:compass": [2469.1],
+
+ "os-odl-sfc-noha:huawei-virtual3:compass": [2452.05],
+
+ "os-odl-sfc-noha:huawei-virtual4:compass": [2438.7],
+
+ "os-odl_l3-nofeature-noha:huawei-virtual3:compass": [2418.4],
+
+ "os-nosdn-ovs-noha:ericsson-virtual4:fuel": [2404.35],
+
+ "os-nosdn-kvm-noha:huawei-virtual3:compass": [2391],
+
+ "os-nosdn-kvm-noha:huawei-virtual4:compass": [2376.75],
+
+ "os-odl_l3-nofeature-noha:huawei-virtual4:compass": [2376.2],
+
+ "os-nosdn-nofeature-noha:huawei-virtual3:compass": [2359.45],
+
+ "os-nosdn-bar-noha:huawei-virtual4:compass": [2353.3],
+
+ "os-odl-sfc-ha:huawei-virtual3:compass": [2351.9],
+
+ "os-nosdn-bar-ha:huawei-virtual3:compass": [2339.4],
+
+ "os-odl-sfc-ha:huawei-virtual4:compass": [2335.6],
+
+ "os-nosdn-bar-ha:huawei-virtual4:compass": [2328],
+
+ "os-odl_l3-nofeature-ha:huawei-virtual3:compass": [2324.5],
+
+ "os-nosdn-bar-noha:huawei-virtual3:compass": [2317.3],
+
+ "os-nosdn-nofeature-ha:huawei-virtual3:compass": [2313.95],
+
+ "os-odl_l3-nofeature-ha:huawei-virtual4:compass": [2308.1],
+
+ "os-nosdn-nofeature-noha:huawei-virtual2:compass": [2299.3],
+
+ "os-nosdn-kvm-ha:huawei-virtual4:compass": [2250.4],
+
+ "os-nosdn-nofeature-noha:huawei-pod12:joid": [2229.7],
+
+ "os-nosdn-nofeature-ha:huawei-pod12:joid": [2228.8],
+
+ "os-nosdn-nofeature-ha:huawei-virtual1:compass": [2171.3],
+
+ "os-nosdn-nofeature-noha:ericsson-virtual3:fuel": [2104.8],
+
+ "os-nosdn-nofeature-ha:ericsson-pod1:fuel": [1961.35],
+
+ "os-nosdn-ovs-ha:arm-pod5:fuel": [1764.2],
+
+ "os-odl-nofeature-ha:arm-pod5:fuel": [1730.95],
+
+ "os-nosdn-ovs-ha:arm-pod6:fuel": [715.55],
+
+ "os-odl-nofeature-ha:arm-pod6:fuel": [715.4],
+
+ "os-nosdn-nofeature-ha:arm-pod6:fuel": [715.25]
+
+}
+
+
+The influence of the scenario
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc014_scenario_fraser.png
+ :width: 800px
+ :alt: TC014 influence of scenario
+
+{
+
+ "os-nosdn-calipso-noha": [3727.2],
+
+ "os-ovn-nofeature-noha": [3723.8],
+
+ "os-odl-nofeature-noha": [3128.05],
+
+ "os-nosdn-openbaton-ha": [2976.2],
+
+ "os-nosdn-ovs-ha": [2814.5],
+
+ "os-odl-nofeature-ha": [2801.4],
+
+ "os-nosdn-nofeature-ha": [2649.7],
+
+ "os-nosdn-ovs-noha": [2587.3],
+
+ "os-odl_l3-nofeature-ha": [2528.45],
+
+ "os-odl-sfc-ha": [2527.6],
+
+ "os-nosdn-bar-ha": [2526.55],
+
+ "os-nosdn-kvm-ha": [2516.95],
+
+ "os-odl-sfc-noha": [2453.65],
+
+ "os-nosdn-bar-noha": [2447.7],
+
+ "os-nosdn-nofeature-noha": [2443.85],
+
+ "os-odl_l3-nofeature-noha": [2394.3],
+
+ "os-nosdn-kvm-noha": [2379.7]
+
+}
+
+
+The influence of the POD
+^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc014_pod_fraser.png
+ :width: 800px
+ :alt: TC014 influence of the POD
+
+{
+
+ "lf-pod2": [3737.6],
+
+ "lf-pod1": [3702.7],
+
+ "ericsson-pod1": [3131.6],
+
+ "intel-pod18": [3098.1],
+
+ "zte-pod2": [2831.4],
+
+ "ericsson-virtual2": [2559.7],
+
+ "huawei-pod2": [2528.9],
+
+ "ericsson-virtual4": [2527.8],
+
+ "huawei-virtual3": [2379.1],
+
+ "huawei-virtual4": [2362.1],
+
+ "huawei-virtual2": [2299.3],
+
+ "huawei-pod12": [2229],
+
+ "huawei-virtual1": [2171.3],
+
+ "ericsson-virtual3": [2104.8],
+
+ "arm-pod5": [1764.2],
+
+ "arm-pod6": [715.4]
+
+}
diff --git a/docs/release/results/tc069-memory-write-bandwidth.rst b/docs/release/results/tc069-memory-write-bandwidth.rst
index 06e2ec922..4cd3be3b0 100644
--- a/docs/release/results/tc069-memory-write-bandwidth.rst
+++ b/docs/release/results/tc069-memory-write-bandwidth.rst
@@ -298,3 +298,219 @@ The influence of the POD
Fraser release
--------------
+
+Test results per scenario and pod (higher is better):
+
+{
+
+ "os-nosdn-nofeature-noha:intel-pod18:joid": [18382.49],
+
+ "os-nosdn-openbaton-ha:intel-pod18:joid": [16774.52],
+
+ "os-nosdn-nofeature-ha:intel-pod18:joid": [16680.305],
+
+ "os-nosdn-ovs-ha:arm-pod6:fuel": [11925.22],
+
+ "os-nosdn-nofeature-ha:arm-pod6:fuel": [11895.71],
+
+ "os-odl-nofeature-ha:arm-pod6:fuel": [11880.7],
+
+ "os-nosdn-nofeature-ha:ericsson-pod1:fuel": [9471.095],
+
+ "os-odl-nofeature-ha:zte-pod2:daisy": [9375.33],
+
+ "os-nosdn-nofeature-ha:zte-pod2:daisy": [9372.95],
+
+ "os-odl-nofeature-ha:ericsson-pod1:fuel": [9174.36],
+
+ "os-nosdn-nofeature-noha:huawei-pod12:joid": [9051.57],
+
+ "os-nosdn-nofeature-ha:huawei-pod12:joid": [8894.74],
+
+ "os-odl_l3-nofeature-ha:huawei-pod2:compass": [8857.23],
+
+ "os-nosdn-nofeature-ha:huawei-pod2:compass": [8855.8],
+
+ "os-nosdn-bar-ha:huawei-pod2:compass": [8840.94],
+
+ "os-odl-sfc-ha:huawei-pod2:compass": [8826.23],
+
+ "os-nosdn-nofeature-noha:huawei-virtual4:compass": [8039.48],
+
+ "os-nosdn-nofeature-noha:huawei-virtual2:compass": [7670.21],
+
+ "os-nosdn-ovs-ha:arm-pod5:fuel": [7590.9],
+
+ "os-odl-sfc-noha:huawei-virtual4:compass": [7579.625],
+
+ "os-nosdn-bar-noha:huawei-virtual3:compass": [7511.775],
+
+ "os-odl-nofeature-ha:arm-pod5:fuel": [7475.16],
+
+ "os-nosdn-bar-noha:huawei-virtual4:compass": [7435.08],
+
+ "os-nosdn-nofeature-noha:ericsson-virtual2:fuel": [7426.79],
+
+ "os-nosdn-nofeature-ha:huawei-virtual4:compass": [7362.8],
+
+ "os-nosdn-kvm-noha:huawei-virtual4:compass": [7263.45],
+
+ "os-nosdn-nofeature-noha:huawei-virtual3:compass": [7262.72],
+
+ "os-odl_l3-nofeature-noha:huawei-virtual3:compass": [7241.07],
+
+ "os-odl-nofeature-noha:ericsson-virtual2:fuel": [7219.21],
+
+ "os-nosdn-kvm-noha:huawei-virtual3:compass": [7174.33],
+
+ "os-odl-sfc-noha:huawei-virtual3:compass": [7170.795],
+
+ "os-odl-nofeature-noha:lf-pod1:apex": [7158.335],
+
+ "os-nosdn-kvm-ha:huawei-pod2:compass": [7122.45],
+
+ "os-odl-sfc-ha:huawei-virtual4:compass": [7104.9],
+
+ "os-nosdn-ovs-noha:ericsson-virtual2:fuel": [7044.37],
+
+ "os-nosdn-bar-ha:huawei-virtual3:compass": [7011.075],
+
+ "os-nosdn-ovs-ha:ericsson-pod1:fuel": [6950.28],
+
+ "os-nosdn-ovs-noha:ericsson-virtual4:fuel": [6918.31],
+
+ "os-nosdn-bar-ha:huawei-virtual4:compass": [6903.11],
+
+ "os-nosdn-nofeature-ha:lf-pod2:fuel": [6880.98],
+
+ "os-odl-sfc-ha:lf-pod1:apex": [6863.39],
+
+ "os-odl_l3-nofeature-ha:huawei-virtual3:compass": [6851.54],
+
+ "os-nosdn-nofeature-noha:lf-pod1:apex": [6834.75],
+
+ "os-nosdn-calipso-noha:lf-pod1:apex": [6833.92],
+
+ "os-nosdn-ovs-ha:lf-pod2:fuel": [6814.68],
+
+ "os-ovn-nofeature-noha:lf-pod1:apex": [6809.44],
+
+ "os-odl_l3-nofeature-ha:huawei-virtual4:compass": [6784.48],
+
+ "os-nosdn-nofeature-ha:lf-pod1:apex": [6737.64],
+
+ "os-nosdn-bar-noha:lf-pod1:apex": [6708.61],
+
+ "os-nosdn-bar-ha:lf-pod1:apex": [6697.2],
+
+ "os-odl-nofeature-ha:lf-pod1:apex": [6626.51],
+
+ "os-odl-sfc-noha:lf-pod1:apex": [6609.57],
+
+ "os-odl-sfc-ha:huawei-virtual3:compass": [6606.87],
+
+ "os-odl_l3-nofeature-noha:huawei-virtual4:compass": [6547.39],
+
+ "os-odl-nofeature-ha:lf-pod2:fuel": [6465.48],
+
+ "os-odl-nofeature-noha:ericsson-virtual4:fuel": [6413],
+
+ "os-nosdn-kvm-ha:huawei-virtual4:compass": [6409.075],
+
+ "os-nosdn-nofeature-ha:huawei-virtual3:compass": [6128.79],
+
+ "os-nosdn-nofeature-noha:ericsson-virtual3:fuel": [5835.59],
+
+ "os-nosdn-nofeature-ha:huawei-virtual1:compass": [5617.12]
+
+}
+
+
+The influence of the scenario
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc069_scenario_fraser.png
+ :width: 800px
+ :alt: TC069 influence of scenario
+
+{
+
+ "os-nosdn-openbaton-ha": [16774.52],
+
+ "os-odl-nofeature-ha": [9363.69],
+
+ "os-nosdn-nofeature-ha": [8878.01],
+
+ "os-odl_l3-nofeature-ha": [8748.4],
+
+ "os-odl-sfc-ha": [8708.045],
+
+ "os-nosdn-nofeature-noha": [7426.79],
+
+ "os-nosdn-kvm-noha": [7230.79],
+
+ "os-odl-sfc-noha": [7224.11],
+
+ "os-odl-nofeature-noha": [7187.84],
+
+ "os-nosdn-ovs-noha": [7044.37],
+
+ "os-nosdn-bar-ha": [6947.87],
+
+ "os-odl_l3-nofeature-noha": [6895.96],
+
+ "os-nosdn-kvm-ha": [6890.92],
+
+ "os-nosdn-calipso-noha": [6833.92],
+
+ "os-nosdn-ovs-ha": [6833.495],
+
+ "os-nosdn-bar-noha": [6811.66],
+
+ "os-ovn-nofeature-noha": [6809.44]
+
+}
+
+
+The influence of the POD
+^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc069_pod_fraser.png
+ :width: 800px
+ :alt: TC069 influence of the POD
+
+{
+
+ "intel-pod18": [16939.24],
+
+ "arm-pod6": [11895.71],
+
+ "zte-pod2": [9375.33],
+
+ "ericsson-pod1": [9140.42],
+
+ "huawei-pod12": [8993.37],
+
+ "huawei-pod2": [8794.01],
+
+ "huawei-virtual2": [7670.21],
+
+ "arm-pod5": [7479.32],
+
+ "ericsson-virtual2": [7219.21],
+
+ "huawei-virtual4": [7059.045],
+
+ "huawei-virtual3": [7023.57],
+
+ "lf-pod2": [6834.7],
+
+ "lf-pod1": [6775.27],
+
+ "ericsson-virtual4": [6522.86],
+
+ "ericsson-virtual3": [5835.59],
+
+ "huawei-virtual1": [5617.12]
+
+}
diff --git a/docs/release/results/tc082-context-switches-under-load.rst b/docs/release/results/tc082-context-switches-under-load.rst
index d8a9f5493..92bc69907 100644
--- a/docs/release/results/tc082-context-switches-under-load.rst
+++ b/docs/release/results/tc082-context-switches-under-load.rst
@@ -70,8 +70,6 @@ The influence of the scenario
:width: 800px
:alt: TC082 influence of scenario
-the influence of the scenario
-
{
"os-nosdn-nofeature-ha": [505],
@@ -88,8 +86,6 @@ The influence of the POD
:width: 800px
:alt: TC082 influence of the POD
-the influence of the POD
-
{
"huawei-pod12": [316],
@@ -127,3 +123,65 @@ the influence of the POD
Fraser release
--------------
+
+Test results per scenario and pod (lower is better):
+
+{
+
+ "os-nosdn-nofeature-ha:zte-pod2:daisy": [306.5],
+
+ "os-nosdn-nofeature-ha:lf-pod2:fuel": [337.5],
+
+ "os-nosdn-nofeature-ha:intel-pod18:joid": [343.5],
+
+ "os-nosdn-nofeature-ha:huawei-pod12:joid": [399],
+
+ "os-nosdn-nofeature-ha:lf-pod1:apex": [454],
+
+ "os-nosdn-nofeature-ha:huawei-pod2:compass": [544.5],
+
+ "os-nosdn-nofeature-ha:huawei-virtual4:compass": [1138],
+
+ "os-nosdn-nofeature-ha:ericsson-pod1:fuel": [1305],
+
+ "os-nosdn-nofeature-ha:huawei-virtual3:compass": [1433],
+
+ "os-nosdn-nofeature-ha:huawei-virtual1:compass": [1470],
+
+ "os-nosdn-nofeature-ha:arm-pod6:fuel": [1738.5]
+
+}
+
+
+The influence of the POD
+^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc082_pod_fraser.png
+ :width: 800px
+ :alt: TC082 influence of the POD
+
+{
+
+ "zte-pod2": [306.5],
+
+ "lf-pod2": [337.5],
+
+ "intel-pod18": [343.5],
+
+ "huawei-pod12": [399],
+
+ "lf-pod1": [454],
+
+ "huawei-pod2": [544.5],
+
+ "huawei-virtual4": [1138],
+
+ "ericsson-pod1": [1305],
+
+ "huawei-virtual3": [1433],
+
+ "huawei-virtual1": [1470],
+
+ "arm-pod6": [1738.5]
+
+}
diff --git a/docs/release/results/tc083-network-throughput-between-vm.rst b/docs/release/results/tc083-network-throughput-between-vm.rst
index f846571a5..0389eaafe 100644
--- a/docs/release/results/tc083-network-throughput-between-vm.rst
+++ b/docs/release/results/tc083-network-throughput-between-vm.rst
@@ -70,8 +70,6 @@ The influence of the scenario
:width: 800px
:alt: TC083 influence of scenario
-the influence of the scenario
-
{
"os-nosdn-nofeature-ha": [1109.12],
@@ -88,8 +86,6 @@ The influence of the POD
:width: 800px
:alt: TC083 influence of the POD
-the influence of the POD
-
{
"lf-pod1": [2204.42],
@@ -127,3 +123,65 @@ the influence of the POD
Fraser release
--------------
+
+Test results per scenario and pod (higher is better):
+
+{
+
+ "os-nosdn-nofeature-ha:lf-pod2:fuel": [1893.39],
+
+ "os-nosdn-nofeature-ha:zte-pod2:daisy": [1543.995],
+
+ "os-nosdn-nofeature-ha:lf-pod1:apex": [1480.86],
+
+ "os-nosdn-nofeature-ha:intel-pod18:joid": [1417.015],
+
+ "os-nosdn-nofeature-ha:huawei-pod12:joid": [1028.55],
+
+ "os-nosdn-nofeature-ha:huawei-pod2:compass": [1007.65],
+
+ "os-nosdn-nofeature-ha:ericsson-pod1:fuel": [811.795],
+
+ "os-nosdn-nofeature-ha:huawei-virtual4:compass": [552.95],
+
+ "os-nosdn-nofeature-ha:arm-pod6:fuel": [227.655],
+
+ "os-nosdn-nofeature-ha:huawei-virtual1:compass": [216.63],
+
+ "os-nosdn-nofeature-ha:huawei-virtual3:compass": [59.255]
+
+}
+
+
+The influence of the POD
+^^^^^^^^^^^^^^^^^^^^^^^^
+
+.. image:: images/tc083_pod_fraser.png
+ :width: 800px
+ :alt: TC083 influence of the POD
+
+{
+
+ "lf-pod2": [1893.39],
+
+ "zte-pod2": [1543.995],
+
+ "lf-pod1": [1480.86],
+
+ "intel-pod18": [1417.015],
+
+ "huawei-pod12": [1028.55],
+
+ "huawei-pod2": [1007.65],
+
+ "ericsson-pod1": [811.795],
+
+ "huawei-virtual4": [552.95],
+
+ "arm-pod6": [227.655],
+
+ "huawei-virtual1": [216.63],
+
+ "huawei-virtual3": [59.255]
+
+}
diff --git a/docs/testing/user/userguide/14-nsb-operation.rst b/docs/testing/user/userguide/14-nsb-operation.rst
index d157914a9..851c6528e 100644
--- a/docs/testing/user/userguide/14-nsb-operation.rst
+++ b/docs/testing/user/userguide/14-nsb-operation.rst
@@ -84,6 +84,116 @@ In this example we have ``TRex xe0 <-> xe0 VNF xe1 <-> xe0 UDP_Replay``
downlink_0:
- xe0
+
+Availability zone
+^^^^^^^^^^^^^^^^^
+
+The configuration of the availability zone is requred in cases where location
+of exact compute host/group of compute hosts needs to be specified for SampleVNF
+or traffic generator in the heat test case. If this is the case, please follow
+the instructions below.
+
+.. _`Create a host aggregate`:
+
+1. Create a host aggregate in the OpenStack and add the available compute hosts
+ into the aggregate group.
+
+ .. note:: Change the ``<AZ_NAME>`` (availability zone name), ``<AGG_NAME>``
+ (host aggregate name) and ``<HOST>`` (host name of one of the compute) in the
+ commands below.
+
+ .. code-block:: bash
+
+ # create host aggregate
+ openstack aggregate create --zone <AZ_NAME> --property availability_zone=<AZ_NAME> <AGG_NAME>
+ # show available hosts
+ openstack compute service list --service nova-compute
+ # add selected host into the host aggregate
+ openstack aggregate add host <AGG_NAME> <HOST>
+
+2. To specify the OpenStack location (the exact compute host or group of the hosts)
+ of SampleVNF or traffic generator in the heat test case, the ``availability_zone`` server
+ configuration option should be used. For example:
+
+ .. note:: The ``<AZ_NAME>`` (availability zone name) should be changed according
+ to the name used during the host aggregate creation steps above.
+
+ .. code-block:: yaml
+
+ context:
+ name: yardstick
+ image: yardstick-samplevnfs
+ ...
+ servers:
+ vnf__0:
+ ...
+ availability_zone: <AZ_NAME>
+ ...
+ tg__0:
+ ...
+ availability_zone: <AZ_NAME>
+ ...
+ networks:
+ ...
+
+There are two example of SampleVNF scale out test case which use the availability zone
+feature to specify the exact location of scaled VNFs and traffic generators.
+
+Those are:
+
+.. code-block:: console
+
+ <repo>/samples/vnf_samples/nsut/prox/tc_prox_heat_context_l2fwd_multiflow-2-scale-out.yaml
+ <repo>/samples/vnf_samples/nsut/vfw/tc_heat_rfc2544_ipv4_1rule_1flow_64B_trex_scale_out.yaml
+
+.. note:: This section describes the PROX scale-out testcase, but the same
+ procedure is used for the vFW test case.
+
+1. Before running the scale-out test case, make sure the host aggregates are
+ configured in the OpenStack environment. To check this, run the following
+ command:
+
+ .. code-block:: console
+
+ # show configured host aggregates (example)
+ openstack aggregate list
+ +----+------+-------------------+
+ | ID | Name | Availability Zone |
+ +----+------+-------------------+
+ | 4 | agg0 | AZ_NAME_0 |
+ | 5 | agg1 | AZ_NAME_1 |
+ +----+------+-------------------+
+
+2. If no host aggregates are configured, please use `steps above`__ to
+ configure them.
+
+__ `Create a host aggregate`_
+
+
+3. Run the SampleVNF PROX scale-out test case, specifying the availability
+ zone of each VNF and traffic generator as a task arguments.
+
+ .. note:: The ``az_0`` and ``az_1`` should be changed according to the host
+ aggregates created in the OpenStack.
+
+ .. code-block:: console
+
+ yardstick -d task start\
+ <repo>/samples/vnf_samples/nsut/prox/tc_prox_heat_context_l2fwd_multiflow-2-scale-out.yaml\
+ --task-args='{
+ "num_vnfs": 4, "availability_zone": {
+ "vnf_0": "az_0", "tg_0": "az_1",
+ "vnf_1": "az_0", "tg_1": "az_1",
+ "vnf_2": "az_0", "tg_2": "az_1",
+ "vnf_3": "az_0", "tg_3": "az_1"
+ }
+ }'
+
+ ``num_vnfs`` specifies how many VNFs are going to be deployed in the
+ ``heat`` contexts. ``vnf_X`` and ``tg_X`` arguments configure the
+ availability zone where the VNF and traffic generator is going to be deployed.
+
+
Collectd KPIs
-------------
@@ -242,7 +352,7 @@ Baremetal
file: /etc/yardstick/nodes/pod.yaml
Scale-Out
---------------------
+---------
VNFs performance data with scale-out helps
diff --git a/nsb_setup.sh b/nsb_setup.sh
index 86796c4d4..3396b82d1 100755
--- a/nsb_setup.sh
+++ b/nsb_setup.sh
@@ -79,4 +79,4 @@ ansible-playbook \
-e img_property="nsb" \
${yardstick_docker_image} \
-e YARD_IMG_ARCH='amd64' ${extra_args}\
- -i yardstick-install-inventory.ini nsb_setup.yml
+ -i install-inventory.ini nsb_setup.yml
diff --git a/samples/vnf_samples/nsut/prox/prox-tg-topology-scale-out.yaml b/samples/vnf_samples/nsut/prox/prox-tg-topology-scale-out.yaml
new file mode 100644
index 000000000..5f01ecb7e
--- /dev/null
+++ b/samples/vnf_samples/nsut/prox/prox-tg-topology-scale-out.yaml
@@ -0,0 +1,53 @@
+# Copyright (c) 2018 Intel Corporation
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+{% set num_vnfs = get(extra_args, 'num_vnfs', 1) %}
+---
+nsd:nsd-catalog:
+ nsd:
+ - id: prox-tg-topology
+ name: prox-tg-topology
+ short-name: prox-tg-topology
+ description: prox-tg-topology
+ constituent-vnfd:
+{% for vnf_num in range(num_vnfs|int) %}
+ - member-vnf-index: '{{ (vnf_num * 2) + 1 }}'
+ vnfd-id-ref: tg__{{ vnf_num }}
+ VNF model: ../../vnf_descriptors/tg_prox_tpl.yaml
+ - member-vnf-index: '{{ (vnf_num * 2) + 2 }}'
+ vnfd-id-ref: vnf__{{ vnf_num }}
+ VNF model: ../../vnf_descriptors/prox_vnf.yaml
+{% endfor %}
+ vld:
+{% for vnf_num in range(num_vnfs|int) %}
+ - id: uplink_{{ vnf_num }}
+ name: tg__{{ vnf_num }} to vnf__{{ vnf_num }} link {{ (vnf_num * 2) + 1 }}
+ type: ELAN
+ vnfd-connection-point-ref:
+ - member-vnf-index-ref: '{{ (vnf_num * 2) + 1 }}'
+ vnfd-connection-point-ref: xe0
+ vnfd-id-ref: tg__{{ vnf_num }}
+ - member-vnf-index-ref: '{{ (vnf_num * 2) + 2 }}'
+ vnfd-connection-point-ref: xe0
+ vnfd-id-ref: vnf__{{ vnf_num }}
+ - id: downlink_{{ vnf_num }}
+ name: vnf__{{ vnf_num }} to tg__{{ vnf_num }} link {{ (vnf_num * 2) + 2 }}
+ type: ELAN
+ vnfd-connection-point-ref:
+ - member-vnf-index-ref: '{{ (vnf_num * 2) + 1 }}'
+ vnfd-connection-point-ref: xe1
+ vnfd-id-ref: vnf__{{ vnf_num }}
+ - member-vnf-index-ref: '{{ (vnf_num * 2) + 2 }}'
+ vnfd-connection-point-ref: xe1
+ vnfd-id-ref: tg__{{ vnf_num }}
+{% endfor %}
diff --git a/samples/vnf_samples/nsut/prox/tc_prox_heat_context_l2fwd_multiflow-2-scale-out.yaml b/samples/vnf_samples/nsut/prox/tc_prox_heat_context_l2fwd_multiflow-2-scale-out.yaml
new file mode 100644
index 000000000..88581d2da
--- /dev/null
+++ b/samples/vnf_samples/nsut/prox/tc_prox_heat_context_l2fwd_multiflow-2-scale-out.yaml
@@ -0,0 +1,113 @@
+# Copyright (c) 2018 Intel Corporation
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+{% set num_vnfs = num_vnfs or 1 %}
+{% set availability_zone = availability_zone or {} %}
+---
+schema: "yardstick:task:0.1"
+scenarios:
+-
+ type: NSPerf
+ traffic_profile: ../../traffic_profiles/prox_binsearch.yaml
+ topology: prox-tg-topology-scale-out.yaml
+ extra_args:
+ num_vnfs: {{ num_vnfs }}
+
+ nodes:
+{% for vnf_num in range(num_vnfs|int) %}
+ tg__{{ vnf_num }}: tg_{{ vnf_num }}.yardstick
+ vnf__{{ vnf_num }}: vnf_{{ vnf_num }}.yardstick
+{% endfor %}
+
+ options:
+{% for vnf_num in range(num_vnfs|int) %}
+ vnf__{{ vnf_num }}:
+ prox_path: /opt/nsb_bin/prox
+ prox_config: "configs/handle_l2fwd_multiflow-2.cfg"
+ prox_args:
+ "-t": ""
+
+ tg__{{ vnf_num }}:
+ prox_path: /opt/nsb_bin/prox
+ prox_config: "configs/gen_l2fwd_multiflow-2.cfg"
+ prox_args:
+ "-e": ""
+ "-t": ""
+{% endfor %}
+
+ runner:
+ type: Duration
+ # we kill after duration, independent of test duration, so set this high
+ duration: 300
+
+context:
+ name: yardstick
+ image: yardstick-samplevnfs
+ user: ubuntu
+ flavor:
+ vcpus: 8
+ ram: 20480
+ disk: 10
+ extra_specs:
+ hw:cpu_sockets: 1
+ hw:cpu_cores: 8
+ hw:cpu_threads: 1
+ placement_groups:
+ pgrp1:
+ policy: "availability"
+
+ servers:
+{% for vnf_num in range(num_vnfs|int) %}
+ vnf_{{ vnf_num }}:
+ floating_ip: true
+ placement: "pgrp1"
+ {% if 'vnf_%s'|format(vnf_num) in availability_zone %}
+ availability_zone: "{{ availability_zone['vnf_%s'|format(vnf_num)] }}"
+ {% endif %}
+ network_ports:
+ mgmt:
+ - mgmt
+ uplink_{{ vnf_num }}:
+ - xe0
+ downlink_{{ vnf_num }}:
+ - xe1
+ tg_{{ vnf_num }}:
+ floating_ip: true
+ placement: "pgrp1"
+ {% if 'tg_%s'|format(vnf_num) in availability_zone %}
+ availability_zone: "{{ availability_zone['tg_%s'|format(vnf_num)] }}"
+ {% endif %}
+ network_ports:
+ mgmt:
+ - mgmt
+ uplink_{{ vnf_num }}:
+ - xe0
+ downlink_{{ vnf_num }}:
+ - xe1
+{% endfor %}
+
+ networks:
+ mgmt:
+ cidr: '10.0.1.0/24'
+{% for vnf_num in range(num_vnfs|int) %}
+ uplink_{{ vnf_num }}:
+ cidr: '10.0.{{ (vnf_num * 2) + 2 }}.0/24'
+ gateway_ip: 'null'
+ port_security_enabled: False
+ enable_dhcp: 'false'
+ downlink_{{ vnf_num }}:
+ cidr: '10.0.{{ (vnf_num * 2) + 3 }}.0/24'
+ gateway_ip: 'null'
+ port_security_enabled: False
+ enable_dhcp: 'false'
+{% endfor %}
diff --git a/samples/vnf_samples/nsut/vfw/tc_heat_rfc2544_ipv4_1rule_1flow_64B_trex_scale_out.yaml b/samples/vnf_samples/nsut/vfw/tc_heat_rfc2544_ipv4_1rule_1flow_64B_trex_scale_out.yaml
new file mode 100644
index 000000000..f1408931f
--- /dev/null
+++ b/samples/vnf_samples/nsut/vfw/tc_heat_rfc2544_ipv4_1rule_1flow_64B_trex_scale_out.yaml
@@ -0,0 +1,114 @@
+# Copyright (c) 2018 Intel Corporation
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+{% set num_vnfs = num_vnfs or 1 %}
+{% set availability_zone = availability_zone or {} %}
+---
+schema: yardstick:task:0.1
+scenarios:
+- type: NSPerf
+ traffic_profile: ../../traffic_profiles/ipv4_throughput_scale_out.yaml
+ topology: vfw_tg_topology_scale_out.yaml
+ extra_args:
+ num_vnfs: {{ num_vnfs }}
+ nodes:
+{% for vnf_num in range(num_vnfs|int) %}
+ tg__{{ vnf_num }}: tg_{{ vnf_num }}.yardstick
+ vnf__{{ vnf_num }}: vnf_{{ vnf_num }}.yardstick
+{% endfor %}
+ options:
+ framesize:
+ uplink: {64B: 100}
+ downlink: {64B: 100}
+ flow:
+ src_ip:
+{% for vnf_num in range(num_vnfs|int) %}
+ - {'tg__{{ vnf_num }}': 'xe0'}
+{% endfor %}
+ dst_ip:
+{% for vnf_num in range(num_vnfs|int) %}
+ - {'tg__{{ vnf_num }}': 'xe1'}
+{% endfor %}
+ count: 1
+ traffic_type: 4
+ rfc2544:
+ allowed_drop_rate: 0.0001 - 0.0001
+{% for vnf_num in range(num_vnfs|int) %}
+ vnf__{{ vnf_num }}:
+ rules: acl_1rule.yaml
+ vnf_config: {lb_config: 'SW', lb_count: 1, worker_config: '1C/1T', worker_threads: 1}
+{% endfor %}
+ runner:
+ type: Iteration
+ iterations: 10
+ interval: 35
+context:
+ # put node context first, so we don't HEAT deploy if node has errors
+ name: yardstick
+ image: yardstick-samplevnfs
+ flavor:
+ vcpus: 10
+ ram: 20480
+ disk: 6
+ extra_specs:
+ hw:cpu_sockets: 1
+ hw:cpu_cores: 10
+ hw:cpu_threads: 1
+ user: ubuntu
+ placement_groups:
+ pgrp1:
+ policy: "availability"
+ servers:
+{% for vnf_num in range(num_vnfs|int) %}
+ vnf_{{ vnf_num }}:
+ floating_ip: true
+ placement: "pgrp1"
+ {% if 'vnf_%s'|format(vnf_num) in availability_zone %}
+ availability_zone: "{{ availability_zone['vnf_%s'|format(vnf_num)] }}"
+ {% endif %}
+ network_ports:
+ mgmt:
+ - mgmt
+ uplink_{{ vnf_num }}:
+ - xe0
+ downlink_{{ vnf_num }}:
+ - xe1
+ tg_{{ vnf_num }}:
+ floating_ip: true
+ placement: "pgrp1"
+ {% if 'tg_%s'|format(vnf_num) in availability_zone %}
+ availability_zone: "{{ availability_zone['tg_%s'|format(vnf_num)] }}"
+ {% endif %}
+ network_ports:
+ mgmt:
+ - mgmt
+ uplink_{{ vnf_num }}:
+ - xe0
+ downlink_{{ vnf_num }}:
+ - xe1
+{% endfor %}
+ networks:
+ mgmt:
+ cidr: '10.0.1.0/24'
+{% for vnf_num in range(num_vnfs|int) %}
+ uplink_{{ vnf_num }}:
+ cidr: '10.0.{{ (vnf_num * 2) + 2 }}.0/24'
+ gateway_ip: 'null'
+ port_security_enabled: False
+ enable_dhcp: 'false'
+ downlink_{{ vnf_num }}:
+ cidr: '10.0.{{ (vnf_num * 2) + 3 }}.0/24'
+ gateway_ip: 'null'
+ port_security_enabled: False
+ enable_dhcp: 'false'
+{% endfor %}
diff --git a/samples/vnf_samples/nsut/vfw/vfw_tg_topology_scale_out.yaml b/samples/vnf_samples/nsut/vfw/vfw_tg_topology_scale_out.yaml
new file mode 100644
index 000000000..8bd01b7f2
--- /dev/null
+++ b/samples/vnf_samples/nsut/vfw/vfw_tg_topology_scale_out.yaml
@@ -0,0 +1,53 @@
+# Copyright (c) 2018 Intel Corporation
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+{% set num_vnfs = get(extra_args, 'num_vnfs', 1) %}
+---
+nsd:nsd-catalog:
+ nsd:
+ - id: 3tg-topology
+ name: 3tg-topology
+ short-name: 3tg-topology
+ description: 3tg-topology
+ constituent-vnfd:
+{% for vnf_num in range(num_vnfs|int) %}
+ - member-vnf-index: '{{ (vnf_num * 2) + 1 }}'
+ vnfd-id-ref: tg__{{ vnf_num }}
+ VNF model: ../../vnf_descriptors/tg_rfc2544_tpl.yaml
+ - member-vnf-index: '{{ (vnf_num * 2) + 2 }}'
+ vnfd-id-ref: vnf__{{ vnf_num }}
+ VNF model: ../../vnf_descriptors/vfw_vnf.yaml
+{% endfor %}
+ vld:
+{% for vnf_num in range(num_vnfs|int) %}
+ - id: uplink_{{ vnf_num }}
+ name: tg__{{ vnf_num }} to vnf__{{ vnf_num }} link {{ (vnf_num * 2) + 1 }}
+ type: ELAN
+ vnfd-connection-point-ref:
+ - member-vnf-index-ref: '{{ (vnf_num * 2) + 1 }}'
+ vnfd-connection-point-ref: xe0
+ vnfd-id-ref: tg__{{ vnf_num }}
+ - member-vnf-index-ref: '{{ (vnf_num * 2) + 2 }}'
+ vnfd-connection-point-ref: xe0
+ vnfd-id-ref: vnf__{{ vnf_num }}
+ - id: downlink_{{ vnf_num }}
+ name: vnf__{{ vnf_num }} to tg__{{ vnf_num }} link {{ (vnf_num * 2) + 2 }}
+ type: ELAN
+ vnfd-connection-point-ref:
+ - member-vnf-index-ref: '{{ (vnf_num * 2) + 2 }}'
+ vnfd-connection-point-ref: xe1
+ vnfd-id-ref: vnf__{{ vnf_num }}
+ - member-vnf-index-ref: '{{ (vnf_num * 2) + 1 }}'
+ vnfd-connection-point-ref: xe1
+ vnfd-id-ref: tg__{{ vnf_num }}
+{% endfor %}
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput-10.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput-10.yaml
index f862abdb7..98b1bf96d 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput-10.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput-10.yaml
@@ -43,8 +43,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
uplink_0:
ipv4:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput-2.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput-2.yaml
index a3218879b..ee0415371 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput-2.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput-2.yaml
@@ -43,8 +43,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
uplink_0:
ipv4:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput-3.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput-3.yaml
index d849ed8ab..19f083646 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput-3.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput-3.yaml
@@ -43,8 +43,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
uplink_0:
ipv4:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput-4.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput-4.yaml
index c03b28d60..95fa0b6d8 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput-4.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput-4.yaml
@@ -43,8 +43,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
uplink_0:
ipv4:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput-cgnapt-ixia-scale-out.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput-cgnapt-ixia-scale-out.yaml
index ad703f291..43f52094a 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput-cgnapt-ixia-scale-out.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput-cgnapt-ixia-scale-out.yaml
@@ -44,8 +44,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: IXIARFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
[% for vnf_num in range(num_vnfs|int) %]
uplink_[[ vnf_num ]]:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput-cgnapt-scale-out.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput-cgnapt-scale-out.yaml
index 75927d40d..a025a6931 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput-cgnapt-scale-out.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput-cgnapt-scale-out.yaml
@@ -44,8 +44,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
[% for vnf_num in range(num_vnfs|int) %]
uplink_[[ vnf_num ]]:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput-ixia-correlated-scale-out.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput-ixia-correlated-scale-out.yaml
index 500163205..081d630ac 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput-ixia-correlated-scale-out.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput-ixia-correlated-scale-out.yaml
@@ -44,8 +44,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: IXIARFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
[% for vnf_num in range(num_vnfs|int) %]
uplink_[[ vnf_num ]]:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput-ixia-scale-out.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput-ixia-scale-out.yaml
index 78e5f516a..d93bf1145 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput-ixia-scale-out.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput-ixia-scale-out.yaml
@@ -44,8 +44,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: IXIARFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
[% for vnf_num in range(num_vnfs|int) %]
uplink_[[ vnf_num ]]:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput-scale-out.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput-scale-out.yaml
index 73c41099f..0e842d48a 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput-scale-out.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput-scale-out.yaml
@@ -44,8 +44,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
[% for vnf_num in range(num_vnfs|int) %]
uplink_[[ vnf_num ]]:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput-scale-up.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput-scale-up.yaml
index d2cc18c15..b9e0c8cd1 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput-scale-up.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput-scale-up.yaml
@@ -44,7 +44,8 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
+ duration: {{ duration }}
+
{% set count = 0 %}
{% for vport in range(vports|int) %}
uplink_{{vport}}:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput.yaml
index 5b5b4473b..c267e7677 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput.yaml
@@ -42,8 +42,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type : RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate : 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
uplink_0:
ipv4:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-10.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-10.yaml
index 80d0872d5..1ff47a5b8 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-10.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-10.yaml
@@ -43,8 +43,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
uplink_0:
ipv4:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-2.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-2.yaml
index d6c9164a0..2b3e6f3d1 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-2.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-2.yaml
@@ -43,8 +43,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
uplink_0:
ipv4:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-4.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-4.yaml
index 55610b048..7df0682ed 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-4.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-4.yaml
@@ -43,8 +43,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
uplink_0:
ipv4:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-scale-out.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-scale-out.yaml
index d455bccea..82c487e1b 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-scale-out.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt-scale-out.yaml
@@ -44,8 +44,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type: RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate: 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
[% for vnf_num in range(num_vnfs|int) %]
uplink_[[ vnf_num ]]:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt.yaml
index 61cbd4e4e..809415a00 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput_cgnapt.yaml
@@ -42,8 +42,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type : RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate : 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
uplink_0:
ipv4:
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput_scale_out.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput_scale_out.yaml
new file mode 100644
index 000000000..71e9e817b
--- /dev/null
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput_scale_out.yaml
@@ -0,0 +1,102 @@
+# Copyright (c) 2018 Intel Corporation
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+# flow definition for ACL tests - 1K flows - ipv4 only
+#
+# the number of flows defines the widest range of parameters
+# for example if srcip_range=1.0.0.1-1.0.0.255 and dst_ip_range=10.0.0.1-10.0.1.255
+# and it should define only 16 flows
+#
+#there is assumption that packets generated will have a random sequences of following addresses pairs
+# in the packets
+# 1. src=1.x.x.x(x.x.x =random from 1..255) dst=10.x.x.x (random from 1..512)
+# 2. src=1.x.x.x(x.x.x =random from 1..255) dst=10.x.x.x (random from 1..512)
+# ...
+# 512. src=1.x.x.x(x.x.x =random from 1..255) dst=10.x.x.x (random from 1..512)
+#
+# not all combination should be filled
+# Any other field with random range will be added to flow definition
+#
+# the example.yaml provides all possibilities for traffic generation
+#
+# the profile defines a public and private side to make limited traffic correlation
+# between private and public side same way as it is made by IXIA solution.
+#
+{% set num_vnfs = get(extra_args, 'num_vnfs', 1) %}
+---
+schema: "nsb:traffic_profile:0.1"
+name: rfc2544
+description: Traffic profile to run RFC2544 latency
+traffic_profile:
+ traffic_type : RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
+ frame_rate : 100 # pc of linerate
+ # that specifies a range (e.g. ipv4 address, port)
+{% for vnf_num in range(num_vnfs|int) %}
+uplink_{{ vnf_num }}:
+ ipv4:
+ id: {{ (vnf_num * 2) + 1 }}
+ outer_l2:
+ framesize:
+ 64B: "{{get(imix, 'imix.uplink.64B', '0') }}"
+ 128B: "{{get(imix, 'imix.uplink.128B', '0') }}"
+ 256B: "{{get(imix, 'imix.uplink.256B', '0') }}"
+ 373B: "{{get(imix, 'imix.uplink.373B', '0') }}"
+ 512B: "{{get(imix, 'imix.uplink.512B', '0') }}"
+ 570B: "{{get(imix, 'imix.uplink.570B', '0') }}"
+ 1024B: "{{get(imix, 'imix.uplink.1024B', '0') }}"
+ 1280B: "{{get(imix, 'imix.uplink.1280B', '0') }}"
+ 1400B: "{{get(imix, 'imix.uplink.1400B', '0') }}"
+ 1500B: "{{get(imix, 'imix.uplink.1500B', '0') }}"
+ 1518B: "{{get(imix, 'imix.uplink.1518B', '0') }}"
+
+ outer_l3v4:
+ proto: "udp"
+ srcip4: "{{get(flow, 'flow.src_ip_{{ vnf_num }}', '10.0.2.1-10.0.2.255') }}"
+ dstip4: "{{get(flow, 'flow.dst_ip_{{ vnf_num }}', '10.0.3.1-10.0.3.255') }}"
+ count: "{{get(flow, 'flow.count', '1') }}"
+ ttl: 32
+ dscp: 0
+ outer_l4:
+ srcport: "{{get(flow, 'flow.src_port_{{ vnf_num }}', '1234-4321') }}"
+ dstport: "{{get(flow, 'flow.dst_port_{{ vnf_num }}', '2001-4001') }}"
+ count: "{{get(flow, 'flow.count', '1') }}"
+downlink_{{ vnf_num }}:
+ ipv4:
+ id: {{ (vnf_num * 2) + 2 }}
+ outer_l2:
+ framesize:
+ 64B: "{{ get(imix, 'imix.downlink.64B', '0') }}"
+ 128B: "{{ get(imix, 'imix.downlink.128B', '0') }}"
+ 256B: "{{ get(imix, 'imix.downlink.256B', '0') }}"
+ 373b: "{{ get(imix, 'imix.downlink.373B', '0') }}"
+ 512B: "{{ get(imix, 'imix.downlink.512B', '0') }}"
+ 570B: "{{get(imix, 'imix.downlink.570B', '0') }}"
+ 1024B: "{{get(imix, 'imix.downlink.1024B', '0') }}"
+ 1280B: "{{get(imix, 'imix.downlink.1280B', '0') }}"
+ 1400B: "{{get(imix, 'imix.downlink.1400B', '0') }}"
+ 1500B: "{{get(imix, 'imix.downlink.1500B', '0') }}"
+ 1518B: "{{get(imix, 'imix.downlink.1518B', '0') }}"
+
+ outer_l3v4:
+ proto: "udp"
+ srcip4: "{{get(flow, 'flow.dst_ip_{{ vnf_num }}', '10.0.3.1-10.0.3.255') }}"
+ dstip4: "{{get(flow, 'flow.src_ip_{{ vnf_num }}', '10.0.2.1-10.0.2.255') }}"
+ count: "{{get(flow, 'flow.count', '1') }}"
+ ttl: 32
+ dscp: 0
+ outer_l4:
+ srcport: "{{get(flow, 'flow.dst_port_{{ vnf_num }}', '1234-4321') }}"
+ dstport: "{{get(flow, 'flow.src_port_{{ vnf_num }}', '2001-4001') }}"
+ count: "{{get(flow, 'flow.count', '1') }}"
+{% endfor %}
diff --git a/samples/vnf_samples/traffic_profiles/ipv4_throughput_vpe.yaml b/samples/vnf_samples/traffic_profiles/ipv4_throughput_vpe.yaml
index 20bc6568d..e113c9de2 100644
--- a/samples/vnf_samples/traffic_profiles/ipv4_throughput_vpe.yaml
+++ b/samples/vnf_samples/traffic_profiles/ipv4_throughput_vpe.yaml
@@ -42,8 +42,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type : RFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate : 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
uplink_0:
ipv4:
diff --git a/samples/vnf_samples/traffic_profiles/ixia_ipv4_latency.yaml b/samples/vnf_samples/traffic_profiles/ixia_ipv4_latency.yaml
index 7b66d663b..b34672907 100644
--- a/samples/vnf_samples/traffic_profiles/ixia_ipv4_latency.yaml
+++ b/samples/vnf_samples/traffic_profiles/ixia_ipv4_latency.yaml
@@ -28,8 +28,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type : IXIARFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate : 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
uplink_0:
ipv4:
diff --git a/samples/vnf_samples/traffic_profiles/ixia_ipv4_latency_cgnapt.yaml b/samples/vnf_samples/traffic_profiles/ixia_ipv4_latency_cgnapt.yaml
index 8fdfe9b2f..513aefb40 100644
--- a/samples/vnf_samples/traffic_profiles/ixia_ipv4_latency_cgnapt.yaml
+++ b/samples/vnf_samples/traffic_profiles/ixia_ipv4_latency_cgnapt.yaml
@@ -28,8 +28,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type : IXIARFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate : 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
-
+ duration: {{ duration }}
uplink_0:
ipv4:
diff --git a/samples/vnf_samples/traffic_profiles/ixia_ipv4_latency_vpe.yaml b/samples/vnf_samples/traffic_profiles/ixia_ipv4_latency_vpe.yaml
index 4d73b8ffe..aad751549 100644
--- a/samples/vnf_samples/traffic_profiles/ixia_ipv4_latency_vpe.yaml
+++ b/samples/vnf_samples/traffic_profiles/ixia_ipv4_latency_vpe.yaml
@@ -42,7 +42,7 @@ description: Traffic profile to run RFC2544 latency
traffic_profile:
traffic_type : IXIARFC2544Profile # defines traffic behavior - constant or look for highest possible throughput
frame_rate : 100 # pc of linerate
- # that specifies a range (e.g. ipv4 address, port)
+ injection_time: {{ injection_time }}
uplink_0:
ipv4:
diff --git a/yardstick/benchmark/scenarios/networking/vnf_generic.py b/yardstick/benchmark/scenarios/networking/vnf_generic.py
index 1c3ea1f8d..4d7c4f9be 100644
--- a/yardstick/benchmark/scenarios/networking/vnf_generic.py
+++ b/yardstick/benchmark/scenarios/networking/vnf_generic.py
@@ -133,11 +133,10 @@ class NetworkServiceTestCase(scenario_base.Scenario):
with utils.open_relative_file(profile, path) as infile:
return infile.read()
- def _get_topology(self):
- topology = self.scenario_cfg["topology"]
- path = self.scenario_cfg["task_path"]
- with utils.open_relative_file(topology, path) as infile:
- return infile.read()
+ def _get_duration(self):
+ options = self.scenario_cfg.get('options', {})
+ return options.get('duration',
+ tprofile_base.TrafficProfileConfig.DEFAULT_DURATION)
def _fill_traffic_profile(self):
tprofile = self._get_traffic_profile()
@@ -147,12 +146,17 @@ class NetworkServiceTestCase(scenario_base.Scenario):
'imix': self._get_traffic_imix(),
tprofile_base.TrafficProfile.UPLINK: {},
tprofile_base.TrafficProfile.DOWNLINK: {},
- 'extra_args': extra_args
- }
-
+ 'extra_args': extra_args,
+ 'duration': self._get_duration()}
traffic_vnfd = vnfdgen.generate_vnfd(tprofile, tprofile_data)
self.traffic_profile = tprofile_base.TrafficProfile.get(traffic_vnfd)
+ def _get_topology(self):
+ topology = self.scenario_cfg["topology"]
+ path = self.scenario_cfg["task_path"]
+ with utils.open_relative_file(topology, path) as infile:
+ return infile.read()
+
def _render_topology(self):
topology = self._get_topology()
topology_args = self.scenario_cfg.get('extra_args', {})
diff --git a/yardstick/common/utils.py b/yardstick/common/utils.py
index 869db469b..f9fe0e336 100644
--- a/yardstick/common/utils.py
+++ b/yardstick/common/utils.py
@@ -422,13 +422,18 @@ class ErrorClass(object):
class Timer(object):
- def __init__(self, timeout=None):
+ def __init__(self, timeout=None, raise_exception=True):
super(Timer, self).__init__()
self.start = self.delta = None
self._timeout = int(timeout) if timeout else None
+ self._timeout_flag = False
+ self._raise_exception = raise_exception
def _timeout_handler(self, *args):
- raise exceptions.TimerTimeout(timeout=self._timeout)
+ self._timeout_flag = True
+ if self._raise_exception:
+ raise exceptions.TimerTimeout(timeout=self._timeout)
+ self.__exit__()
def __enter__(self):
self.start = datetime.datetime.now()
@@ -445,6 +450,23 @@ class Timer(object):
def __getattr__(self, item):
return getattr(self.delta, item)
+ def __iter__(self):
+ self._raise_exception = False
+ return self.__enter__()
+
+ def next(self): # pragma: no cover
+ # NOTE(ralonsoh): Python 2 support.
+ if not self._timeout_flag:
+ return datetime.datetime.now()
+ raise StopIteration()
+
+ def __next__(self): # pragma: no cover
+ # NOTE(ralonsoh): Python 3 support.
+ return self.next()
+
+ def __del__(self): # pragma: no cover
+ signal.alarm(0)
+
def read_meminfo(ssh_client):
"""Read "/proc/meminfo" file and parse all keys and values"""
diff --git a/yardstick/network_services/traffic_profile/base.py b/yardstick/network_services/traffic_profile/base.py
index 9eba550aa..f4b5b178c 100644
--- a/yardstick/network_services/traffic_profile/base.py
+++ b/yardstick/network_services/traffic_profile/base.py
@@ -16,6 +16,31 @@ from yardstick.common import exceptions
from yardstick.common import utils
+class TrafficProfileConfig(object):
+ """Class to contain the TrafficProfile class information
+
+ This object will parse and validate the traffic profile information.
+ """
+
+ DEFAULT_SCHEMA = 'nsb:traffic_profile:0.1'
+ DEFAULT_FRAME_RATE = 100
+ DEFAULT_DURATION = 30
+
+ def __init__(self, tp_config):
+ self.schema = tp_config.get('schema', self.DEFAULT_SCHEMA)
+ self.name = tp_config.get('name')
+ self.description = tp_config.get('description')
+ tprofile = tp_config['traffic_profile']
+ self.traffic_type = tprofile.get('traffic_type')
+ self.frame_rate = tprofile.get('frame_rate', self.DEFAULT_FRAME_RATE)
+ self.test_precision = tprofile.get('test_precision')
+ self.packet_sizes = tprofile.get('packet_sizes')
+ self.duration = tprofile.get('duration', self.DEFAULT_DURATION)
+ self.lower_bound = tprofile.get('lower_bound')
+ self.upper_bound = tprofile.get('upper_bound')
+ self.step_interval = tprofile.get('step_interval')
+
+
class TrafficProfile(object):
"""
This class defines the behavior
@@ -43,6 +68,7 @@ class TrafficProfile(object):
# e.g. RFC2544 start_ip, stop_ip, drop_rate,
# IMIX = {"10K": 0.1, "100M": 0.5}
self.params = tp_config
+ self.config = TrafficProfileConfig(tp_config)
def execute_traffic(self, traffic_generator, **kawrgs):
""" This methods defines the behavior of the traffic generator.
diff --git a/yardstick/network_services/traffic_profile/ixia_rfc2544.py b/yardstick/network_services/traffic_profile/ixia_rfc2544.py
index 73806f958..e105c2f55 100644
--- a/yardstick/network_services/traffic_profile/ixia_rfc2544.py
+++ b/yardstick/network_services/traffic_profile/ixia_rfc2544.py
@@ -95,7 +95,6 @@ class IXIARFC2544Profile(TrexProfile):
if not profile_data:
continue
self.profile_data = profile_data
- self.get_streams(self.profile_data)
self.full_profile.update({vld_id: self.profile_data})
for intf in intfs:
yield traffic_generator.vnfd_helper.port_num(intf)
diff --git a/yardstick/network_services/traffic_profile/rfc2544.py b/yardstick/network_services/traffic_profile/rfc2544.py
index 83020c85c..c24e2f65a 100644
--- a/yardstick/network_services/traffic_profile/rfc2544.py
+++ b/yardstick/network_services/traffic_profile/rfc2544.py
@@ -11,190 +11,288 @@
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
-""" RFC2544 Throughput implemenation """
-from __future__ import absolute_import
-from __future__ import division
import logging
-from trex_stl_lib.trex_stl_client import STLStream
-from trex_stl_lib.trex_stl_streams import STLFlowLatencyStats
-from trex_stl_lib.trex_stl_streams import STLTXCont
+from trex_stl_lib import api as Pkt
+from trex_stl_lib import trex_stl_client
+from trex_stl_lib import trex_stl_packet_builder_scapy
+from trex_stl_lib import trex_stl_streams
+
+from yardstick.network_services.traffic_profile import trex_traffic_profile
-from yardstick.network_services.traffic_profile.trex_traffic_profile \
- import TrexProfile
LOGGING = logging.getLogger(__name__)
+SRC_PORT = 'sport'
+DST_PORT = 'dport'
+
+
+class PortPgIDMap(object):
+ """Port and pg_id mapping class
+
+ "pg_id" is the identification STL library gives to each stream. In the
+ RFC2544Profile class, the traffic has a STLProfile per port, which contains
+ one or several streams, one per packet size defined in the IMIX test case
+ description.
+
+ Example of port <-> pg_id map:
+ self._port_pg_id_map = {
+ 0: [1, 2, 3, 4],
+ 1: [5, 6, 7, 8]
+ }
+ """
+
+ def __init__(self):
+ self._pg_id = 0
+ self._last_port = None
+ self._port_pg_id_map = {}
+
+ def add_port(self, port):
+ self._last_port = port
+ self._port_pg_id_map[port] = []
+
+ def get_pg_ids(self, port):
+ return self._port_pg_id_map.get(port)
+
+ def increase_pg_id(self, port=None):
+ port = self._last_port if not port else port
+ if port is None:
+ return
+ pg_id_list = self._port_pg_id_map.get(port)
+ if not pg_id_list:
+ self.add_port(port)
+ pg_id_list = self._port_pg_id_map[port]
+ self._pg_id += 1
+ pg_id_list.append(self._pg_id)
+ return self._pg_id
-class RFC2544Profile(TrexProfile):
- """ This class handles rfc2544 implemenation. """
+class RFC2544Profile(trex_traffic_profile.TrexProfile):
+ """TRex RFC2544 traffic profile"""
+
+ TOLERANCE_LIMIT = 0.05
def __init__(self, traffic_generator):
super(RFC2544Profile, self).__init__(traffic_generator)
self.generator = None
- self.max_rate = None
- self.min_rate = None
- self.ports = None
- self.rate = 100
- self.drop_percent_at_max_tx = None
- self.throughput_max = None
+ self.rate = self.config.frame_rate
+ self.max_rate = self.config.frame_rate
+ self.min_rate = 0
+ self.drop_percent_max = 0
def register_generator(self, generator):
self.generator = generator
- def execute_traffic(self, traffic_generator=None):
- """ Generate the stream and run traffic on the given ports """
+ def stop_traffic(self, traffic_generator=None):
+ """"Stop traffic injection, reset counters and remove streams"""
if traffic_generator is not None and self.generator is None:
self.generator = traffic_generator
- if self.ports is not None:
- return
+ self.generator.client.stop()
+ self.generator.client.reset()
+ self.generator.client.remove_all_streams()
+
+ def execute_traffic(self, traffic_generator=None):
+ """Generate the stream and run traffic on the given ports
+
+ :param traffic_generator: (TrexTrafficGenRFC) traffic generator
+ :return ports: (list of int) indexes of ports
+ port_pg_id: (dict) port indexes and pg_id [1] map
+ [1] https://trex-tgn.cisco.com/trex/doc/cp_stl_docs/api/
+ profile_code.html#stlstream-modes
+ """
+ if traffic_generator is not None and self.generator is None:
+ self.generator = traffic_generator
- self.ports = []
+ port_pg_id = PortPgIDMap()
+ ports = []
for vld_id, intfs in sorted(self.generator.networks.items()):
profile_data = self.params.get(vld_id)
- # no profile for this port
if not profile_data:
continue
- # correlated traffic doesn't use public traffic?
- if vld_id.startswith(self.DOWNLINK) and \
- self.generator.rfc2544_helper.correlated_traffic:
+ if (vld_id.startswith(self.DOWNLINK) and
+ self.generator.rfc2544_helper.correlated_traffic):
continue
for intf in intfs:
- port = self.generator.port_num(intf)
- self.ports.append(port)
- self.generator.client.add_streams(self.get_streams(profile_data), ports=port)
-
- self.max_rate = self.rate
- self.min_rate = 0
- self.generator.client.start(ports=self.ports, mult=self.get_multiplier(),
- duration=30, force=True)
- self.drop_percent_at_max_tx = 0
- self.throughput_max = 0
-
- def get_multiplier(self):
- """ Get the rate at which next iteration to run """
- self.rate = round((self.max_rate + self.min_rate) / 2.0, 2)
- multiplier = round(self.rate / self.pps, 2)
- return str(multiplier)
-
- def get_drop_percentage(self, generator=None):
- """ Calculate the drop percentage and run the traffic """
- if generator is None:
- generator = self.generator
- run_duration = self.generator.RUN_DURATION
- samples = self.generator.generate_samples(self.ports)
-
- in_packets = sum([value['in_packets'] for value in samples.values()])
- out_packets = sum([value['out_packets'] for value in samples.values()])
-
- packet_drop = abs(out_packets - in_packets)
- drop_percent = 100.0
- try:
- drop_percent = round((packet_drop / float(out_packets)) * 100, 5)
- except ZeroDivisionError:
- LOGGING.info('No traffic is flowing')
+ port_num = int(self.generator.port_num(intf))
+ ports.append(port_num)
+ port_pg_id.add_port(port_num)
+ profile = self._create_profile(profile_data,
+ self.rate, port_pg_id)
+ self.generator.client.add_streams(profile, ports=[port_num])
+
+ self.generator.client.start(ports=ports,
+ duration=self.config.duration,
+ force=True)
+ return ports, port_pg_id
+
+ def _create_profile(self, profile_data, rate, port_pg_id):
+ """Create a STL profile (list of streams) for a port"""
+ streams = []
+ for packet_name in profile_data:
+ imix = (profile_data[packet_name].
+ get('outer_l2', {}).get('framesize'))
+ imix_data = self._create_imix_data(imix)
+ self._create_vm(profile_data[packet_name])
+ _streams = self._create_streams(imix_data, rate, port_pg_id)
+ streams.extend(_streams)
+ return trex_stl_streams.STLProfile(streams)
+
+ def _create_imix_data(self, imix):
+ """Generate the IMIX distribution for a STL profile
+
+ The input information is the framesize dictionary in a test case
+ traffic profile definition. E.g.:
+ downlink_0:
+ ipv4:
+ id: 2
+ outer_l2:
+ framesize:
+ 64B: 10
+ 128B: 20
+ ...
+
+ This function normalizes the sum of framesize weights to 100 and
+ returns a dictionary of frame sizes in bytes and weight in percentage.
+ E.g.:
+ imix_count = {64: 25, 128: 75}
+
+ :param imix: (dict) IMIX size and weight
+ """
+ imix_count = {}
+ if not imix:
+ return imix_count
+
+ imix_count = {size.upper().replace('B', ''): int(weight)
+ for size, weight in imix.items()}
+ imix_sum = sum(imix_count.values())
+ if imix_sum <= 0:
+ imix_count = {64: 100}
+ imix_sum = 100
+
+ weight_normalize = float(imix_sum) / 100
+ return {size: float(weight) / weight_normalize
+ for size, weight in imix_count.items()}
+
+ def _create_vm(self, packet_definition):
+ """Create the STL Raw instructions"""
+ self.ether_packet = Pkt.Ether()
+ self.ip_packet = Pkt.IP()
+ self.ip6_packet = None
+ self.udp_packet = Pkt.UDP()
+ self.udp[DST_PORT] = 'UDP.dport'
+ self.udp[SRC_PORT] = 'UDP.sport'
+ self.qinq = False
+ self.vm_flow_vars = []
+ outer_l2 = packet_definition.get('outer_l2')
+ outer_l3v4 = packet_definition.get('outer_l3v4')
+ outer_l3v6 = packet_definition.get('outer_l3v6')
+ outer_l4 = packet_definition.get('outer_l4')
+ if outer_l2:
+ self._set_outer_l2_fields(outer_l2)
+ if outer_l3v4:
+ self._set_outer_l3v4_fields(outer_l3v4)
+ if outer_l3v6:
+ self._set_outer_l3v6_fields(outer_l3v6)
+ if outer_l4:
+ self._set_outer_l4_fields(outer_l4)
+ self.trex_vm = trex_stl_packet_builder_scapy.STLScVmRaw(
+ self.vm_flow_vars)
+
+ def _create_single_packet(self, size=64):
+ size -= 4
+ ether_packet = self.ether_packet
+ ip_packet = self.ip6_packet if self.ip6_packet else self.ip_packet
+ udp_packet = self.udp_packet
+ if self.qinq:
+ qinq_packet = self.qinq_packet
+ base_pkt = ether_packet / qinq_packet / ip_packet / udp_packet
+ else:
+ base_pkt = ether_packet / ip_packet / udp_packet
+ pad = max(0, size - len(base_pkt)) * 'x'
+ return trex_stl_packet_builder_scapy.STLPktBuilder(
+ pkt=base_pkt / pad, vm=self.trex_vm)
+
+ def _create_streams(self, imix_data, rate, port_pg_id):
+ """Create a list of streams per packet size
+
+ The STL TX mode speed of the generated streams will depend on the frame
+ weight and the frame rate. Both the frame weight and the total frame
+ rate are normalized to 100. The STL TX mode speed, defined in
+ percentage, is the combitation of both percentages. E.g.:
+ frame weight = 100
+ rate = 90
+ --> STLTXmode percentage = 10 (%)
+
+ frame weight = 80
+ rate = 50
+ --> STLTXmode percentage = 40 (%)
+
+ :param imix_data: (dict) IMIX size and weight
+ :param rate: (float) normalized [0..100] total weight
+ :param pg_id: (PortPgIDMap) port / pg_id (list) map
+ """
+ streams = []
+ for size, weight in ((int(size), float(weight)) for (size, weight)
+ in imix_data.items() if float(weight) > 0):
+ packet = self._create_single_packet(size)
+ pg_id = port_pg_id.increase_pg_id()
+ stl_flow = trex_stl_streams.STLFlowLatencyStats(pg_id=pg_id)
+ mode = trex_stl_streams.STLTXCont(percentage=weight * rate / 100)
+ streams.append(trex_stl_client.STLStream(
+ packet=packet, flow_stats=stl_flow, mode=mode))
+ return streams
+
+ def get_drop_percentage(self, samples, tol_low, tol_high,
+ correlated_traffic):
+ """Calculate the drop percentage and run the traffic"""
+ tx_rate_fps = 0
+ rx_rate_fps = 0
+ for sample in samples:
+ tx_rate_fps += sum(
+ port['tx_throughput_fps'] for port in sample.values())
+ rx_rate_fps += sum(
+ port['rx_throughput_fps'] for port in sample.values())
+ tx_rate_fps = round(float(tx_rate_fps) / len(samples), 2)
+ rx_rate_fps = round(float(rx_rate_fps) / len(samples), 2)
# TODO(esm): RFC2544 doesn't tolerate packet loss, why do we?
- tolerance_low = generator.rfc2544_helper.tolerance_low
- tolerance_high = generator.rfc2544_helper.tolerance_high
-
- tx_rate = out_packets / run_duration
- rx_rate = in_packets / run_duration
-
- throughput_max = self.throughput_max
- drop_percent_at_max_tx = self.drop_percent_at_max_tx
+ out_packets = sum(port['out_packets'] for port in samples[-1].values())
+ in_packets = sum(port['in_packets'] for port in samples[-1].values())
+ drop_percent = 100.0
- if self.drop_percent_at_max_tx is None:
- self.rate = tx_rate
- self.first_run = False
+ # https://tools.ietf.org/html/rfc2544#section-26.3
+ if out_packets:
+ drop_percent = round(
+ (float(abs(out_packets - in_packets)) / out_packets) * 100, 5)
- if drop_percent > tolerance_high:
- # TODO(esm): why don't we discard results that are out of tolerance?
+ tol_high = tol_high if tol_high > self.TOLERANCE_LIMIT else tol_high
+ tol_low = tol_low if tol_low > self.TOLERANCE_LIMIT else tol_low
+ if drop_percent > tol_high:
self.max_rate = self.rate
- if throughput_max == 0:
- throughput_max = rx_rate
- drop_percent_at_max_tx = drop_percent
-
- elif drop_percent >= tolerance_low:
- # TODO(esm): why do we update the samples dict in this case
- # and not update our tracking values?
- throughput_max = rx_rate
- drop_percent_at_max_tx = drop_percent
-
- elif drop_percent >= self.drop_percent_at_max_tx:
- # TODO(esm): why don't we discard results that are out of tolerance?
+ elif drop_percent < tol_low:
self.min_rate = self.rate
- self.drop_percent_at_max_tx = drop_percent_at_max_tx = drop_percent
- self.throughput_max = throughput_max = rx_rate
+ # else:
+ # NOTE(ralonsoh): the test should finish here
+ # pass
+ last_rate = self.rate
+ self.rate = round(float(self.max_rate + self.min_rate) / 2.0, 5)
- else:
- # TODO(esm): why don't we discard results that are out of tolerance?
- self.min_rate = self.rate
+ throughput = rx_rate_fps * 2 if correlated_traffic else rx_rate_fps
- generator.clear_client_stats(self.ports)
- generator.start_client(self.ports, mult=self.get_multiplier(),
- duration=run_duration, force=True)
+ if drop_percent > self.drop_percent_max:
+ self.drop_percent_max = drop_percent
- # if correlated traffic update the Throughput
- if generator.rfc2544_helper.correlated_traffic:
- throughput_max *= 2
+ latency = {port_num: value['latency']
+ for port_num, value in samples[-1].items()}
- samples.update({
- 'TxThroughput': tx_rate,
- 'RxThroughput': rx_rate,
+ output = {
+ 'TxThroughput': tx_rate_fps,
+ 'RxThroughput': rx_rate_fps,
'CurrentDropPercentage': drop_percent,
- 'Throughput': throughput_max,
- 'DropPercentage': drop_percent_at_max_tx,
- })
-
- return samples
-
- def execute_latency(self, generator=None, samples=None):
- if generator is not None and self.generator is None:
- self.generator = generator
-
- if samples is None:
- samples = self.generator.generate_samples()
-
- self.pps, multiplier = self.calculate_pps(samples)
- self.ports = []
- self.pg_id = self.params['traffic_profile'].get('pg_id', 1)
- for vld_id, intfs in sorted(self.generator.networks.items()):
- profile_data = self.params.get(vld_id)
- if not profile_data:
- continue
- # correlated traffic doesn't use public traffic?
- if vld_id.startswith(self.DOWNLINK) and \
- self.generator.rfc2544_helper.correlated_traffic:
- continue
- for intf in intfs:
- port = self.generator.port_num(intf)
- self.ports.append(port)
- self.generator.client.add_streams(self.get_streams(profile_data), ports=port)
-
- self.generator.start_client(ports=self.ports, mult=str(multiplier),
- duration=120, force=True)
- self.first_run = False
-
- def calculate_pps(self, samples):
- pps = round(samples['Throughput'] / 2, 2)
- multiplier = round(self.rate / self.pps, 2)
- return pps, multiplier
-
- def create_single_stream(self, packet_size, pps, isg=0):
- packet = self._create_single_packet(packet_size)
- if pps:
- stl_mode = STLTXCont(pps=pps)
- else:
- stl_mode = STLTXCont(pps=self.pps)
- if self.pg_id:
- LOGGING.debug("pg_id: %s", self.pg_id)
- stl_flow_stats = STLFlowLatencyStats(pg_id=self.pg_id)
- stream = STLStream(isg=isg, packet=packet, mode=stl_mode,
- flow_stats=stl_flow_stats)
- self.pg_id += 1
- else:
- stream = STLStream(isg=isg, packet=packet, mode=stl_mode)
- return stream
+ 'Throughput': throughput,
+ 'DropPercentage': self.drop_percent_max,
+ 'Rate': last_rate,
+ 'Latency': latency
+ }
+ return output
diff --git a/yardstick/network_services/traffic_profile/trex_traffic_profile.py b/yardstick/network_services/traffic_profile/trex_traffic_profile.py
index f5e3923d5..ed0355fa5 100644
--- a/yardstick/network_services/traffic_profile/trex_traffic_profile.py
+++ b/yardstick/network_services/traffic_profile/trex_traffic_profile.py
@@ -19,21 +19,16 @@ from random import SystemRandom
import ipaddress
import six
-
-from yardstick.common import exceptions as y_exc
-from yardstick.network_services.traffic_profile import base
-from trex_stl_lib.trex_stl_client import STLStream
-from trex_stl_lib.trex_stl_streams import STLFlowLatencyStats
-from trex_stl_lib.trex_stl_streams import STLTXCont
-from trex_stl_lib.trex_stl_streams import STLProfile
from trex_stl_lib.trex_stl_packet_builder_scapy import STLVmWrFlowVar
from trex_stl_lib.trex_stl_packet_builder_scapy import STLVmFlowVarRepeatableRandom
from trex_stl_lib.trex_stl_packet_builder_scapy import STLVmFlowVar
-from trex_stl_lib.trex_stl_packet_builder_scapy import STLPktBuilder
-from trex_stl_lib.trex_stl_packet_builder_scapy import STLScVmRaw
from trex_stl_lib.trex_stl_packet_builder_scapy import STLVmFixIpv4
from trex_stl_lib import api as Pkt
+from yardstick.common import exceptions as y_exc
+from yardstick.network_services.traffic_profile import base
+
+
SRC = 'src'
DST = 'dst'
ETHERNET = 'Ethernet'
@@ -342,115 +337,6 @@ class TrexProfile(base.TrafficProfile):
if 'dstport' in outer_l4:
self._set_proto_addr(UDP, DST_PORT, outer_l4['dstport'], outer_l4['count'])
- def generate_imix_data(self, packet_definition):
- """ generate packet size for a given traffic profile """
- imix_count = {}
- imix_data = {}
- if not packet_definition:
- return imix_count
- imix = packet_definition.get('framesize')
- if imix:
- for size in imix:
- data = imix[size]
- imix_data[int(size[:-1])] = int(data)
- imix_sum = sum(imix_data.values())
- if imix_sum > 100:
- raise SystemExit("Error in IMIX data")
- elif imix_sum < 100:
- imix_data[64] = imix_data.get(64, 0) + (100 - imix_sum)
-
- avg_size = 0.0
- for size in imix_data:
- count = int(imix_data[size])
- if count:
- avg_size += round(size * count / 100, 2)
- pps = round(self.pps * count / 100, 0)
- imix_count[size] = pps
- self.rate = round(1342177280 / avg_size, 0) * 2
- logging.debug("Imax: %s rate: %s", imix_count, self.rate)
- return imix_count
-
- def get_streams(self, profile_data):
- """ generate trex stream
- :param profile_data:
- :type profile_data:
- """
- self.streams = []
- self.pps = self.params['traffic_profile'].get('frame_rate', 100)
- for packet_name in profile_data:
- outer_l2 = profile_data[packet_name].get('outer_l2')
- imix_data = self.generate_imix_data(outer_l2)
- if not imix_data:
- imix_data = {64: self.pps}
- self.generate_vm(profile_data[packet_name])
- for size in imix_data:
- self._generate_streams(size, imix_data[size])
- self._generate_profile()
- return self.profile
-
- def generate_vm(self, packet_definition):
- """ generate trex vm with flows setup """
- self.ether_packet = Pkt.Ether()
- self.ip_packet = Pkt.IP()
- self.ip6_packet = None
- self.udp_packet = Pkt.UDP()
- self.udp[DST_PORT] = 'UDP.dport'
- self.udp[SRC_PORT] = 'UDP.sport'
- self.qinq = False
- self.vm_flow_vars = []
- outer_l2 = packet_definition.get('outer_l2', None)
- outer_l3v4 = packet_definition.get('outer_l3v4', None)
- outer_l3v6 = packet_definition.get('outer_l3v6', None)
- outer_l4 = packet_definition.get('outer_l4', None)
- if outer_l2:
- self._set_outer_l2_fields(outer_l2)
- if outer_l3v4:
- self._set_outer_l3v4_fields(outer_l3v4)
- if outer_l3v6:
- self._set_outer_l3v6_fields(outer_l3v6)
- if outer_l4:
- self._set_outer_l4_fields(outer_l4)
- self.trex_vm = STLScVmRaw(self.vm_flow_vars)
-
- def generate_packets(self):
- """ generate packets from trex TG """
- base_pkt = self.base_pkt
- size = self.fsize - 4
- pad = max(0, size - len(base_pkt)) * 'x'
- self.packets = [STLPktBuilder(pkt=base_pkt / pad,
- vm=vm) for vm in self.vms]
-
- def _create_single_packet(self, size=64):
- size = size - 4
- ether_packet = self.ether_packet
- ip_packet = self.ip6_packet if self.ip6_packet else self.ip_packet
- udp_packet = self.udp_packet
- if self.qinq:
- qinq_packet = self.qinq_packet
- base_pkt = ether_packet / qinq_packet / ip_packet / udp_packet
- else:
- base_pkt = ether_packet / ip_packet / udp_packet
- pad = max(0, size - len(base_pkt)) * 'x'
- packet = STLPktBuilder(pkt=base_pkt / pad, vm=self.trex_vm)
- return packet
-
- def _create_single_stream(self, packet_size, pps, isg=0):
- packet = self._create_single_packet(packet_size)
- if self.pg_id:
- self.pg_id += 1
- stl_flow = STLFlowLatencyStats(pg_id=self.pg_id)
- stream = STLStream(isg=isg, packet=packet, mode=STLTXCont(pps=pps),
- flow_stats=stl_flow)
- else:
- stream = STLStream(isg=isg, packet=packet, mode=STLTXCont(pps=pps))
- return stream
-
- def _generate_streams(self, packet_size, pps):
- self.streams.append(self._create_single_stream(packet_size, pps))
-
- def _generate_profile(self):
- self.profile = STLProfile(self.streams)
-
@classmethod
def _count_ip(cls, start_ip, end_ip):
start = ipaddress.ip_address(six.u(start_ip))
diff --git a/yardstick/network_services/vnf_generic/vnf/sample_vnf.py b/yardstick/network_services/vnf_generic/vnf/sample_vnf.py
index 653603da8..3976acb76 100644
--- a/yardstick/network_services/vnf_generic/vnf/sample_vnf.py
+++ b/yardstick/network_services/vnf_generic/vnf/sample_vnf.py
@@ -11,20 +11,17 @@
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
-""" Base class implementation for generic vnf implementation """
-from collections import Mapping
import logging
from multiprocessing import Queue, Value, Process
import os
import posixpath
import re
+import six
import subprocess
import time
-import six
-
from trex_stl_lib.trex_stl_client import LoggerApi
from trex_stl_lib.trex_stl_client import STLClient
from trex_stl_lib.trex_stl_exceptions import STLError
@@ -388,39 +385,14 @@ class ClientResourceHelper(ResourceHelper):
LOG.error('TRex client not connected')
return {}
- def generate_samples(self, ports, key=None, default=None):
- # needs to be used ports
- last_result = self.get_stats(ports)
- key_value = last_result.get(key, default)
-
- if not isinstance(last_result, Mapping): # added for mock unit test
- self._terminated.value = 1
- return {}
-
- samples = {}
- # recalculate port for interface and see if it matches ports provided
- for intf in self.vnfd_helper.interfaces:
- name = intf["name"]
- port = self.vnfd_helper.port_num(name)
- if port in ports:
- xe_value = last_result.get(port, {})
- samples[name] = {
- "rx_throughput_fps": float(xe_value.get("rx_pps", 0.0)),
- "tx_throughput_fps": float(xe_value.get("tx_pps", 0.0)),
- "rx_throughput_mbps": float(xe_value.get("rx_bps", 0.0)),
- "tx_throughput_mbps": float(xe_value.get("tx_bps", 0.0)),
- "in_packets": int(xe_value.get("ipackets", 0)),
- "out_packets": int(xe_value.get("opackets", 0)),
- }
- if key:
- samples[name][key] = key_value
- return samples
+ def _get_samples(self, ports, port_pg_id=False):
+ raise NotImplementedError()
def _run_traffic_once(self, traffic_profile):
traffic_profile.execute_traffic(self)
self.client_started.value = 1
time.sleep(self.RUN_DURATION)
- samples = self.generate_samples(traffic_profile.ports)
+ samples = self._get_samples(traffic_profile.ports)
time.sleep(self.QUEUE_WAIT_TIME)
self._queue.put(samples)
diff --git a/yardstick/network_services/vnf_generic/vnf/tg_rfc2544_trex.py b/yardstick/network_services/vnf_generic/vnf/tg_rfc2544_trex.py
index 4e9f4bdc1..07cec6745 100644
--- a/yardstick/network_services/vnf_generic/vnf/tg_rfc2544_trex.py
+++ b/yardstick/network_services/vnf_generic/vnf/tg_rfc2544_trex.py
@@ -11,74 +11,45 @@
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
-""" Trex traffic generation definitions which implements rfc2544 """
-from __future__ import absolute_import
-from __future__ import print_function
-import time
import logging
-from collections import Mapping
-
-from yardstick.network_services.vnf_generic.vnf.tg_trex import TrexTrafficGen
-from yardstick.network_services.vnf_generic.vnf.sample_vnf import Rfc2544ResourceHelper
-from yardstick.network_services.vnf_generic.vnf.tg_trex import TrexResourceHelper
-
-LOGGING = logging.getLogger(__name__)
+import time
+from yardstick.common import utils
+from yardstick.network_services.vnf_generic.vnf import sample_vnf
+from yardstick.network_services.vnf_generic.vnf import tg_trex
-class TrexRfc2544ResourceHelper(Rfc2544ResourceHelper):
- def is_done(self):
- return self.latency and self.iteration.value > 10
+LOGGING = logging.getLogger(__name__)
-class TrexRfcResourceHelper(TrexResourceHelper):
+class TrexRfcResourceHelper(tg_trex.TrexResourceHelper):
- LATENCY_TIME_SLEEP = 120
- RUN_DURATION = 30
- WAIT_TIME = 3
+ SAMPLING_PERIOD = 2
+ TRANSIENT_PERIOD = 10
- def __init__(self, setup_helper, rfc_helper_type=None):
+ def __init__(self, setup_helper):
super(TrexRfcResourceHelper, self).__init__(setup_helper)
-
- if rfc_helper_type is None:
- rfc_helper_type = TrexRfc2544ResourceHelper
-
- self.rfc2544_helper = rfc_helper_type(self.scenario_helper)
+ self.rfc2544_helper = sample_vnf.Rfc2544ResourceHelper(
+ self.scenario_helper)
def _run_traffic_once(self, traffic_profile):
- if self._terminated.value:
- return
-
- traffic_profile.execute_traffic(self)
self.client_started.value = 1
- time.sleep(self.RUN_DURATION)
- self.client.stop(traffic_profile.ports)
- time.sleep(self.WAIT_TIME)
- samples = traffic_profile.get_drop_percentage(self)
- self._queue.put(samples)
-
- if not self.rfc2544_helper.is_done():
- return
-
- self.client.stop(traffic_profile.ports)
- self.client.reset(ports=traffic_profile.ports)
- self.client.remove_all_streams(traffic_profile.ports)
- traffic_profile.execute_traffic_latency(samples=samples)
- multiplier = traffic_profile.calculate_pps(samples)[1]
- for _ in range(5):
- time.sleep(self.LATENCY_TIME_SLEEP)
- self.client.stop(traffic_profile.ports)
- time.sleep(self.WAIT_TIME)
- last_res = self.client.get_stats(traffic_profile.ports)
- if not isinstance(last_res, Mapping):
- self._terminated.value = 1
- continue
- self.generate_samples(traffic_profile.ports, 'latency', {})
- self._queue.put(samples)
- self.client.start(mult=str(multiplier),
- ports=traffic_profile.ports,
- duration=120, force=True)
+ ports, port_pg_id = traffic_profile.execute_traffic(self)
+
+ samples = []
+ timeout = int(traffic_profile.config.duration) - self.TRANSIENT_PERIOD
+ time.sleep(self.TRANSIENT_PERIOD)
+ for _ in utils.Timer(timeout=timeout):
+ samples.append(self._get_samples(ports, port_pg_id=port_pg_id))
+ time.sleep(self.SAMPLING_PERIOD)
+
+ traffic_profile.stop_traffic(self)
+ output = traffic_profile.get_drop_percentage(
+ samples, self.rfc2544_helper.tolerance_low,
+ self.rfc2544_helper.tolerance_high,
+ self.rfc2544_helper.correlated_traffic)
+ self._queue.put(output)
def start_client(self, ports, mult=None, duration=None, force=True):
self.client.start(ports=ports, mult=mult, duration=duration, force=force)
@@ -86,12 +57,8 @@ class TrexRfcResourceHelper(TrexResourceHelper):
def clear_client_stats(self, ports):
self.client.clear_stats(ports=ports)
- def collect_kpi(self):
- self.rfc2544_helper.iteration.value += 1
- return super(TrexRfcResourceHelper, self).collect_kpi()
-
-class TrexTrafficGenRFC(TrexTrafficGen):
+class TrexTrafficGenRFC(tg_trex.TrexTrafficGen):
"""
This class handles mapping traffic profile and generating
traffic for rfc2544 testcase.
diff --git a/yardstick/network_services/vnf_generic/vnf/tg_trex.py b/yardstick/network_services/vnf_generic/vnf/tg_trex.py
index 0084a124c..80b42e22d 100644
--- a/yardstick/network_services/vnf_generic/vnf/tg_trex.py
+++ b/yardstick/network_services/vnf_generic/vnf/tg_trex.py
@@ -13,7 +13,6 @@
# limitations under the License.
""" Trex acts as traffic generation and vnf definitions based on IETS Spec """
-from __future__ import absolute_import
import logging
import os
@@ -25,6 +24,7 @@ from yardstick.network_services.vnf_generic.vnf.sample_vnf import SampleVNFTraff
from yardstick.network_services.vnf_generic.vnf.sample_vnf import ClientResourceHelper
from yardstick.network_services.vnf_generic.vnf.sample_vnf import DpdkVnfSetupEnvHelper
+
LOG = logging.getLogger(__name__)
@@ -165,6 +165,30 @@ class TrexResourceHelper(ClientResourceHelper):
cmd = "sudo fuser -n tcp %s %s -k > /dev/null 2>&1"
self.ssh_helper.execute(cmd % (self.SYNC_PORT, self.ASYNC_PORT))
+ def _get_samples(self, ports, port_pg_id=None):
+ stats = self.get_stats(ports)
+ samples = {}
+ for pname in (intf['name'] for intf in self.vnfd_helper.interfaces):
+ port_num = self.vnfd_helper.port_num(pname)
+ port_stats = stats.get(port_num, {})
+ samples[pname] = {
+ 'rx_throughput_fps': float(port_stats.get('rx_pps', 0.0)),
+ 'tx_throughput_fps': float(port_stats.get('tx_pps', 0.0)),
+ 'rx_throughput_bps': float(port_stats.get('rx_bps', 0.0)),
+ 'tx_throughput_bps': float(port_stats.get('tx_bps', 0.0)),
+ 'in_packets': int(port_stats.get('ipackets', 0)),
+ 'out_packets': int(port_stats.get('opackets', 0)),
+ }
+
+ pg_id_list = port_pg_id.get_pg_ids(port_num)
+ samples[pname]['latency'] = {}
+ for pg_id in pg_id_list:
+ latency_global = stats.get('latency', {})
+ pg_latency = latency_global.get(pg_id, {}).get('latency')
+ samples[pname]['latency'][pg_id] = pg_latency
+
+ return samples
+
class TrexTrafficGen(SampleVNFTrafficGen):
"""
diff --git a/yardstick/tests/unit/benchmark/contexts/standalone/test_model.py b/yardstick/tests/unit/benchmark/contexts/standalone/test_model.py
index 2cf1d92d7..246a5b2b9 100644
--- a/yardstick/tests/unit/benchmark/contexts/standalone/test_model.py
+++ b/yardstick/tests/unit/benchmark/contexts/standalone/test_model.py
@@ -549,5 +549,5 @@ class OvsDeployTestCase(unittest.TestCase):
'ovs_version': ovs_version,
'dpdk_version': dpdk_version,
'proxy': 'test_proxy'})
- mock_execute.assert_called_with(cmd)
- mock_env_get.assert_called_with('http_proxy', '')
+ mock_execute.assert_called_once_with(cmd)
+ mock_env_get.assert_has_calls([mock.call('http_proxy', '')])
diff --git a/yardstick/tests/unit/benchmark/scenarios/networking/test_vnf_generic.py b/yardstick/tests/unit/benchmark/scenarios/networking/test_vnf_generic.py
index 2885dc6fb..bb1a7aaca 100644
--- a/yardstick/tests/unit/benchmark/scenarios/networking/test_vnf_generic.py
+++ b/yardstick/tests/unit/benchmark/scenarios/networking/test_vnf_generic.py
@@ -628,7 +628,8 @@ class TestNetworkServiceTestCase(unittest.TestCase):
'extra_args': {'arg1': 'value1', 'arg2': 'value2'},
'flow': {'flow': {}},
'imix': {'imix': {'64B': 100}},
- 'uplink': {}}
+ 'uplink': {},
+ 'duration': 30}
)
mock_tprofile_get.assert_called_once_with(fake_vnfd)
diff --git a/yardstick/tests/unit/common/test_utils.py b/yardstick/tests/unit/common/test_utils.py
index 5fd91c87f..31b10e6da 100644
--- a/yardstick/tests/unit/common/test_utils.py
+++ b/yardstick/tests/unit/common/test_utils.py
@@ -1174,6 +1174,17 @@ class TimerTestCase(unittest.TestCase):
with utils.Timer(timeout=1):
time.sleep(2)
+ def test__enter_with_timeout_no_exception(self):
+ with utils.Timer(timeout=1, raise_exception=False):
+ time.sleep(2)
+
+ def test__iter(self):
+ iterations = []
+ for i in utils.Timer(timeout=2):
+ iterations.append(i)
+ time.sleep(1.1)
+ self.assertEqual(2, len(iterations))
+
class WaitUntilTrueTestCase(unittest.TestCase):
diff --git a/yardstick/tests/unit/network_services/traffic_profile/test_base.py b/yardstick/tests/unit/network_services/traffic_profile/test_base.py
index 641064cbe..55276af58 100644
--- a/yardstick/tests/unit/network_services/traffic_profile/test_base.py
+++ b/yardstick/tests/unit/network_services/traffic_profile/test_base.py
@@ -69,5 +69,20 @@ class TestTrafficProfile(unittest.TestCase):
class TestDummyProfile(unittest.TestCase):
def test_execute(self):
- dummy_profile = base.DummyProfile(base.TrafficProfile)
+ tp_config = {'traffic_profile': {'duration': 15}}
+ dummy_profile = base.DummyProfile(tp_config)
self.assertIsNone(dummy_profile.execute({}))
+
+
+class TrafficProfileConfigTestCase(unittest.TestCase):
+
+ def test__init(self):
+ tp_config = {'traffic_profile': {'packet_sizes': {'64B': 100}}}
+ tp_config_obj = base.TrafficProfileConfig(tp_config)
+ self.assertEqual({'64B': 100}, tp_config_obj.packet_sizes)
+ self.assertEqual(base.TrafficProfileConfig.DEFAULT_SCHEMA,
+ tp_config_obj.schema)
+ self.assertEqual(base.TrafficProfileConfig.DEFAULT_FRAME_RATE,
+ tp_config_obj.frame_rate)
+ self.assertEqual(base.TrafficProfileConfig.DEFAULT_DURATION,
+ tp_config_obj.duration)
diff --git a/yardstick/tests/unit/network_services/traffic_profile/test_fixed.py b/yardstick/tests/unit/network_services/traffic_profile/test_fixed.py
index 39905e6b1..2f6713760 100644
--- a/yardstick/tests/unit/network_services/traffic_profile/test_fixed.py
+++ b/yardstick/tests/unit/network_services/traffic_profile/test_fixed.py
@@ -102,8 +102,7 @@ class TestFixedProfile(unittest.TestCase):
'id': 'VpeApproxVnf', 'name': 'VPEVnfSsh'}]}}
def test___init__(self):
- fixed_profile = \
- FixedProfile(TrafficProfile)
+ fixed_profile = FixedProfile(self.TRAFFIC_PROFILE)
self.assertIsNotNone(fixed_profile)
def test_execute(self):
diff --git a/yardstick/tests/unit/network_services/traffic_profile/test_http.py b/yardstick/tests/unit/network_services/traffic_profile/test_http.py
index 0d1b916a7..d44fab2b5 100644
--- a/yardstick/tests/unit/network_services/traffic_profile/test_http.py
+++ b/yardstick/tests/unit/network_services/traffic_profile/test_http.py
@@ -11,30 +11,29 @@
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
-#
import unittest
-from yardstick.network_services.traffic_profile.base import TrafficProfile
-from yardstick.network_services.traffic_profile.http import \
- TrafficProfileGenericHTTP
+from yardstick.network_services.traffic_profile import http
class TestTrafficProfileGenericHTTP(unittest.TestCase):
+
+ TP_CONFIG = {'traffic_profile': {'duration': 10}}
+
def test___init__(self):
- traffic_profile_generic_htt_p = \
- TrafficProfileGenericHTTP(TrafficProfile)
- self.assertIsNotNone(traffic_profile_generic_htt_p)
+ tp_generic_http = http.TrafficProfileGenericHTTP(
+ self.TP_CONFIG)
+ self.assertIsNotNone(tp_generic_http)
def test_execute(self):
- traffic_profile_generic_htt_p = \
- TrafficProfileGenericHTTP(TrafficProfile)
+ tp_generic_http = http.TrafficProfileGenericHTTP(
+ self.TP_CONFIG)
traffic_generator = {}
- self.assertIsNone(
- traffic_profile_generic_htt_p.execute(traffic_generator))
+ self.assertIsNone(tp_generic_http.execute(traffic_generator))
def test__send_http_request(self):
- traffic_profile_generic_htt_p = \
- TrafficProfileGenericHTTP(TrafficProfile)
- self.assertIsNone(traffic_profile_generic_htt_p._send_http_request(
- "10.1.1.1", "250", "/req"))
+ tp_generic_http = http.TrafficProfileGenericHTTP(
+ self.TP_CONFIG)
+ self.assertIsNone(tp_generic_http._send_http_request(
+ '10.1.1.1', '250', '/req'))
diff --git a/yardstick/tests/unit/network_services/traffic_profile/test_rfc2544.py b/yardstick/tests/unit/network_services/traffic_profile/test_rfc2544.py
index 2684e0ba1..0cf93f9ae 100644
--- a/yardstick/tests/unit/network_services/traffic_profile/test_rfc2544.py
+++ b/yardstick/tests/unit/network_services/traffic_profile/test_rfc2544.py
@@ -11,33 +11,26 @@
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
-#
-import unittest
import mock
-from yardstick.tests import STL_MOCKS
-
+from trex_stl_lib import api as Pkt
+from trex_stl_lib import trex_stl_client
+from trex_stl_lib import trex_stl_packet_builder_scapy
+from trex_stl_lib import trex_stl_streams
-STLClient = mock.MagicMock()
-stl_patch = mock.patch.dict("sys.modules", STL_MOCKS)
-stl_patch.start()
+from yardstick.network_services.traffic_profile import rfc2544
+from yardstick.tests.unit import base
-if stl_patch:
- from yardstick.network_services.traffic_profile.trex_traffic_profile \
- import TrexProfile
- from yardstick.network_services.traffic_profile.rfc2544 import \
- RFC2544Profile
-
-class TestRFC2544Profile(unittest.TestCase):
+class TestRFC2544Profile(base.BaseUnitTestCase):
TRAFFIC_PROFILE = {
"schema": "isb:traffic_profile:0.1",
"name": "fixed",
"description": "Fixed traffic profile to run UDP traffic",
"traffic_profile": {
"traffic_type": "FixedTraffic",
- "frame_rate": 100, # pps
+ "frame_rate": 100,
"flow_number": 10,
"frame_size": 64}}
@@ -45,233 +38,251 @@ class TestRFC2544Profile(unittest.TestCase):
'name': 'rfc2544',
'traffic_profile': {'traffic_type': 'RFC2544Profile',
'frame_rate': 100},
- 'downlink_0': {'ipv4':
- {'outer_l2': {'framesize':
- {'64B': '100', '1518B': '0',
- '128B': '0', '1400B': '0',
- '256B': '0', '373b': '0',
- '570B': '0'}},
- 'outer_l3v4': {'dstip4': '1.1.1.1-1.15.255.255',
- 'proto': 'udp',
- 'srcip4': '90.90.1.1-90.105.255.255',
- 'dscp': 0, 'ttl': 32, 'count': 1},
- 'outer_l4': {'srcport': '2001',
- 'dsrport': '1234', 'count': 1}}},
- 'uplink_0': {'ipv4':
- {'outer_l2': {'framesize':
- {'64B': '100', '1518B': '0',
- '128B': '0', '1400B': '0',
- '256B': '0', '373b': '0',
- '570B': '0'}},
- 'outer_l3v4': {'dstip4': '9.9.1.1-90.105.255.255',
- 'proto': 'udp',
- 'srcip4': '1.1.1.1-1.15.255.255',
- 'dscp': 0, 'ttl': 32, 'count': 1},
- 'outer_l4': {'dstport': '2001',
- 'srcport': '1234', 'count': 1}}},
+ 'downlink_0':
+ {'ipv4':
+ {'outer_l2':
+ {'framesize':
+ {'64B': '100', '1518B': '0',
+ '128B': '0', '1400B': '0',
+ '256B': '0', '373b': '0',
+ '570B': '0'}},
+ 'outer_l3v4':
+ {'dstip4': '1.1.1.1-1.15.255.255',
+ 'proto': 'udp',
+ 'srcip4': '90.90.1.1-90.105.255.255',
+ 'dscp': 0, 'ttl': 32, 'count': 1},
+ 'outer_l4':
+ {'srcport': '2001',
+ 'dsrport': '1234', 'count': 1}}},
+ 'uplink_0':
+ {'ipv4':
+ {'outer_l2':
+ {'framesize':
+ {'64B': '100', '1518B': '0',
+ '128B': '0', '1400B': '0',
+ '256B': '0', '373b': '0',
+ '570B': '0'}},
+ 'outer_l3v4':
+ {'dstip4': '9.9.1.1-90.105.255.255',
+ 'proto': 'udp',
+ 'srcip4': '1.1.1.1-1.15.255.255',
+ 'dscp': 0, 'ttl': 32, 'count': 1},
+ 'outer_l4':
+ {'dstport': '2001',
+ 'srcport': '1234', 'count': 1}}},
'schema': 'isb:traffic_profile:0.1'}
def test___init__(self):
- r_f_c2544_profile = RFC2544Profile(self.TRAFFIC_PROFILE)
- self.assertIsNotNone(r_f_c2544_profile.rate)
+ rfc2544_profile = rfc2544.RFC2544Profile(self.TRAFFIC_PROFILE)
+ self.assertEqual(rfc2544_profile.max_rate, rfc2544_profile.rate)
+ self.assertEqual(0, rfc2544_profile.min_rate)
- def test_execute(self):
- traffic_generator = mock.Mock(autospec=TrexProfile)
- traffic_generator.networks = {
- "uplink_0": ["xe0"],
- "downlink_0": ["xe1"],
- }
- traffic_generator.client.return_value = True
- r_f_c2544_profile = RFC2544Profile(self.TRAFFIC_PROFILE)
- r_f_c2544_profile.params = self.PROFILE
- r_f_c2544_profile.first_run = True
- self.assertIsNone(r_f_c2544_profile.execute_traffic(traffic_generator))
+ def test_stop_traffic(self):
+ rfc2544_profile = rfc2544.RFC2544Profile(self.TRAFFIC_PROFILE)
+ mock_generator = mock.Mock()
+ rfc2544_profile.stop_traffic(traffic_generator=mock_generator)
+ mock_generator.client.stop.assert_called_once()
+ mock_generator.client.reset.assert_called_once()
+ mock_generator.client.remove_all_streams.assert_called_once()
- def test_get_drop_percentage(self):
- traffic_generator = mock.Mock(autospec=TrexProfile)
- traffic_generator.networks = {
- "uplink_0": ["xe0"],
- "downlink_0": ["xe1"],
- }
- traffic_generator.client.return_value = True
+ def test_execute_traffic(self):
+ rfc2544_profile = rfc2544.RFC2544Profile(self.TRAFFIC_PROFILE)
+ mock_generator = mock.Mock()
+ mock_generator.networks = {
+ 'downlink_0': ['xe0', 'xe1'],
+ 'uplink_0': ['xe2', 'xe3'],
+ 'downlink_1': []}
+ mock_generator.port_num.side_effect = [10, 20, 30, 40]
+ mock_generator.rfc2544_helper.correlated_traffic = False
+ rfc2544_profile.params = {
+ 'downlink_0': 'profile1',
+ 'uplink_0': 'profile2'}
- r_f_c2544_profile = RFC2544Profile(self.TRAFFIC_PROFILE)
- r_f_c2544_profile.params = self.PROFILE
- r_f_c2544_profile.register_generator(traffic_generator)
- self.assertIsNone(r_f_c2544_profile.execute_traffic(traffic_generator))
+ with mock.patch.object(rfc2544_profile, '_create_profile') as \
+ mock_create_profile:
+ rfc2544_profile.execute_traffic(traffic_generator=mock_generator)
+ mock_create_profile.assert_has_calls([
+ mock.call('profile1', rfc2544_profile.rate, mock.ANY),
+ mock.call('profile1', rfc2544_profile.rate, mock.ANY),
+ mock.call('profile2', rfc2544_profile.rate, mock.ANY),
+ mock.call('profile2', rfc2544_profile.rate, mock.ANY)])
+ mock_generator.client.add_streams.assert_has_calls([
+ mock.call(mock.ANY, ports=[10]),
+ mock.call(mock.ANY, ports=[20]),
+ mock.call(mock.ANY, ports=[30]),
+ mock.call(mock.ANY, ports=[40])])
+ mock_generator.client.start(ports=[10, 20, 30, 40],
+ duration=rfc2544_profile.config.duration,
+ force=True)
- samples = {}
- for ifname in range(1):
- name = "xe{}".format(ifname)
- samples[name] = {
- "rx_throughput_fps": 20,
- "tx_throughput_fps": 20,
- "rx_throughput_mbps": 10,
- "tx_throughput_mbps": 10,
- "in_packets": 1000,
- "out_packets": 1000,
- }
+ @mock.patch.object(trex_stl_streams, 'STLProfile')
+ def test__create_profile(self, mock_stl_profile):
+ rfc2544_profile = rfc2544.RFC2544Profile(self.TRAFFIC_PROFILE)
+ port_pg_id = mock.ANY
+ profile_data = {'packetid_1': {'outer_l2': {'framesize': 'imix_info'}}}
+ rate = 100
+ with mock.patch.object(rfc2544_profile, '_create_imix_data') as \
+ mock_create_imix, \
+ mock.patch.object(rfc2544_profile, '_create_vm') as \
+ mock_create_vm, \
+ mock.patch.object(rfc2544_profile, '_create_streams') as \
+ mock_create_streams:
+ mock_create_imix.return_value = 'imix_data'
+ mock_create_streams.return_value = ['stream1']
+ rfc2544_profile._create_profile(profile_data, rate, port_pg_id)
- expected = {
- 'DropPercentage': 0.0,
- 'RxThroughput': 100 / 3.0,
- 'TxThroughput': 100 / 3.0,
- 'CurrentDropPercentage': 0.0,
- 'Throughput': 66.66666666666667,
- 'xe0': {
- 'tx_throughput_fps': 20,
- 'in_packets': 1000,
- 'out_packets': 1000,
- 'rx_throughput_mbps': 10,
- 'tx_throughput_mbps': 10,
- 'rx_throughput_fps': 20,
- },
- }
- traffic_generator.generate_samples.return_value = samples
- traffic_generator.RUN_DURATION = 30
- traffic_generator.rfc2544_helper.tolerance_low = 0.0001
- traffic_generator.rfc2544_helper.tolerance_high = 0.0001
- result = r_f_c2544_profile.get_drop_percentage(traffic_generator)
- self.assertDictEqual(result, expected)
+ mock_create_imix.assert_called_once_with('imix_info')
+ mock_create_vm.assert_called_once_with(
+ {'outer_l2': {'framesize': 'imix_info'}})
+ mock_create_streams.assert_called_once_with('imix_data', 100,
+ port_pg_id)
+ mock_stl_profile.assert_called_once_with(['stream1'])
- def test_get_drop_percentage_update(self):
- traffic_generator = mock.Mock(autospec=RFC2544Profile)
- traffic_generator.networks = {
- "uplink_0": ["xe0"],
- "downlink_0": ["xe1"],
- }
- traffic_generator.client = mock.Mock(return_value=True)
+ def test__create_imix_data(self):
+ rfc2544_profile = rfc2544.RFC2544Profile(self.TRAFFIC_PROFILE)
+ data = {'64B': 50, '128B': 50}
+ self.assertEqual({'64': 50.0, '128': 50.0},
+ rfc2544_profile._create_imix_data(data))
+ data = {'64B': 1, '128b': 3}
+ self.assertEqual({'64': 25.0, '128': 75.0},
+ rfc2544_profile._create_imix_data(data))
+ data = {}
+ self.assertEqual({}, rfc2544_profile._create_imix_data(data))
- r_f_c2544_profile = RFC2544Profile(self.TRAFFIC_PROFILE)
- r_f_c2544_profile.params = self.PROFILE
- r_f_c2544_profile.register_generator(traffic_generator)
- self.assertIsNone(r_f_c2544_profile.execute_traffic())
+ def test__create_vm(self):
+ packet = {'outer_l2': 'l2_definition'}
+ rfc2544_profile = rfc2544.RFC2544Profile(self.TRAFFIC_PROFILE)
+ with mock.patch.object(rfc2544_profile, '_set_outer_l2_fields') as \
+ mock_l2_fileds:
+ rfc2544_profile._create_vm(packet)
+ mock_l2_fileds.assert_called_once_with('l2_definition')
- samples = {}
- for ifname in range(1):
- name = "xe{}".format(ifname)
- samples[name] = {
- "rx_throughput_fps": 20,
- "tx_throughput_fps": 20,
- "rx_throughput_mbps": 10,
- "tx_throughput_mbps": 10,
- "in_packets": 1000,
- "out_packets": 1002,
- }
- expected = {
- 'DropPercentage': 0.1996,
- 'RxThroughput': 33.333333333333336,
- 'TxThroughput': 33.4,
- 'CurrentDropPercentage': 0.1996,
- 'Throughput': 66.66666666666667,
- 'xe0': {
- 'tx_throughput_fps': 20,
- 'in_packets': 1000,
- 'out_packets': 1002,
- 'rx_throughput_mbps': 10,
- 'tx_throughput_mbps': 10,
- 'rx_throughput_fps': 20,
- },
- }
- traffic_generator.generate_samples = mock.MagicMock(
- return_value=samples)
- traffic_generator.RUN_DURATION = 30
- traffic_generator.rfc2544_helper.tolerance_low = 0.0001
- traffic_generator.rfc2544_helper.tolerance_high = 0.0001
- result = r_f_c2544_profile.get_drop_percentage(traffic_generator)
- self.assertDictEqual(expected, result)
+ @mock.patch.object(trex_stl_packet_builder_scapy, 'STLPktBuilder',
+ return_value='packet')
+ def test__create_single_packet(self, mock_pktbuilder):
+ size = 128
+ rfc2544_profile = rfc2544.RFC2544Profile(self.TRAFFIC_PROFILE)
+ rfc2544_profile.ether_packet = Pkt.Eth()
+ rfc2544_profile.ip_packet = Pkt.IP()
+ rfc2544_profile.udp_packet = Pkt.UDP()
+ rfc2544_profile.trex_vm = 'trex_vm'
+ base_pkt = (rfc2544_profile.ether_packet / rfc2544_profile.ip_packet /
+ rfc2544_profile.udp_packet)
+ pad = (size - len(base_pkt)) * 'x'
+ output = rfc2544_profile._create_single_packet(size=size)
+ mock_pktbuilder.assert_called_once_with(pkt=base_pkt / pad,
+ vm='trex_vm')
+ self.assertEqual(output, 'packet')
- def test_get_drop_percentage_div_zero(self):
- traffic_generator = mock.Mock(autospec=TrexProfile)
- traffic_generator.networks = {
- "uplink_0": ["xe0"],
- "downlink_0": ["xe1"],
- }
- traffic_generator.client = \
- mock.Mock(return_value=True)
- r_f_c2544_profile = RFC2544Profile(self.TRAFFIC_PROFILE)
- r_f_c2544_profile.params = self.PROFILE
- self.assertIsNone(
- r_f_c2544_profile.execute_traffic(traffic_generator))
- samples = {}
- for ifname in range(1):
- name = "xe{}".format(ifname)
- samples[name] = {"rx_throughput_fps": 20,
- "tx_throughput_fps": 20,
- "rx_throughput_mbps": 10,
- "tx_throughput_mbps": 10,
- "in_packets": 1000,
- "out_packets": 0}
- r_f_c2544_profile.throughput_max = 0
- expected = {
- 'DropPercentage': 100.0, 'RxThroughput': 100 / 3.0,
- 'TxThroughput': 0.0, 'CurrentDropPercentage': 100.0,
- 'Throughput': 66.66666666666667,
- 'xe0': {
- 'tx_throughput_fps': 20, 'in_packets': 1000,
- 'out_packets': 0, 'rx_throughput_mbps': 10,
- 'tx_throughput_mbps': 10, 'rx_throughput_fps': 20
- }
- }
- traffic_generator.generate_samples = mock.Mock(return_value=samples)
- traffic_generator.RUN_DURATION = 30
- traffic_generator.rfc2544_helper.tolerance_low = 0.0001
- traffic_generator.rfc2544_helper.tolerance_high = 0.0001
- self.assertDictEqual(expected,
- r_f_c2544_profile.get_drop_percentage(traffic_generator))
+ @mock.patch.object(trex_stl_packet_builder_scapy, 'STLPktBuilder',
+ return_value='packet')
+ def test__create_single_packet_qinq(self, mock_pktbuilder):
+ size = 128
+ rfc2544_profile = rfc2544.RFC2544Profile(self.TRAFFIC_PROFILE)
+ rfc2544_profile.ether_packet = Pkt.Eth()
+ rfc2544_profile.ip_packet = Pkt.IP()
+ rfc2544_profile.udp_packet = Pkt.UDP()
+ rfc2544_profile.trex_vm = 'trex_vm'
+ rfc2544_profile.qinq = True
+ rfc2544_profile.qinq_packet = Pkt.Dot1Q(vlan=1) / Pkt.Dot1Q(vlan=2)
+ base_pkt = (rfc2544_profile.ether_packet /
+ rfc2544_profile.qinq_packet / rfc2544_profile.ip_packet /
+ rfc2544_profile.udp_packet)
+ pad = (size - len(base_pkt)) * 'x'
+ output = rfc2544_profile._create_single_packet(size=size)
+ mock_pktbuilder.assert_called_once_with(pkt=base_pkt / pad,
+ vm='trex_vm')
+ self.assertEqual(output, 'packet')
+
+ @mock.patch.object(trex_stl_streams, 'STLFlowLatencyStats')
+ @mock.patch.object(trex_stl_streams, 'STLTXCont')
+ @mock.patch.object(trex_stl_client, 'STLStream')
+ def test__create_streams(self, mock_stream, mock_txcont, mock_latency):
+ imix_data = {'64': 25, '512': 75}
+ rate = 35
+ port_pg_id = rfc2544.PortPgIDMap()
+ port_pg_id.add_port(10)
+ mock_stream.side_effect = ['stream1', 'stream2']
+ mock_txcont.side_effect = ['txcont1', 'txcont2']
+ mock_latency.side_effect = ['latency1', 'latency2']
+ rfc2544_profile = rfc2544.RFC2544Profile(self.TRAFFIC_PROFILE)
+ with mock.patch.object(rfc2544_profile, '_create_single_packet'):
+ output = rfc2544_profile._create_streams(imix_data, rate,
+ port_pg_id)
+ self.assertEqual(['stream1', 'stream2'], output)
+ mock_latency.assert_has_calls([
+ mock.call(pg_id=1), mock.call(pg_id=2)])
+ mock_txcont.assert_has_calls([
+ mock.call(percentage=float(25 * 35) / 100),
+ mock.call(percentage=float(75 * 35) / 100)], any_order=True)
+
+ def test_get_drop_percentage(self):
+ rfc2544_profile = rfc2544.RFC2544Profile(self.TRAFFIC_PROFILE)
+ samples = [
+ {'xe1': {'tx_throughput_fps': 100,
+ 'rx_throughput_fps': 101,
+ 'out_packets': 2000,
+ 'in_packets': 2010},
+ 'xe2': {'tx_throughput_fps': 200,
+ 'rx_throughput_fps': 201,
+ 'out_packets': 4000,
+ 'in_packets': 4010}},
+ {'xe1': {'tx_throughput_fps': 106,
+ 'rx_throughput_fps': 108,
+ 'out_packets': 2031,
+ 'in_packets': 2040,
+ 'latency': 'Latency1'},
+ 'xe2': {'tx_throughput_fps': 203,
+ 'rx_throughput_fps': 215,
+ 'out_packets': 4025,
+ 'in_packets': 4040,
+ 'latency': 'Latency2'}}
+ ]
+ output = rfc2544_profile.get_drop_percentage(samples, 0, 0, False)
+ expected = {'DropPercentage': 0.3963,
+ 'Latency': {'xe1': 'Latency1', 'xe2': 'Latency2'},
+ 'RxThroughput': 312.5,
+ 'TxThroughput': 304.5,
+ 'CurrentDropPercentage': 0.3963,
+ 'Rate': 100,
+ 'Throughput': 312.5}
+ self.assertEqual(expected, output)
- def test_get_multiplier(self):
- r_f_c2544_profile = RFC2544Profile(self.TRAFFIC_PROFILE)
- r_f_c2544_profile.max_rate = 100
- r_f_c2544_profile.min_rate = 100
- self.assertEqual("1.0", r_f_c2544_profile.get_multiplier())
- def test_calculate_pps(self):
- r_f_c2544_profile = RFC2544Profile(self.TRAFFIC_PROFILE)
- r_f_c2544_profile.rate = 100
- r_f_c2544_profile.pps = 100
- samples = {'Throughput': 4549093.33}
- self.assertEqual((2274546.67, 1.0),
- r_f_c2544_profile.calculate_pps(samples))
+class PortPgIDMapTestCase(base.BaseUnitTestCase):
- def test_create_single_stream(self):
- r_f_c2544_profile = RFC2544Profile(self.TRAFFIC_PROFILE)
- r_f_c2544_profile._create_single_packet = mock.MagicMock()
- r_f_c2544_profile.pg_id = 1
- self.assertIsNotNone(
- r_f_c2544_profile.create_single_stream(64, 2274546.67))
+ def test_add_port(self):
+ port_pg_id_map = rfc2544.PortPgIDMap()
+ port_pg_id_map.add_port(10)
+ self.assertEqual(10, port_pg_id_map._last_port)
+ self.assertEqual([], port_pg_id_map._port_pg_id_map[10])
- def test_create_single_stream_no_pg_id(self):
- r_f_c2544_profile = RFC2544Profile(self.TRAFFIC_PROFILE)
- r_f_c2544_profile._create_single_packet = mock.MagicMock()
- r_f_c2544_profile.pg_id = 0
- self.assertIsNotNone(
- r_f_c2544_profile.create_single_stream(64, 2274546.67))
+ def test_get_pg_ids(self):
+ port_pg_id_map = rfc2544.PortPgIDMap()
+ port_pg_id_map.add_port(10)
+ port_pg_id_map.increase_pg_id()
+ port_pg_id_map.increase_pg_id()
+ port_pg_id_map.add_port(20)
+ port_pg_id_map.increase_pg_id()
+ self.assertEqual([1, 2], port_pg_id_map.get_pg_ids(10))
+ self.assertEqual([3], port_pg_id_map.get_pg_ids(20))
- def test_execute_latency(self):
- traffic_generator = mock.Mock(autospec=TrexProfile)
- traffic_generator.networks = {
- "private_0": ["xe0"],
- "public_0": ["xe1"],
- }
- traffic_generator.client = \
- mock.Mock(return_value=True)
- r_f_c2544_profile = RFC2544Profile(self.TRAFFIC_PROFILE)
- r_f_c2544_profile.params = self.PROFILE
- r_f_c2544_profile.first_run = True
- samples = {}
- for ifname in range(1):
- name = "xe{}".format(ifname)
- samples[name] = {"rx_throughput_fps": 20,
- "tx_throughput_fps": 20,
- "rx_throughput_mbps": 10,
- "tx_throughput_mbps": 10,
- "in_packets": 1000,
- "out_packets": 0}
+ def test_increase_pg_id_no_port(self):
+ port_pg_id_map = rfc2544.PortPgIDMap()
+ self.assertIsNone(port_pg_id_map.increase_pg_id())
- samples['Throughput'] = 4549093.33
- r_f_c2544_profile.calculate_pps = mock.Mock(return_value=[2274546.67,
- 1.0])
+ def test_increase_pg_id_last_port(self):
+ port_pg_id_map = rfc2544.PortPgIDMap()
+ port_pg_id_map.add_port(10)
+ self.assertEqual(1, port_pg_id_map.increase_pg_id())
+ self.assertEqual([1], port_pg_id_map.get_pg_ids(10))
+ self.assertEqual(10, port_pg_id_map._last_port)
- self.assertIsNone(r_f_c2544_profile.execute_latency(traffic_generator,
- samples))
+ def test_increase_pg_id(self):
+ port_pg_id_map = rfc2544.PortPgIDMap()
+ port_pg_id_map.add_port(10)
+ port_pg_id_map.increase_pg_id()
+ self.assertEqual(2, port_pg_id_map.increase_pg_id(port=20))
+ self.assertEqual([1], port_pg_id_map.get_pg_ids(10))
+ self.assertEqual([2], port_pg_id_map.get_pg_ids(20))
+ self.assertEqual(20, port_pg_id_map._last_port)
diff --git a/yardstick/tests/unit/network_services/traffic_profile/test_trex_traffic_profile.py b/yardstick/tests/unit/network_services/traffic_profile/test_trex_traffic_profile.py
index 7111c8075..628e85459 100644
--- a/yardstick/tests/unit/network_services/traffic_profile/test_trex_traffic_profile.py
+++ b/yardstick/tests/unit/network_services/traffic_profile/test_trex_traffic_profile.py
@@ -14,29 +14,12 @@
import ipaddress
-import mock
import six
import unittest
from yardstick.common import exceptions as y_exc
-from yardstick.tests import STL_MOCKS
-
-STLClient = mock.MagicMock()
-stl_patch = mock.patch.dict("sys.modules", STL_MOCKS)
-stl_patch.start()
-
-if stl_patch:
- from yardstick.network_services.traffic_profile.base import TrafficProfile
- from yardstick.network_services.traffic_profile.trex_traffic_profile import TrexProfile
- from yardstick.network_services.traffic_profile.trex_traffic_profile import SRC
- from yardstick.network_services.traffic_profile.trex_traffic_profile import DST
- from yardstick.network_services.traffic_profile.trex_traffic_profile import ETHERNET
- from yardstick.network_services.traffic_profile.trex_traffic_profile import IP
- from yardstick.network_services.traffic_profile.trex_traffic_profile import IPv6
- from yardstick.network_services.traffic_profile.trex_traffic_profile import UDP
- from yardstick.network_services.traffic_profile.trex_traffic_profile import SRC_PORT
- from yardstick.network_services.traffic_profile.trex_traffic_profile import DST_PORT
- from yardstick.network_services.traffic_profile.trex_traffic_profile import TYPE_OF_SERVICE
+from yardstick.network_services.traffic_profile import base as tp_base
+from yardstick.network_services.traffic_profile import trex_traffic_profile
class TestTrexProfile(unittest.TestCase):
@@ -59,7 +42,7 @@ class TestTrexProfile(unittest.TestCase):
'name': 'rfc2544',
'traffic_profile': {'traffic_type': 'RFC2544Profile',
'frame_rate': 100},
- TrafficProfile.DOWNLINK: {
+ tp_base.TrafficProfile.DOWNLINK: {
'ipv4': {'outer_l2': {'framesize': {'64B': '100',
'1518B': '0',
'128B': '0',
@@ -77,7 +60,7 @@ class TestTrexProfile(unittest.TestCase):
'outer_l4': {'srcport': '2001',
'dsrport': '1234',
'count': 1}}},
- TrafficProfile.UPLINK: {
+ tp_base.TrafficProfile.UPLINK: {
'ipv4':
{'outer_l2': {'framesize':
{'64B': '100', '1518B': '0',
@@ -99,7 +82,7 @@ class TestTrexProfile(unittest.TestCase):
'name': 'rfc2544',
'traffic_profile': {'traffic_type': 'RFC2544Profile',
'frame_rate': 100},
- TrafficProfile.DOWNLINK: {
+ tp_base.TrafficProfile.DOWNLINK: {
'ipv6': {'outer_l2': {'framesize':
{'64B': '100', '1518B': '0',
'128B': '0', '1400B': '0',
@@ -118,7 +101,7 @@ class TestTrexProfile(unittest.TestCase):
'outer_l4': {'srcport': '2001',
'dsrport': '1234',
'count': 1}}},
- TrafficProfile.UPLINK: {
+ tp_base.TrafficProfile.UPLINK: {
'ipv6': {'outer_l2': {'framesize':
{'64B': '100', '1518B': '0',
'128B': '0', '1400B': '0',
@@ -140,17 +123,15 @@ class TestTrexProfile(unittest.TestCase):
'schema': 'isb:traffic_profile:0.1'}
def test___init__(self):
- TrafficProfile.params = self.PROFILE
- trex_profile = \
- TrexProfile(TrafficProfile)
+ trex_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
self.assertEqual(trex_profile.pps, 100)
def test_qinq(self):
+ trex_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
qinq = {"S-VLAN": {"id": 128, "priority": 0, "cfi": 0},
"C-VLAN": {"id": 512, "priority": 0, "cfi": 0}}
- trex_profile = \
- TrexProfile(TrafficProfile)
+ trex_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
self.assertIsNone(trex_profile.set_qinq(qinq))
qinq = {"S-VLAN": {"id": "128-130", "priority": 0, "cfi": 0},
@@ -158,64 +139,39 @@ class TestTrexProfile(unittest.TestCase):
self.assertIsNone(trex_profile.set_qinq(qinq))
def test__set_outer_l2_fields(self):
- trex_profile = \
- TrexProfile(TrafficProfile)
+ trex_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
qinq = {"S-VLAN": {"id": 128, "priority": 0, "cfi": 0},
"C-VLAN": {"id": 512, "priority": 0, "cfi": 0}}
- outer_l2 = self.PROFILE[TrafficProfile.UPLINK]['ipv4']['outer_l2']
+ outer_l2 = self.PROFILE[
+ tp_base.TrafficProfile.UPLINK]['ipv4']['outer_l2']
outer_l2['QinQ'] = qinq
self.assertIsNone(trex_profile._set_outer_l2_fields(outer_l2))
def test__set_outer_l3v4_fields(self):
- trex_profile = \
- TrexProfile(TrafficProfile)
- outer_l3v4 = self.PROFILE[TrafficProfile.UPLINK]['ipv4']['outer_l3v4']
+ trex_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
+ outer_l3v4 = self.PROFILE[
+ tp_base.TrafficProfile.UPLINK]['ipv4']['outer_l3v4']
outer_l3v4['proto'] = 'tcp'
self.assertIsNone(trex_profile._set_outer_l3v4_fields(outer_l3v4))
def test__set_outer_l3v6_fields(self):
- trex_profile = \
- TrexProfile(TrafficProfile)
- outer_l3v6 = self.PROFILE_v6[TrafficProfile.UPLINK]['ipv6']['outer_l3v4']
+ trex_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
+ outer_l3v6 = self.PROFILE_v6[
+ tp_base.TrafficProfile.UPLINK]['ipv6']['outer_l3v4']
outer_l3v6['proto'] = 'tcp'
outer_l3v6['tc'] = 1
outer_l3v6['hlim'] = 10
self.assertIsNone(trex_profile._set_outer_l3v6_fields(outer_l3v6))
def test__set_outer_l4_fields(self):
- trex_profile = \
- TrexProfile(TrafficProfile)
- outer_l4 = self.PROFILE[TrafficProfile.UPLINK]['ipv4']['outer_l4']
+ trex_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
+ outer_l4 = self.PROFILE[
+ tp_base.TrafficProfile.UPLINK]['ipv4']['outer_l4']
self.assertIsNone(trex_profile._set_outer_l4_fields(outer_l4))
- def test_get_streams(self):
- trex_profile = \
- TrexProfile(TrafficProfile)
- trex_profile.params = self.PROFILE
- profile_data = self.PROFILE[TrafficProfile.UPLINK]
- self.assertIsNotNone(trex_profile.get_streams(profile_data))
- trex_profile.pg_id = 1
- self.assertIsNotNone(trex_profile.get_streams(profile_data))
- trex_profile.params = self.PROFILE_v6
- trex_profile.profile_data = self.PROFILE_v6[TrafficProfile.UPLINK]
- self.assertIsNotNone(trex_profile.get_streams(profile_data))
- trex_profile.pg_id = 1
- self.assertIsNotNone(trex_profile.get_streams(profile_data))
-
- def test_generate_packets(self):
- trex_profile = \
- TrexProfile(TrafficProfile)
- trex_profile.fsize = 10
- trex_profile.base_pkt = [10]
- self.assertIsNone(trex_profile.generate_packets())
-
- def test_generate_imix_data_error(self):
- trex_profile = \
- TrexProfile(TrafficProfile)
- self.assertEqual({}, trex_profile.generate_imix_data(False))
-
def test__count_ip_ipv4(self):
- start, end, count = TrexProfile._count_ip('1.1.1.1', '1.2.3.4')
+ start, end, count = trex_traffic_profile.TrexProfile._count_ip(
+ '1.1.1.1', '1.2.3.4')
self.assertEqual('1.1.1.1', str(start))
self.assertEqual('1.2.3.4', str(end))
diff = (int(ipaddress.IPv4Address(six.u('1.2.3.4'))) -
@@ -225,7 +181,8 @@ class TestTrexProfile(unittest.TestCase):
def test__count_ip_ipv6(self):
start_ip = '0064:ff9b:0:0:0:0:9810:6414'
end_ip = '0064:ff9b:0:0:0:0:9810:6420'
- start, end, count = TrexProfile._count_ip(start_ip, end_ip)
+ start, end, count = trex_traffic_profile.TrexProfile._count_ip(
+ start_ip, end_ip)
self.assertEqual(0x98106414, start)
self.assertEqual(0x98106420, end)
self.assertEqual(0x98106420 - 0x98106414, count)
@@ -234,10 +191,10 @@ class TestTrexProfile(unittest.TestCase):
start_ip = '0064:ff9b:0:0:0:0:9810:6420'
end_ip = '0064:ff9b:0:0:0:0:9810:6414'
with self.assertRaises(y_exc.IPv6RangeError):
- TrexProfile._count_ip(start_ip, end_ip)
+ trex_traffic_profile.TrexProfile._count_ip(start_ip, end_ip)
def test__dscp_range_action_partial_actual_count_zero(self):
- traffic_profile = TrexProfile(TrafficProfile)
+ traffic_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
dscp_partial = traffic_profile._dscp_range_action_partial()
flow_vars_initial_length = len(traffic_profile.vm_flow_vars)
@@ -245,7 +202,7 @@ class TestTrexProfile(unittest.TestCase):
self.assertEqual(len(traffic_profile.vm_flow_vars), flow_vars_initial_length + 2)
def test__dscp_range_action_partial_count_greater_than_actual(self):
- traffic_profile = TrexProfile(TrafficProfile)
+ traffic_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
dscp_partial = traffic_profile._dscp_range_action_partial()
flow_vars_initial_length = len(traffic_profile.vm_flow_vars)
@@ -253,7 +210,7 @@ class TestTrexProfile(unittest.TestCase):
self.assertEqual(len(traffic_profile.vm_flow_vars), flow_vars_initial_length + 2)
def test__udp_range_action_partial_actual_count_zero(self):
- traffic_profile = TrexProfile(TrafficProfile)
+ traffic_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
traffic_profile.udp['field1'] = 'value1'
udp_partial = traffic_profile._udp_range_action_partial('field1')
@@ -262,48 +219,59 @@ class TestTrexProfile(unittest.TestCase):
self.assertEqual(len(traffic_profile.vm_flow_vars), flow_vars_initial_length + 2)
def test__udp_range_action_partial_count_greater_than_actual(self):
- traffic_profile = TrexProfile(TrafficProfile)
+ traffic_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
traffic_profile.udp['field1'] = 'value1'
- udp_partial = traffic_profile._udp_range_action_partial('field1', 'not_used_count')
-
+ udp_partial = traffic_profile._udp_range_action_partial(
+ 'field1', 'not_used_count')
flow_vars_initial_length = len(traffic_profile.vm_flow_vars)
udp_partial('1', '10', '100')
self.assertEqual(len(traffic_profile.vm_flow_vars), flow_vars_initial_length + 2)
def test__general_single_action_partial(self):
- trex_profile = TrexProfile(TrafficProfile)
-
- trex_profile._general_single_action_partial(ETHERNET)(SRC)(
+ trex_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
+ trex_profile._general_single_action_partial(
+ trex_traffic_profile.ETHERNET)(trex_traffic_profile.SRC)(
self.EXAMPLE_ETHERNET_ADDR)
self.assertEqual(self.EXAMPLE_ETHERNET_ADDR,
trex_profile.ether_packet.src)
- trex_profile._general_single_action_partial(IP)(DST)(
- self.EXAMPLE_IP_ADDR)
+ trex_profile._general_single_action_partial(trex_traffic_profile.IP)(
+ trex_traffic_profile.DST)(self.EXAMPLE_IP_ADDR)
self.assertEqual(self.EXAMPLE_IP_ADDR, trex_profile.ip_packet.dst)
- trex_profile._general_single_action_partial(IPv6)(DST)(
- self.EXAMPLE_IPv6_ADDR)
+ trex_profile._general_single_action_partial(trex_traffic_profile.IPv6)(
+ trex_traffic_profile.DST)(self.EXAMPLE_IPv6_ADDR)
self.assertEqual(self.EXAMPLE_IPv6_ADDR, trex_profile.ip6_packet.dst)
- trex_profile._general_single_action_partial(UDP)(SRC_PORT)(5060)
+ trex_profile._general_single_action_partial(trex_traffic_profile.UDP)(
+ trex_traffic_profile.SRC_PORT)(5060)
self.assertEqual(5060, trex_profile.udp_packet.sport)
- trex_profile._general_single_action_partial(IP)(TYPE_OF_SERVICE)(0)
+ trex_profile._general_single_action_partial(trex_traffic_profile.IP)(
+ trex_traffic_profile.TYPE_OF_SERVICE)(0)
self.assertEqual(0, trex_profile.ip_packet.tos)
def test__set_proto_addr(self):
- trex_profile = TrexProfile(TrafficProfile)
+ trex_profile = trex_traffic_profile.TrexProfile(self.PROFILE)
ether_range = "00:00:00:00:00:01-00:00:00:00:00:02"
ip_range = "1.1.1.2-1.1.1.10"
ipv6_range = '0064:ff9b:0:0:0:0:9810:6414-0064:ff9b:0:0:0:0:9810:6420'
- trex_profile._set_proto_addr(ETHERNET, SRC, ether_range)
- trex_profile._set_proto_addr(ETHERNET, DST, ether_range)
- trex_profile._set_proto_addr(IP, SRC, ip_range)
- trex_profile._set_proto_addr(IP, DST, ip_range)
- trex_profile._set_proto_addr(IPv6, SRC, ipv6_range)
- trex_profile._set_proto_addr(IPv6, DST, ipv6_range)
- trex_profile._set_proto_addr(UDP, SRC_PORT, "5060-5090")
- trex_profile._set_proto_addr(UDP, DST_PORT, "5060")
+ trex_profile._set_proto_addr(trex_traffic_profile.ETHERNET,
+ trex_traffic_profile.SRC, ether_range)
+ trex_profile._set_proto_addr(trex_traffic_profile.ETHERNET,
+ trex_traffic_profile.DST, ether_range)
+ trex_profile._set_proto_addr(trex_traffic_profile.IP,
+ trex_traffic_profile.SRC, ip_range)
+ trex_profile._set_proto_addr(trex_traffic_profile.IP,
+ trex_traffic_profile.DST, ip_range)
+ trex_profile._set_proto_addr(trex_traffic_profile.IPv6,
+ trex_traffic_profile.SRC, ipv6_range)
+ trex_profile._set_proto_addr(trex_traffic_profile.IPv6,
+ trex_traffic_profile.DST, ipv6_range)
+ trex_profile._set_proto_addr(trex_traffic_profile.UDP,
+ trex_traffic_profile.SRC_PORT,
+ '5060-5090')
+ trex_profile._set_proto_addr(trex_traffic_profile.UDP,
+ trex_traffic_profile.DST_PORT, '5060')
diff --git a/yardstick/tests/unit/network_services/vnf_generic/vnf/test_sample_vnf.py b/yardstick/tests/unit/network_services/vnf_generic/vnf/test_sample_vnf.py
index 7ee2005ba..ce849d174 100644
--- a/yardstick/tests/unit/network_services/vnf_generic/vnf/test_sample_vnf.py
+++ b/yardstick/tests/unit/network_services/vnf_generic/vnf/test_sample_vnf.py
@@ -11,7 +11,6 @@
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
-#
from copy import deepcopy
@@ -19,37 +18,29 @@ import unittest
import mock
import six
-from yardstick.tests.unit.network_services.vnf_generic.vnf.test_base import mock_ssh
-from yardstick.tests import STL_MOCKS
from yardstick.benchmark.contexts.base import Context
from yardstick.common import exceptions as y_exceptions
from yardstick.common import utils
from yardstick.network_services.nfvi.resource import ResourceProfile
from yardstick.network_services.vnf_generic.vnf.base import VnfdHelper
-
-
-class MockError(BaseException):
+from yardstick.network_services.vnf_generic.vnf import sample_vnf
+from yardstick.network_services.vnf_generic.vnf.vnf_ssh_helper import VnfSshHelper
+from yardstick.network_services.vnf_generic.vnf.sample_vnf import SampleVNFDeployHelper
+from yardstick.network_services.vnf_generic.vnf.sample_vnf import ScenarioHelper
+from yardstick.network_services.vnf_generic.vnf.sample_vnf import ResourceHelper
+from yardstick.network_services.vnf_generic.vnf.sample_vnf import ClientResourceHelper
+from yardstick.network_services.vnf_generic.vnf.sample_vnf import Rfc2544ResourceHelper
+from yardstick.network_services.vnf_generic.vnf.sample_vnf import SetupEnvHelper
+from yardstick.network_services.vnf_generic.vnf.sample_vnf import SampleVNF
+from yardstick.network_services.vnf_generic.vnf.sample_vnf import SampleVNFTrafficGen
+from yardstick.network_services.vnf_generic.vnf.sample_vnf import DpdkVnfSetupEnvHelper
+from yardstick.tests.unit.network_services.vnf_generic.vnf import test_base
+
+
+class MockError(Exception):
pass
-STLClient = mock.MagicMock()
-stl_patch = mock.patch.dict("sys.modules", STL_MOCKS)
-stl_patch.start()
-
-if stl_patch:
- from yardstick.network_services.vnf_generic.vnf import sample_vnf
- from yardstick.network_services.vnf_generic.vnf.vnf_ssh_helper import VnfSshHelper
- from yardstick.network_services.vnf_generic.vnf.sample_vnf import SampleVNFDeployHelper
- from yardstick.network_services.vnf_generic.vnf.sample_vnf import ScenarioHelper
- from yardstick.network_services.vnf_generic.vnf.sample_vnf import ResourceHelper
- from yardstick.network_services.vnf_generic.vnf.sample_vnf import ClientResourceHelper
- from yardstick.network_services.vnf_generic.vnf.sample_vnf import Rfc2544ResourceHelper
- from yardstick.network_services.vnf_generic.vnf.sample_vnf import SetupEnvHelper
- from yardstick.network_services.vnf_generic.vnf.sample_vnf import SampleVNF
- from yardstick.network_services.vnf_generic.vnf.sample_vnf import SampleVNFTrafficGen
- from yardstick.network_services.vnf_generic.vnf.sample_vnf import DpdkVnfSetupEnvHelper
-
-
class TestVnfSshHelper(unittest.TestCase):
VNFD_0 = {
@@ -1003,187 +994,52 @@ class TestClientResourceHelper(unittest.TestCase):
}
@mock.patch('yardstick.network_services.vnf_generic.vnf.sample_vnf.LOG')
- @mock.patch('yardstick.network_services.vnf_generic.vnf.sample_vnf.STLError',
- new_callable=lambda: MockError)
- def test_get_stats_not_connected(self, mock_state_error, *args):
+ @mock.patch.object(sample_vnf, 'STLError', new_callable=lambda: MockError)
+ def test_get_stats_not_connected(self, mock_stl_error, *args):
vnfd_helper = VnfdHelper(self.VNFD_0)
ssh_helper = mock.Mock()
scenario_helper = mock.Mock()
- dpdk_setup_helper = DpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
+ dpdk_setup_helper = DpdkVnfSetupEnvHelper(
+ vnfd_helper, ssh_helper, scenario_helper)
client_resource_helper = ClientResourceHelper(dpdk_setup_helper)
- client_resource_helper.client = mock.MagicMock()
- client_resource_helper.client.get_stats.side_effect = mock_state_error
+ client_resource_helper.client = mock.Mock()
+ client_resource_helper.client.get_stats.side_effect = mock_stl_error
self.assertEqual(client_resource_helper.get_stats(), {})
client_resource_helper.client.get_stats.assert_called_once()
- def test_generate_samples(self):
- vnfd_helper = VnfdHelper(self.VNFD_0)
- ssh_helper = mock.Mock()
- scenario_helper = mock.Mock()
- dpdk_setup_helper = DpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
- client_resource_helper = ClientResourceHelper(dpdk_setup_helper)
- client_resource_helper.client = mock.MagicMock()
- client_resource_helper.client.get_stats.return_value = {
- 0: {
- 'rx_pps': 5.5,
- 'tx_pps': 4.9,
- 'rx_bps': 234.78,
- 'tx_bps': 243.11,
- 'ipackets': 34251,
- 'opackets': 52342,
- },
- 1: {
- 'tx_pps': 5.9,
- 'rx_bps': 434.78,
- 'opackets': 48791,
- },
- }
-
- expected = {
- 'xe0': {
- "rx_throughput_fps": 5.5,
- "tx_throughput_fps": 4.9,
- "rx_throughput_mbps": 234.78,
- "tx_throughput_mbps": 243.11,
- "in_packets": 34251,
- "out_packets": 52342,
- },
- 'xe1': {
- "rx_throughput_fps": 0.0,
- "tx_throughput_fps": 5.9,
- "rx_throughput_mbps": 434.78,
- "tx_throughput_mbps": 0.0,
- "in_packets": 0,
- "out_packets": 48791,
- },
- }
- ports = vnfd_helper.port_nums(vnfd_helper.port_pairs.all_ports)
- result = client_resource_helper.generate_samples(ports)
- self.assertDictEqual(result, expected)
-
- def test_generate_samples_with_key(self):
- vnfd_helper = VnfdHelper(self.VNFD_0)
- ssh_helper = mock.Mock()
- scenario_helper = mock.Mock()
- dpdk_setup_helper = DpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
- client_resource_helper = ClientResourceHelper(dpdk_setup_helper)
- client_resource_helper.client = mock.MagicMock()
- client_resource_helper.client.get_stats.return_value = {
- 'key_name': 'key_value',
- 0: {
- 'rx_pps': 5.5,
- 'tx_pps': 4.9,
- 'rx_bps': 234.78,
- 'tx_bps': 243.11,
- 'ipackets': 34251,
- 'opackets': 52342,
- },
- 1: {
- 'tx_pps': 5.9,
- 'rx_bps': 434.78,
- 'opackets': 48791,
- },
- }
-
- expected = {
- 'xe0': {
- 'key_name': 'key_value',
- "rx_throughput_fps": 5.5,
- "tx_throughput_fps": 4.9,
- "rx_throughput_mbps": 234.78,
- "tx_throughput_mbps": 243.11,
- "in_packets": 34251,
- "out_packets": 52342,
- },
- 'xe1': {
- 'key_name': 'key_value',
- "rx_throughput_fps": 0.0,
- "tx_throughput_fps": 5.9,
- "rx_throughput_mbps": 434.78,
- "tx_throughput_mbps": 0.0,
- "in_packets": 0,
- "out_packets": 48791,
- },
- }
- ports = vnfd_helper.port_nums(vnfd_helper.port_pairs.all_ports)
- result = client_resource_helper.generate_samples(ports, 'key_name')
- self.assertDictEqual(result, expected)
-
- def test_generate_samples_with_key_and_default(self):
- vnfd_helper = VnfdHelper(self.VNFD_0)
- ssh_helper = mock.Mock()
- scenario_helper = mock.Mock()
- dpdk_setup_helper = DpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
- client_resource_helper = ClientResourceHelper(dpdk_setup_helper)
- client_resource_helper.client = mock.MagicMock()
- client_resource_helper.client.get_stats.return_value = {
- 0: {
- 'rx_pps': 5.5,
- 'tx_pps': 4.9,
- 'rx_bps': 234.78,
- 'tx_bps': 243.11,
- 'ipackets': 34251,
- 'opackets': 52342,
- },
- 1: {
- 'tx_pps': 5.9,
- 'rx_bps': 434.78,
- 'opackets': 48791,
- },
- }
-
- expected = {
- 'xe0': {
- 'key_name': 'default',
- "rx_throughput_fps": 5.5,
- "tx_throughput_fps": 4.9,
- "rx_throughput_mbps": 234.78,
- "tx_throughput_mbps": 243.11,
- "in_packets": 34251,
- "out_packets": 52342,
- },
- 'xe1': {
- 'key_name': 'default',
- "rx_throughput_fps": 0.0,
- "tx_throughput_fps": 5.9,
- "rx_throughput_mbps": 434.78,
- "tx_throughput_mbps": 0.0,
- "in_packets": 0,
- "out_packets": 48791,
- },
- }
- ports = vnfd_helper.port_nums(vnfd_helper.port_pairs.all_ports)
- result = client_resource_helper.generate_samples(ports, 'key_name', 'default')
- self.assertDictEqual(result, expected)
-
def test_clear_stats(self):
vnfd_helper = VnfdHelper(self.VNFD_0)
ssh_helper = mock.Mock()
scenario_helper = mock.Mock()
- dpdk_setup_helper = DpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
+ dpdk_setup_helper = DpdkVnfSetupEnvHelper(
+ vnfd_helper, ssh_helper, scenario_helper)
client_resource_helper = ClientResourceHelper(dpdk_setup_helper)
client_resource_helper.client = mock.Mock()
self.assertIsNone(client_resource_helper.clear_stats())
- client_resource_helper.client.clear_stats.assert_called_once()
+ self.assertEqual(
+ client_resource_helper.client.clear_stats.call_count, 1)
def test_clear_stats_of_ports(self):
vnfd_helper = VnfdHelper(self.VNFD_0)
ssh_helper = mock.Mock()
scenario_helper = mock.Mock()
- dpdk_setup_helper = DpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
+ dpdk_setup_helper = DpdkVnfSetupEnvHelper(
+ vnfd_helper, ssh_helper, scenario_helper)
client_resource_helper = ClientResourceHelper(dpdk_setup_helper)
client_resource_helper.client = mock.Mock()
self.assertIsNone(client_resource_helper.clear_stats([3, 4]))
- client_resource_helper.client.clear_stats.assert_called_once()
+ self.assertEqual(
+ client_resource_helper.client.clear_stats.call_count, 1)
def test_start(self):
vnfd_helper = VnfdHelper(self.VNFD_0)
ssh_helper = mock.Mock()
scenario_helper = mock.Mock()
- dpdk_setup_helper = DpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
+ dpdk_setup_helper = DpdkVnfSetupEnvHelper(
+ vnfd_helper, ssh_helper, scenario_helper)
client_resource_helper = ClientResourceHelper(dpdk_setup_helper)
client_resource_helper.client = mock.Mock()
@@ -1194,7 +1050,8 @@ class TestClientResourceHelper(unittest.TestCase):
vnfd_helper = VnfdHelper(self.VNFD_0)
ssh_helper = mock.Mock()
scenario_helper = mock.Mock()
- dpdk_setup_helper = DpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
+ dpdk_setup_helper = DpdkVnfSetupEnvHelper(
+ vnfd_helper, ssh_helper, scenario_helper)
client_resource_helper = ClientResourceHelper(dpdk_setup_helper)
client_resource_helper.client = mock.Mock()
@@ -1221,17 +1078,15 @@ class TestClientResourceHelper(unittest.TestCase):
self.assertDictEqual(result, expected)
@mock.patch('yardstick.network_services.vnf_generic.vnf.sample_vnf.time')
- @mock.patch('yardstick.network_services.vnf_generic.vnf.sample_vnf.LOG')
- @mock.patch('yardstick.network_services.vnf_generic.vnf.sample_vnf.STLError',
- new_callable=lambda: MockError)
- def test__connect_with_failures(self, mock_error, *args):
+ @mock.patch.object(sample_vnf, 'STLError')
+ def test__connect_with_failures(self, mock_stl_error, *args):
vnfd_helper = VnfdHelper(self.VNFD_0)
ssh_helper = mock.Mock()
scenario_helper = mock.Mock()
dpdk_setup_helper = DpdkVnfSetupEnvHelper(vnfd_helper, ssh_helper, scenario_helper)
client_resource_helper = ClientResourceHelper(dpdk_setup_helper)
client = mock.MagicMock()
- client.connect.side_effect = mock_error
+ client.connect.side_effect = mock_stl_error(msg='msg')
self.assertIs(client_resource_helper._connect(client), client)
@@ -1680,7 +1535,7 @@ class TestSampleVnf(unittest.TestCase):
@mock.patch("yardstick.ssh.SSH")
def test_instantiate(self, ssh):
- mock_ssh(ssh)
+ test_base.mock_ssh(ssh)
nodes = {
'vnf1': 'name1',
@@ -1780,7 +1635,7 @@ class TestSampleVnf(unittest.TestCase):
@mock.patch("yardstick.network_services.vnf_generic.vnf.sample_vnf.time")
@mock.patch("yardstick.ssh.SSH")
def test_wait_for_instantiate_empty_queue(self, ssh, *args):
- mock_ssh(ssh, exec_result=(1, "", ""))
+ test_base.mock_ssh(ssh, exec_result=(1, "", ""))
queue_size_list = [
0,
diff --git a/yardstick/tests/unit/network_services/vnf_generic/vnf/test_tg_rfc2544_trex.py b/yardstick/tests/unit/network_services/vnf_generic/vnf/test_tg_rfc2544_trex.py
index 8b1b8a39c..9531b90c4 100644
--- a/yardstick/tests/unit/network_services/vnf_generic/vnf/test_tg_rfc2544_trex.py
+++ b/yardstick/tests/unit/network_services/vnf_generic/vnf/test_tg_rfc2544_trex.py
@@ -11,44 +11,37 @@
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
-#
-import unittest
import mock
+import unittest
-from yardstick.tests import STL_MOCKS
-SSH_HELPER = 'yardstick.network_services.vnf_generic.vnf.sample_vnf.VnfSshHelper'
-
-
-STLClient = mock.MagicMock()
-stl_patch = mock.patch.dict("sys.modules", STL_MOCKS)
-stl_patch.start()
-
-if stl_patch:
- from yardstick.network_services.vnf_generic.vnf.tg_rfc2544_trex import TrexTrafficGenRFC, \
- TrexRfcResourceHelper
- from yardstick.network_services.vnf_generic.vnf import tg_rfc2544_trex
- from yardstick.network_services.traffic_profile.base import TrafficProfile
- from yardstick.tests.unit.network_services.vnf_generic.vnf.test_base \
- import FileAbsPath, mock_ssh
-
-MODULE_PATH = FileAbsPath(__file__)
-get_file_abspath = MODULE_PATH.get_path
+from yardstick.network_services.traffic_profile import base as tp_base
+from yardstick.network_services.vnf_generic.vnf import sample_vnf
+from yardstick.network_services.vnf_generic.vnf import tg_rfc2544_trex
class TestTrexRfcResouceHelper(unittest.TestCase):
- @mock.patch('yardstick.network_services.helpers.samplevnf_helper.MultiPortConfig')
- @mock.patch("yardstick.network_services.vnf_generic.vnf.tg_rfc2544_trex.time")
- @mock.patch(SSH_HELPER)
- def test__run_traffic_once(self, ssh, *_):
- mock_ssh(ssh)
+ def test__run_traffic_once(self):
+ mock_setup_helper = mock.Mock()
+ mock_traffic_profile = mock.Mock()
+ mock_traffic_profile.config.duration = 3
+ mock_traffic_profile.execute_traffic.return_value = ('fake_ports',
+ 'port_pg_id_map')
+ mock_traffic_profile.get_drop_percentage.return_value = 'percentage'
+ rfc_rh = tg_rfc2544_trex.TrexRfcResourceHelper(mock_setup_helper)
+ rfc_rh.TRANSIENT_PERIOD = 0
+ rfc_rh.rfc2544_helper = mock.Mock()
- mock_traffic_profile = mock.MagicMock(autospec=TrafficProfile,
- **{'get_drop_percentage.return_value': {}})
- sut = TrexRfcResourceHelper(mock.MagicMock(), mock.MagicMock())
- sut.client = mock.MagicMock()
- sut._run_traffic_once(mock_traffic_profile)
+ with mock.patch.object(rfc_rh, '_get_samples') as mock_get_samples:
+ rfc_rh._run_traffic_once(mock_traffic_profile)
+
+ mock_traffic_profile.execute_traffic.assert_called_once_with(rfc_rh)
+ mock_traffic_profile.stop_traffic.assert_called_once_with(rfc_rh)
+ mock_traffic_profile.stop_traffic.assert_called_once()
+ mock_get_samples.assert_has_calls([
+ mock.call('fake_ports', port_pg_id='port_pg_id_map'),
+ mock.call('fake_ports', port_pg_id='port_pg_id_map')])
class TestTrexTrafficGenRFC(unittest.TestCase):
@@ -219,33 +212,24 @@ class TestTrexTrafficGenRFC(unittest.TestCase):
'schema': 'yardstick:task:0.1',
}
- @mock.patch(SSH_HELPER)
- def test___init__(self, ssh):
- mock_ssh(ssh)
- trex_traffic_gen = TrexTrafficGenRFC('vnf1', self.VNFD_0)
- self.assertIsNotNone(trex_traffic_gen.resource_helper._terminated.value)
+ def setUp(self):
+ self._mock_ssh_helper = mock.patch.object(sample_vnf, 'VnfSshHelper')
+ self.mock_ssh_helper = self._mock_ssh_helper.start()
+ self.addCleanup(self._stop_mocks)
- @mock.patch(SSH_HELPER)
- def test_collect_kpi(self, ssh):
- mock_ssh(ssh)
- trex_traffic_gen = TrexTrafficGenRFC('vnf1', self.VNFD_0)
- self.assertEqual(trex_traffic_gen.collect_kpi(), {})
+ def _stop_mocks(self):
+ self._mock_ssh_helper.stop()
- @mock.patch(SSH_HELPER)
- def test_listen_traffic(self, ssh):
- mock_ssh(ssh)
- trex_traffic_gen = TrexTrafficGenRFC('vnf1', self.VNFD_0)
- self.assertIsNone(trex_traffic_gen.listen_traffic({}))
-
- @mock.patch(SSH_HELPER)
- def test_instantiate(self, ssh):
- mock_ssh(ssh)
+ def test___init__(self):
+ trex_traffic_gen = tg_rfc2544_trex.TrexTrafficGenRFC('vnf1', self.VNFD_0)
+ self.assertIsNotNone(trex_traffic_gen.resource_helper._terminated.value)
- mock_traffic_profile = mock.Mock(autospec=TrafficProfile)
+ def test_instantiate(self):
+ mock_traffic_profile = mock.Mock(autospec=tp_base.TrafficProfile)
mock_traffic_profile.get_traffic_definition.return_value = "64"
mock_traffic_profile.params = self.TRAFFIC_PROFILE
- trex_traffic_gen = TrexTrafficGenRFC('vnf1', self.VNFD_0)
+ trex_traffic_gen = tg_rfc2544_trex.TrexTrafficGenRFC('vnf1', self.VNFD_0)
trex_traffic_gen._start_server = mock.Mock(return_value=0)
trex_traffic_gen.resource_helper = mock.MagicMock()
trex_traffic_gen.setup_helper.setup_vnf_environment = mock.MagicMock()
@@ -274,15 +258,12 @@ class TestTrexTrafficGenRFC(unittest.TestCase):
scenario_cfg.update({"nodes": ["tg_1", "vnf_1"]})
self.assertIsNone(trex_traffic_gen.instantiate(scenario_cfg, {}))
- @mock.patch(SSH_HELPER)
- def test_instantiate_error(self, ssh):
- mock_ssh(ssh, exec_result=(1, "", ""))
-
- mock_traffic_profile = mock.Mock(autospec=TrafficProfile)
+ def test_instantiate_error(self):
+ mock_traffic_profile = mock.Mock(autospec=tp_base.TrafficProfile)
mock_traffic_profile.get_traffic_definition.return_value = "64"
mock_traffic_profile.params = self.TRAFFIC_PROFILE
- trex_traffic_gen = TrexTrafficGenRFC('vnf1', self.VNFD_0)
+ trex_traffic_gen = tg_rfc2544_trex.TrexTrafficGenRFC('vnf1', self.VNFD_0)
trex_traffic_gen.resource_helper = mock.MagicMock()
trex_traffic_gen.setup_helper.setup_vnf_environment = mock.MagicMock()
scenario_cfg = {
@@ -310,29 +291,3 @@ class TestTrexTrafficGenRFC(unittest.TestCase):
},
}
trex_traffic_gen.instantiate(scenario_cfg, {})
-
- @mock.patch(SSH_HELPER)
- def test__start_server(self, ssh):
- mock_ssh(ssh)
- trex_traffic_gen = TrexTrafficGenRFC('vnf1', self.VNFD_0)
- trex_traffic_gen.resource_helper = mock.MagicMock()
- self.assertIsNone(trex_traffic_gen._start_server())
-
- @mock.patch("yardstick.network_services.vnf_generic.vnf.tg_rfc2544_trex.time")
- @mock.patch(SSH_HELPER)
- def test__generate_trex_cfg(self, ssh, _):
- mock_ssh(ssh)
-
- trex_traffic_gen = TrexTrafficGenRFC('vnf1', self.VNFD_0)
- trex_traffic_gen.ssh_helper = mock.MagicMock()
- trex_traffic_gen.resource_helper.ssh_helper = mock.MagicMock()
- self.assertIsNone(trex_traffic_gen.resource_helper.generate_cfg())
-
- def test_terminate(self):
- with mock.patch(SSH_HELPER) as ssh:
- ssh_mock = mock.Mock(autospec=ssh.SSH)
- ssh_mock.execute = mock.Mock(return_value=(0, "", ""))
- ssh.from_node.return_value = ssh_mock
- trex_traffic_gen = TrexTrafficGenRFC('vnf1', self.VNFD_0)
- trex_traffic_gen.resource_helper = mock.MagicMock()
- self.assertIsNone(trex_traffic_gen.terminate())
diff --git a/yardstick/tests/unit/network_services/vnf_generic/vnf/test_tg_trex.py b/yardstick/tests/unit/network_services/vnf_generic/vnf/test_tg_trex.py
index aae3d468f..4f8742477 100644
--- a/yardstick/tests/unit/network_services/vnf_generic/vnf/test_tg_trex.py
+++ b/yardstick/tests/unit/network_services/vnf_generic/vnf/test_tg_trex.py
@@ -11,31 +11,23 @@
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
-#
import copy
import mock
import unittest
-from yardstick.tests.unit.network_services.vnf_generic.vnf.test_base import mock_ssh
-from yardstick.tests import STL_MOCKS
+from yardstick.network_services.traffic_profile import base as tp_base
+from yardstick.network_services.traffic_profile import rfc2544
+from yardstick.network_services.vnf_generic.vnf import sample_vnf
+from yardstick.network_services.vnf_generic.vnf import tg_trex
-SSH_HELPER = 'yardstick.network_services.vnf_generic.vnf.sample_vnf.VnfSshHelper'
NAME = 'vnf_1'
-STLClient = mock.MagicMock()
-stl_patch = mock.patch.dict("sys.modules", STL_MOCKS)
-stl_patch.start()
-
-if stl_patch:
- from yardstick.network_services.vnf_generic.vnf.tg_trex import \
- TrexTrafficGen, TrexResourceHelper
- from yardstick.network_services.traffic_profile.base import TrafficProfile
-
class TestTrexTrafficGen(unittest.TestCase):
+
VNFD = {'vnfd:vnfd-catalog':
{'vnfd':
[{'short-name': 'VpeVnf',
@@ -168,7 +160,7 @@ class TestTrexTrafficGen(unittest.TestCase):
"interfaces": {
"xe0": {
"local_iface_name": "ens786f0",
- "vld_id": TrafficProfile.UPLINK,
+ "vld_id": tp_base.TrafficProfile.UPLINK,
"netmask": "255.255.255.0",
"vpci": "0000:05:00.0",
"local_ip": "152.16.100.19",
@@ -180,7 +172,7 @@ class TestTrexTrafficGen(unittest.TestCase):
},
"xe1": {
"local_iface_name": "ens786f1",
- "vld_id": TrafficProfile.DOWNLINK,
+ "vld_id": tp_base.TrafficProfile.DOWNLINK,
"netmask": "255.255.255.0",
"vpci": "0000:05:00.1",
"local_ip": "152.16.40.19",
@@ -236,7 +228,7 @@ class TestTrexTrafficGen(unittest.TestCase):
"interfaces": {
"xe0": {
"local_iface_name": "ens513f0",
- "vld_id": TrafficProfile.DOWNLINK,
+ "vld_id": tp_base.TrafficProfile.DOWNLINK,
"netmask": "255.255.255.0",
"vpci": "0000:02:00.0",
"local_ip": "152.16.40.20",
@@ -270,7 +262,7 @@ class TestTrexTrafficGen(unittest.TestCase):
"interfaces": {
"xe0": {
"local_iface_name": "ens785f0",
- "vld_id": TrafficProfile.UPLINK,
+ "vld_id": tp_base.TrafficProfile.UPLINK,
"netmask": "255.255.255.0",
"vpci": "0000:05:00.0",
"local_ip": "152.16.100.20",
@@ -297,36 +289,35 @@ class TestTrexTrafficGen(unittest.TestCase):
}
}
- @mock.patch(SSH_HELPER)
- def test___init__(self, ssh):
- mock_ssh(ssh)
+ def setUp(self):
+ self._mock_ssh_helper = mock.patch.object(sample_vnf, 'VnfSshHelper')
+ self.mock_ssh_helper = self._mock_ssh_helper.start()
+ self.addCleanup(self._stop_mocks)
+
+ def _stop_mocks(self):
+ self._mock_ssh_helper.stop()
+
+ def test___init__(self):
vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
- trex_traffic_gen = TrexTrafficGen(NAME, vnfd)
- self.assertIsInstance(
- trex_traffic_gen.resource_helper, TrexResourceHelper)
+ trex_traffic_gen = tg_trex.TrexTrafficGen(NAME, vnfd)
+ self.assertIsInstance(trex_traffic_gen.resource_helper,
+ tg_trex.TrexResourceHelper)
- @mock.patch(SSH_HELPER)
- def test_collect_kpi(self, ssh):
- mock_ssh(ssh)
+ def test_collect_kpi(self):
vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
- trex_traffic_gen = TrexTrafficGen(NAME, vnfd)
+ trex_traffic_gen = tg_trex.TrexTrafficGen(NAME, vnfd)
trex_traffic_gen.resource_helper._queue.put({})
result = trex_traffic_gen.collect_kpi()
self.assertEqual({}, result)
- @mock.patch(SSH_HELPER)
- def test_listen_traffic(self, ssh):
- mock_ssh(ssh)
+ def test_listen_traffic(self):
vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
- trex_traffic_gen = TrexTrafficGen(NAME, vnfd)
+ trex_traffic_gen = tg_trex.TrexTrafficGen(NAME, vnfd)
self.assertIsNone(trex_traffic_gen.listen_traffic({}))
- @mock.patch(SSH_HELPER)
- def test_instantiate(self, ssh):
- mock_ssh(ssh)
-
+ def test_instantiate(self):
vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
- trex_traffic_gen = TrexTrafficGen(NAME, vnfd)
+ trex_traffic_gen = tg_trex.TrexTrafficGen(NAME, vnfd)
trex_traffic_gen._start_server = mock.Mock(return_value=0)
trex_traffic_gen._tg_process = mock.MagicMock()
trex_traffic_gen._tg_process.start = mock.Mock()
@@ -335,16 +326,12 @@ class TestTrexTrafficGen(unittest.TestCase):
trex_traffic_gen.ssh_helper = mock.MagicMock()
trex_traffic_gen.resource_helper.ssh_helper = mock.MagicMock()
trex_traffic_gen.setup_helper.setup_vnf_environment = mock.MagicMock()
+ self.assertIsNone(trex_traffic_gen.instantiate(self.SCENARIO_CFG,
+ self.CONTEXT_CFG))
- self.assertIsNone(trex_traffic_gen.instantiate(
- self.SCENARIO_CFG, self.CONTEXT_CFG))
-
- @mock.patch(SSH_HELPER)
- def test_instantiate_error(self, ssh):
- mock_ssh(ssh, exec_result=(1, "", ""))
-
+ def test_instantiate_error(self):
vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
- trex_traffic_gen = TrexTrafficGen(NAME, vnfd)
+ trex_traffic_gen = tg_trex.TrexTrafficGen(NAME, vnfd)
trex_traffic_gen._start_server = mock.Mock(return_value=0)
trex_traffic_gen._tg_process = mock.MagicMock()
trex_traffic_gen._tg_process.start = mock.Mock()
@@ -352,62 +339,53 @@ class TestTrexTrafficGen(unittest.TestCase):
trex_traffic_gen.ssh_helper = mock.MagicMock()
trex_traffic_gen.resource_helper.ssh_helper = mock.MagicMock()
trex_traffic_gen.setup_helper.setup_vnf_environment = mock.MagicMock()
- self.assertIsNone(trex_traffic_gen.instantiate(
- self.SCENARIO_CFG, self.CONTEXT_CFG))
+ self.assertIsNone(trex_traffic_gen.instantiate(self.SCENARIO_CFG,
+ self.CONTEXT_CFG))
- @mock.patch(SSH_HELPER)
- def test__start_server(self, ssh):
- mock_ssh(ssh)
+ def test__start_server(self):
vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
- trex_traffic_gen = TrexTrafficGen(NAME, vnfd)
+ trex_traffic_gen = tg_trex.TrexTrafficGen(NAME, vnfd)
trex_traffic_gen.ssh_helper = mock.MagicMock()
trex_traffic_gen.resource_helper.ssh_helper = mock.MagicMock()
trex_traffic_gen.scenario_helper.scenario_cfg = {}
self.assertIsNone(trex_traffic_gen._start_server())
- @mock.patch(SSH_HELPER)
- def test__start_server_multiple_queues(self, ssh):
- mock_ssh(ssh)
+ def test__start_server_multiple_queues(self):
vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
- trex_traffic_gen = TrexTrafficGen(NAME, vnfd)
+ trex_traffic_gen = tg_trex.TrexTrafficGen(NAME, vnfd)
trex_traffic_gen.ssh_helper = mock.MagicMock()
trex_traffic_gen.resource_helper.ssh_helper = mock.MagicMock()
trex_traffic_gen.scenario_helper.scenario_cfg = {
"options": {NAME: {"queues_per_port": 2}}}
self.assertIsNone(trex_traffic_gen._start_server())
- @mock.patch(SSH_HELPER)
- def test__traffic_runner(self, ssh):
- mock_ssh(ssh)
-
- mock_traffic_profile = mock.Mock(autospec=TrafficProfile)
+ def test__traffic_runner(self):
+ mock_traffic_profile = mock.Mock(autospec=tp_base.TrafficProfile)
mock_traffic_profile.get_traffic_definition.return_value = "64"
mock_traffic_profile.execute_traffic.return_value = "64"
mock_traffic_profile.params = self.TRAFFIC_PROFILE
vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
- self.sut = TrexTrafficGen(NAME, vnfd)
+ self.sut = tg_trex.TrexTrafficGen(NAME, vnfd)
self.sut.ssh_helper = mock.Mock()
self.sut.ssh_helper.run = mock.Mock()
- self.sut._connect_client = mock.Mock(autospec=STLClient)
+ self.sut._connect_client = mock.Mock()
self.sut._connect_client.get_stats = mock.Mock(return_value="0")
self.sut.resource_helper.RUN_DURATION = 0
self.sut.resource_helper.QUEUE_WAIT_TIME = 0
- # must generate cfg before we can run traffic so Trex port mapping is created
+ # must generate cfg before we can run traffic so Trex port mapping is
+ # created
self.sut.resource_helper.generate_cfg()
- self.sut._traffic_runner(mock_traffic_profile)
+ with mock.patch.object(self.sut.resource_helper, 'run_traffic'):
+ self.sut._traffic_runner(mock_traffic_profile)
- @mock.patch(SSH_HELPER)
- def test__generate_trex_cfg(self, ssh):
- mock_ssh(ssh)
+ def test__generate_trex_cfg(self):
vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
- trex_traffic_gen = TrexTrafficGen(NAME, vnfd)
+ trex_traffic_gen = tg_trex.TrexTrafficGen(NAME, vnfd)
trex_traffic_gen.resource_helper.ssh_helper = mock.MagicMock()
self.assertIsNone(trex_traffic_gen.resource_helper.generate_cfg())
- @mock.patch(SSH_HELPER)
- def test_build_ports_reversed_pci_ordering(self, ssh):
- mock_ssh(ssh)
+ def test_build_ports_reversed_pci_ordering(self):
vnfd = copy.deepcopy(self.VNFD['vnfd:vnfd-catalog']['vnfd'][0])
vnfd['vdu'][0]['external-interface'] = [
{'virtual-interface':
@@ -442,26 +420,24 @@ class TestTrexTrafficGen(unittest.TestCase):
'local_mac': '00:00:00:00:00:01'},
'vnfd-connection-point-ref': 'xe1',
'name': 'xe1'}]
- trex_traffic_gen = TrexTrafficGen(NAME, vnfd)
+ trex_traffic_gen = tg_trex.TrexTrafficGen(NAME, vnfd)
trex_traffic_gen.resource_helper.ssh_helper = mock.MagicMock()
trex_traffic_gen.resource_helper.generate_cfg()
trex_traffic_gen.resource_helper._build_ports()
- self.assertEqual(
- sorted(trex_traffic_gen.resource_helper.all_ports), [0, 1])
+ self.assertEqual(sorted(trex_traffic_gen.resource_helper.all_ports),
+ [0, 1])
# there is a gap in ordering
- self.assertEqual(dict(trex_traffic_gen.resource_helper.dpdk_to_trex_port_map),
- {0: 0, 2: 1})
-
- @mock.patch(SSH_HELPER)
- def test_run_traffic(self, ssh):
- mock_ssh(ssh)
+ self.assertEqual(
+ {0: 0, 2: 1},
+ dict(trex_traffic_gen.resource_helper.dpdk_to_trex_port_map))
- mock_traffic_profile = mock.Mock(autospec=TrafficProfile)
+ def test_run_traffic(self):
+ mock_traffic_profile = mock.Mock(autospec=tp_base.TrafficProfile)
mock_traffic_profile.get_traffic_definition.return_value = "64"
mock_traffic_profile.params = self.TRAFFIC_PROFILE
vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
- self.sut = TrexTrafficGen(NAME, vnfd)
+ self.sut = tg_trex.TrexTrafficGen(NAME, vnfd)
self.sut.ssh_helper = mock.Mock()
self.sut.ssh_helper.run = mock.Mock()
self.sut._traffic_runner = mock.Mock(return_value=0)
@@ -470,20 +446,60 @@ class TestTrexTrafficGen(unittest.TestCase):
self.sut._traffic_process.terminate()
self.assertIsNotNone(result)
- @mock.patch(SSH_HELPER)
- def test_terminate(self, ssh):
- mock_ssh(ssh)
+ def test_terminate(self):
vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
- trex_traffic_gen = TrexTrafficGen(NAME, vnfd)
+ trex_traffic_gen = tg_trex.TrexTrafficGen(NAME, vnfd)
trex_traffic_gen.ssh_helper = mock.MagicMock()
trex_traffic_gen.resource_helper.ssh_helper = mock.MagicMock()
self.assertIsNone(trex_traffic_gen.terminate())
- @mock.patch(SSH_HELPER)
- def test__connect_client(self, ssh):
- mock_ssh(ssh)
+ def test__connect_client(self):
vnfd = self.VNFD['vnfd:vnfd-catalog']['vnfd'][0]
- trex_traffic_gen = TrexTrafficGen(NAME, vnfd)
- client = mock.Mock(autospec=STLClient)
+ trex_traffic_gen = tg_trex.TrexTrafficGen(NAME, vnfd)
+ client = mock.Mock()
client.connect = mock.Mock(return_value=0)
self.assertIsNotNone(trex_traffic_gen.resource_helper._connect(client))
+
+
+class TrexResourceHelperTestCase(unittest.TestCase):
+
+ def test__get_samples(self):
+ mock_setup_helper = mock.Mock()
+ trex_rh = tg_trex.TrexResourceHelper(mock_setup_helper)
+ trex_rh.vnfd_helper.interfaces = [
+ {'name': 'interface1'},
+ {'name': 'interface2'}]
+ stats = {
+ 10: {'rx_pps': 5, 'ipackets': 200},
+ 20: {'rx_pps': 10, 'ipackets': 300},
+ 'latency': {1: {'latency': 'latency_port_10_pg_id_1'},
+ 2: {'latency': 'latency_port_10_pg_id_2'},
+ 3: {'latency': 'latency_port_20_pg_id_3'},
+ 4: {'latency': 'latency_port_20_pg_id_4'}}
+ }
+ port_pg_id = rfc2544.PortPgIDMap()
+ port_pg_id.add_port(10)
+ port_pg_id.increase_pg_id()
+ port_pg_id.increase_pg_id()
+ port_pg_id.add_port(20)
+ port_pg_id.increase_pg_id()
+ port_pg_id.increase_pg_id()
+
+ with mock.patch.object(trex_rh, 'get_stats') as mock_get_stats, \
+ mock.patch.object(trex_rh.vnfd_helper, 'port_num') as \
+ mock_port_num:
+ mock_get_stats.return_value = stats
+ mock_port_num.side_effect = [10, 20]
+ output = trex_rh._get_samples([10, 20], port_pg_id=port_pg_id)
+
+ interface = output['interface1']
+ self.assertEqual(5.0, interface['rx_throughput_fps'])
+ self.assertEqual(200, interface['in_packets'])
+ self.assertEqual('latency_port_10_pg_id_1', interface['latency'][1])
+ self.assertEqual('latency_port_10_pg_id_2', interface['latency'][2])
+
+ interface = output['interface2']
+ self.assertEqual(10.0, interface['rx_throughput_fps'])
+ self.assertEqual(300, interface['in_packets'])
+ self.assertEqual('latency_port_20_pg_id_3', interface['latency'][3])
+ self.assertEqual('latency_port_20_pg_id_4', interface['latency'][4])
diff --git a/yardstick/tests/unit/test_cmd/commands/test_env.py b/yardstick/tests/unit/test_cmd/commands/test_env.py
index 57dacbcd3..5d3520986 100644
--- a/yardstick/tests/unit/test_cmd/commands/test_env.py
+++ b/yardstick/tests/unit/test_cmd/commands/test_env.py
@@ -6,60 +6,64 @@
# which accompanies this distribution, and is available at
# http://www.apache.org/licenses/LICENSE-2.0
##############################################################################
-from __future__ import absolute_import
-import unittest
+
+import os
+import sys
+
import mock
import uuid
-from yardstick.cmd.commands.env import EnvCommand
+from yardstick.cmd.commands import env
+from yardstick.tests.unit import base
-class EnvCommandTestCase(unittest.TestCase):
+class EnvCommandTestCase(base.BaseUnitTestCase):
- @mock.patch('yardstick.cmd.commands.env.EnvCommand._start_async_task')
- @mock.patch('yardstick.cmd.commands.env.EnvCommand._check_status')
+ @mock.patch.object(env.EnvCommand, '_start_async_task')
+ @mock.patch.object(env.EnvCommand, '_check_status')
def test_do_influxdb(self, check_status_mock, start_async_task_mock):
- env = EnvCommand()
- env.do_influxdb({})
+ _env = env.EnvCommand()
+ _env.do_influxdb({})
start_async_task_mock.assert_called_once()
check_status_mock.assert_called_once()
- @mock.patch('yardstick.cmd.commands.env.EnvCommand._start_async_task')
- @mock.patch('yardstick.cmd.commands.env.EnvCommand._check_status')
+ @mock.patch.object(env.EnvCommand, '_start_async_task')
+ @mock.patch.object(env.EnvCommand, '_check_status')
def test_do_grafana(self, check_status_mock, start_async_task_mock):
- env = EnvCommand()
- env.do_grafana({})
+ _env = env.EnvCommand()
+ _env.do_grafana({})
start_async_task_mock.assert_called_once()
check_status_mock.assert_called_once()
- @mock.patch('yardstick.cmd.commands.env.EnvCommand._start_async_task')
- @mock.patch('yardstick.cmd.commands.env.EnvCommand._check_status')
+ @mock.patch.object(env.EnvCommand, '_start_async_task')
+ @mock.patch.object(env.EnvCommand, '_check_status')
def test_do_prepare(self, check_status_mock, start_async_task_mock):
- env = EnvCommand()
- env.do_prepare({})
+ _env = env.EnvCommand()
+ _env.do_prepare({})
start_async_task_mock.assert_called_once()
check_status_mock.assert_called_once()
- @mock.patch('yardstick.cmd.commands.env.HttpClient.post')
+ @mock.patch.object(env.HttpClient, 'post')
def test_start_async_task(self, post_mock):
data = {'action': 'create_grafana'}
- EnvCommand()._start_async_task(data)
+ env.EnvCommand()._start_async_task(data)
post_mock.assert_called_once()
- @mock.patch('yardstick.cmd.commands.env.HttpClient.get')
- @mock.patch('yardstick.cmd.commands.env.EnvCommand._print_status')
- def test_check_status(self, print_mock, get_mock):
- # pylint: disable=unused-argument
- # NOTE(ralonsoh): the pylint exception must be removed. The mocked
- # command call must be tested.
+ @mock.patch.object(env.HttpClient, 'get')
+ @mock.patch.object(env.EnvCommand, '_print_status')
+ def test_check_status(self, mock_print, mock_get):
task_id = str(uuid.uuid4())
- get_mock.return_value = {'status': 2, 'result': 'error'}
- status = EnvCommand()._check_status(task_id, 'hello world')
- self.assertEqual(status, 2)
+ mock_get.return_value = {'status': 2, 'result': 'error'}
+ self.assertEqual(
+ 2, env.EnvCommand()._check_status(task_id, 'hello world'))
+ self.assertEqual(2, mock_print.call_count)
- def test_print_status(self):
- try:
- EnvCommand()._print_status('hello', 'word')
- except Exception as e: # pylint: disable=broad-except
- # NOTE(ralonsoh): try to reduce the scope of this exception.
- self.assertIsInstance(e, IndexError)
+ @mock.patch.object(sys, 'stdout')
+ @mock.patch.object(os, 'popen')
+ def test_print_status(self, mock_popen, mock_stdout):
+ mock_popen_obj = mock.Mock()
+ mock_popen_obj.read.return_value = ''
+ mock_popen.return_value = mock_popen_obj
+ env.EnvCommand()._print_status('hello', 'word')
+ mock_stdout.write.assert_not_called()
+ mock_stdout.flush.assert_not_called()