These network testing tools are barely used nowadays. Standard tools like iperf are preferred for performance testing, and OVS system tests already cover basic connectivity use cases. Remove the utilities, their man pages, the supporting ovstest Python module, and all build system and packaging references.
ovs-vlan-test is retained as it is an independent self-contained tool. Suggested-by: Ilya Maximets <[email protected]> Signed-off-by: Timothy Redaelli <[email protected]> --- Documentation/automake.mk | 2 - Documentation/conf.py | 4 - Documentation/ref/index.rst | 6 - Documentation/ref/ovs-l3ping.8.rst | 129 --------- Documentation/ref/ovs-test.8.rst | 163 ----------- Documentation/ref/ovs-vlan-test.8.rst | 9 +- NEWS | 3 + debian/control.in | 7 - debian/openvswitch-test.install | 5 - python/automake.mk | 14 +- python/ovstest/__init__.py | 1 - python/ovstest/args.py | 283 -------------------- python/ovstest/rpcserver.py | 372 -------------------------- python/ovstest/tcp.py | 120 --------- python/ovstest/tests.py | 248 ----------------- python/ovstest/udp.py | 85 ------ python/ovstest/util.py | 249 ----------------- python/ovstest/vswitch.py | 107 -------- rhel/openvswitch-fedora.spec.in | 5 - rhel/openvswitch.spec.in | 6 +- utilities/.gitignore | 4 - utilities/automake.mk | 6 - utilities/ovs-l3ping.in | 76 ------ utilities/ovs-test.in | 141 ---------- 24 files changed, 7 insertions(+), 2038 deletions(-) delete mode 100644 Documentation/ref/ovs-l3ping.8.rst delete mode 100644 Documentation/ref/ovs-test.8.rst delete mode 100644 python/ovstest/__init__.py delete mode 100644 python/ovstest/args.py delete mode 100644 python/ovstest/rpcserver.py delete mode 100644 python/ovstest/tcp.py delete mode 100644 python/ovstest/tests.py delete mode 100644 python/ovstest/udp.py delete mode 100644 python/ovstest/util.py delete mode 100644 python/ovstest/vswitch.py delete mode 100644 utilities/ovs-l3ping.in delete mode 100644 utilities/ovs-test.in diff --git a/Documentation/automake.mk b/Documentation/automake.mk index ea9459b55..8cc5058cb 100644 --- a/Documentation/automake.mk +++ b/Documentation/automake.mk @@ -163,11 +163,9 @@ RST_MANPAGES = \ ovs-appctl.8.rst \ ovs-ctl.8.rst \ ovs-flowviz.8.rst \ - ovs-l3ping.8.rst \ ovs-pki.8.rst \ ovs-tcpdump.8.rst \ ovs-tcpundump.1.rst \ - ovs-test.8.rst \ ovs-vlan-test.8.rst \ ovsdb-server.7.rst \ ovsdb.5.rst \ diff --git a/Documentation/conf.py b/Documentation/conf.py index 276999b29..dc62c3fd4 100644 --- a/Documentation/conf.py +++ b/Documentation/conf.py @@ -132,8 +132,6 @@ _man_pages = [ u'OVS startup helper script'), ('ovs-flowviz.8', u'utility for visualizing OpenFlow and datapath flows'), - ('ovs-l3ping.8', - u'check network deployment for L3 tunneling problems'), ('ovs-pki.8', u'OpenFlow public key infrastructure management utility'), ('ovs-sim.1', @@ -142,8 +140,6 @@ _man_pages = [ u'Dump traffic from an Open vSwitch port using tcpdump'), ('ovs-tcpundump.1', u'convert "tcpdump -xx" output to hex strings'), - ('ovs-test.8', - u'Check Linux drivers for performance, vlan and L3 tunneling problems'), ('ovs-vlan-test.8', u'Check Linux drivers for problems with vlan traffic'), ('ovsdb-server.7', diff --git a/Documentation/ref/index.rst b/Documentation/ref/index.rst index fbf296647..9d931018a 100644 --- a/Documentation/ref/index.rst +++ b/Documentation/ref/index.rst @@ -43,12 +43,10 @@ time: ovs-appctl.8 ovs-ctl.8 ovs-flowviz.8 - ovs-l3ping.8 ovs-pki.8 ovs-sim.1 ovs-tcpdump.8 ovs-tcpundump.1 - ovs-test.8 ovs-vlan-test.8 ovsdb-server.7 ovsdb.5 @@ -94,10 +92,6 @@ The remainder are still in roff format can be found below: - `(pdf) <http://www.openvswitch.org/support/dist-docs/ovs-pcap.1.pdf>`__ - `(html) <http://www.openvswitch.org/support/dist-docs/ovs-pcap.1.html>`__ - `(plain text) <http://www.openvswitch.org/support/dist-docs/ovs-pcap.1.txt>`__ - * - ovs-test(8) - - `(pdf) <http://www.openvswitch.org/support/dist-docs/ovs-test.8.pdf>`__ - - `(html) <http://www.openvswitch.org/support/dist-docs/ovs-test.8.html>`__ - - `(plain text) <http://www.openvswitch.org/support/dist-docs/ovs-test.8.txt>`__ * - ovs-testcontroller(8) - `(pdf) <http://www.openvswitch.org/support/dist-docs/ovs-testcontroller.8.pdf>`__ - `(html) <http://www.openvswitch.org/support/dist-docs/ovs-testcontroller.8.html>`__ diff --git a/Documentation/ref/ovs-l3ping.8.rst b/Documentation/ref/ovs-l3ping.8.rst deleted file mode 100644 index f9c88fcd6..000000000 --- a/Documentation/ref/ovs-l3ping.8.rst +++ /dev/null @@ -1,129 +0,0 @@ -========== -ovs-l3ping -========== - -Synopsis -======== - -``ovs-l3ping -s <TunnelRemoteIP>,<InnerIP>[/<mask>] -t <tunnelmode>`` - -``ovs-l3ping -s <TunnelRemoteIP>,<InnerIP>[/<mask>][:<ControlPort>] -t -<tunnelmode>`` - -``ovs-l3ping -c <TunnelRemoteIP>,<InnerIP>[/<mask>],<RemoteInnerIP> -t -<tunnelmode>`` - -``ovs-l3ping -c -<TunnelRemoteIP>,<InnerIP>[/<mask>][:<ControlPort>[:<DataPort>]],<RemoteInnerIP>[:<ControlPort>[:<DataPort>]] -[-b <targetbandwidth>] [-i <testinterval>] --t <tunnelmode>`` - -``ovs-l3ping -h | --help`` - -``ovs-l3ping -V | --version`` - -Description -=========== - -The ``ovs-l3ping`` program may be used to check for problems that -could be caused by invalid routing policy, misconfigured firewall in -the tunnel path or a bad NIC driver. On one of the nodes, run -``ovs-l3ping`` in server mode and on the other node run it in client -mode. The client and server will establish L3 tunnel, over which -client will give further testing instructions. The ``ovs-l3ping`` -client will perform UDP and TCP tests. This tool is different from -``ovs-test`` that it encapsulates XML/RPC control connection over the -tunnel, so there is no need to open special holes in firewall. - -UDP tests can report packet loss and achieved bandwidth for various -datagram sizes. By default target bandwidth for UDP tests is 1Mbit/s. - -TCP tests report only achieved bandwidth, because kernel TCP stack -takes care of flow control and packet loss. - -Client Mode ------------ - -An ``ovs-l3ping`` client will create a L3 tunnel and connect over it -to the ``ovs-l3ping`` server to schedule the tests. <TunnelRemoteIP> -is the peer's IP address, where tunnel will be terminated. <InnerIP> -is the address that will be temporarily assigned during testing. All -test traffic originating from this IP address to the <RemoteInnerIP> -will be tunneled. It is possible to override default <ControlPort> -and <DataPort>, if there is any other application that already listens -on those two ports. - -Server Mode ------------ - -To conduct tests, ``ovs-l3ping`` server must be running. It is -required that both client and server <InnerIP> addresses are in the -same subnet. It is possible to specify <InnerIP> with netmask in CIDR -format. - -Options -======= - -One of ``-s`` or ``-c`` is required. The ``-t`` option is -also required. - -* ``-s <TunnelRemoteIP>,<InnerIP>[/<mask>][:<ControlPort>]`` or - ``--server <TunnelRemoteIP>,<InnerIP>[/<mask>][:<ControlPort>]`` - - Run in server mode and create L3 tunnel with the client that will be - accepting tunnel at <TunnelRemoteIP> address. The socket on - ``<InnerIP>[:<ControlPort>]`` will be used to receive further - instructions from the client. - -* ``-c - <TunnelRemoteIP>,<InnerIP>[/<mask>][:<ControlPort>[:<DataPort>]],<RemoteInnerIP>[:<ControlPort>[:<DataPort>]]`` - or ``--client - <TunnelRemoteIP>,<InnerIP>[/<mask>][:<ControlPort>[:<DataPort>]],<RemoteInnerIP>[:<ControlPort>[:<DataPort>]]`` - - Run in client mode and create L3 tunnel with the server on - <TunnelRemoteIP>. The client will use <InnerIP> to generate test - traffic with the server's <RemoteInnerIP>. - -* ``-b <targetbandwidth>`` or ``--bandwidth <targetbandwidth>`` - - Target bandwidth for UDP tests. The <targetbandwidth> must be given - in bits per second. Use postfix M or K to alter the target - bandwidth magnitude. - -* ``-i <testinterval>`` or ``--interval <testinterval>`` - - How long each test should run. By default 5 seconds. - -* ``-t <tunnelmode>`` or ``--tunnel-mode <tunnelmode>`` - - Specify the tunnel type. This option must match on server and - client. - -* ``-h`` or ``--help`` - - Prints a brief help message to the console. - -* ``-V`` or ``--version`` - - Prints version information to the console. - -Examples -======== - -On host 192.168.122.220 start ``ovs-l3ping`` in server mode. This command -will create a temporary GRE tunnel with the host 192.168.122.236 and assign -10.1.1.1/28 as the inner IP address, where client will have to connect:: - - ovs-l3ping -s 192.168.122.236,10.1.1.1/28 -t gre - -On host 192.168.122.236 start ``ovs-l3ping`` in client mode. This command -will use 10.1.1.2/28 as the local inner IP address and will connect over the -L3 tunnel to the server's inner IP address at 10.1.1.1:: - - ovs-l3ping -c 192.168.122.220,10.1.1.2/28,10.1.1.1 -t gre - -See Also -======== - -``ovs-vswitchd(8)``, ``ovs-ofctl(8)``, ``ovs-vsctl(8)``, -``ovs-vlan-test(8)``, ``ovs-test(8)``, ``ethtool(8)``, ``uname(1)``. diff --git a/Documentation/ref/ovs-test.8.rst b/Documentation/ref/ovs-test.8.rst deleted file mode 100644 index f902d9c3b..000000000 --- a/Documentation/ref/ovs-test.8.rst +++ /dev/null @@ -1,163 +0,0 @@ -======== -ovs-test -======== - -Synopsis -======== - -**ovs-test** -s *port* - -**ovs-test** -c *server1* *server2* [**-b** *targetbandwidth*] [**-i** *testinterval*] [**-d**] - [**-l** *vlantag*] [**-t** *tunnelmodes*] - -Description -=========== - -The :program:`ovs-test` program may be used to check for problems sending -802.1Q or GRE traffic that Open vSwitch may uncover. These problems, for -example, can occur when Open vSwitch is used to send 802.1Q traffic through -physical interfaces running certain drivers of certain Linux kernel versions. -To run a test, configure IP addresses on `server1` and `server2` for interfaces -you intended to test. These interfaces could also be already configured OVS -bridges that have a physical interface attached to them. Then, on one of the -nodes, run :program:`ovs-test` in server mode and on the other node run it in -client mode. The client will connect to :program:`ovs-test` server and schedule -tests between both of them. The :program:`ovs-test` client will perform UDP and -TCP tests. - -UDP tests can report packet loss and achieved bandwidth for various datagram -sizes. By default target bandwidth for UDP tests is 1Mbit/s. - -TCP tests report only achieved bandwidth, because kernel TCP stack takes care -of flow control and packet loss. TCP tests are essential to detect potential -TSO related issues. - -To determine whether Open vSwitch is encountering any problems, the user must -compare packet loss and achieved bandwidth in a setup where traffic is being -directly sent and in one where it is not. If in the 802.1Q or L3 tunneled tests -both :program:`ovs-test` processes are unable to communicate or the achieved -bandwidth is much lower compared to direct setup, then, most likely, Open -vSwitch has encountered a pre-existing kernel or driver bug. - -Some examples of the types of problems that may be encountered are: - -- When NICs use VLAN stripping on receive they must pass a pointer to a - `vlan_group` when reporting the stripped tag to the networking core. If no - `vlan_group` is in use then some drivers just drop the extracted tag. - Drivers are supposed to only enable stripping if a `vlan_group` is registered - but not all of them do that. - -- On receive, some drivers handle priority tagged packets specially and don't - pass the tag onto the network stack at all, so Open vSwitch never has a - chance to see it. - -- Some drivers size their receive buffers based on whether a `vlan_group` is - enabled, meaning that a maximum size packet with a VLAN tag will not fit if - no `vlan_group` is configured. - -- On transmit, some drivers expect that VLAN acceleration will be used if it is - available, which can only be done if a `vlan_group` is configured. In these - cases, the driver may fail to parse the packet and correctly setup checksum - offloading or TSO. - -Client Mode - An :program:`ovs-test` client will connect to two :program:`ovs-test` servers - and will ask them to exchange test traffic. It is also possible to spawn an - :program:`ovs-test` server automatically from the client. - -Server Mode - To conduct tests, two :program:`ovs-test` servers must be running on two - different hosts where the client can connect. The actual test traffic is - exchanged only between both :program:`ovs-test` servers. It is recommended - that both servers have their IP addresses in the same subnet, otherwise one - would have to make sure that routing is set up correctly. - -Options -======= - -.. program:: ovs-test - -.. option:: -s <port>, --server <port> - - Run in server mode and wait for the client to establish XML RPC Control - Connection on this TCP port. It is recommended to have `ethtool(8)` - installed on the server so that it could retrieve information about the NIC - driver. - -.. option:: -c <server1> <server2>, --client <server1> <server2> - - Run in client mode and schedule tests between `server1` and `server2`, - where each server must be given in the following format:: - - OuterIP[:OuterPort],InnerIP[/Mask][:InnerPort]. - - The `OuterIP` must be already assigned to the physical interface which is - going to be tested. This is the IP address where client will try to - establish XML RPC connection. If `OuterIP` is 127.0.0.1 then client will - automatically spawn a local instance of :program:`ovs-test` server. - OuterPort is TCP port where server is listening for incoming XML/RPC - control connections to schedule tests (by default it is 15531). The - :program:`ovs-test` will automatically assign `InnerIP[/Mask]` to the - interfaces that will be created on the fly for testing purposes. It is - important that `InnerIP[/Mask]` does not interfere with already existing IP - addresses on both :program:`ovs-test` servers and client. InnerPort is port - which will be used by server to listen for test traffic that will be - encapsulated (by default it is 15532). - -.. option:: -b <targetbandwidth>, --bandwidth <targetbandwidth> - - Target bandwidth for UDP tests. The targetbandwidth must be given in bits - per second. It is possible to use postfix `M` or `K` to alter the target - bandwidth magnitude. - -.. option:: -i <testinterval>, --interval <testinterval> - - How long each test should run. By default 5 seconds. - -.. option:: -h, --help - - Prints a brief help message to the console. - -.. option:: -V, --version - - Prints version information to the console. - -The following test modes are supported by :program:`ovs-test`. It is possible -to combine multiple of them in a single :program:`ovs-test` invocation. - -.. option:: -d, --direct - - Perform direct tests between both OuterIP addresses. These tests could be - used as a reference to compare 802.1Q or L3 tunneling test results. - -.. option:: -l <vlantag>, --vlan-tag <vlantag> - - Perform 802.1Q tests between both servers. These tests will create a - temporary OVS bridge, if necessary, and attach a VLAN tagged port to - it for testing purposes. - -.. option:: -t <tunnelmodes>, --tunnel-modes <tunnelmodes> - - Perform L3 tunneling tests. The given argument is a comma sepa‐ rated - string that specifies all the L3 tunnel modes that should be tested (e.g. - gre). The L3 tunnels are terminated on interface that has the OuterIP - address assigned. - -Examples -======== - -On host 1.2.3.4 start :program:`ovs-test` in server mode:: - - ovs-test -s 15531 - -On host 1.2.3.5 start :program:`ovs-test` in client mode and do direct, VLAN -and GRE tests between both nodes:: - - ovs-test -c 127.0.0.1,1.1.1.1/30 1.2.3.4,1.1.1.2/30 -d -l 123 -t - gre - -See Also -======== - -`ovs-vswitchd(8)`, `ovs-ofctl(8)`, `ovs-vsctl(8)`, :program:`ovs-vlan-test`, -`ethtool(8)`, `uname(1)` diff --git a/Documentation/ref/ovs-vlan-test.8.rst b/Documentation/ref/ovs-vlan-test.8.rst index d4fbabbdf..bd945c016 100644 --- a/Documentation/ref/ovs-vlan-test.8.rst +++ b/Documentation/ref/ovs-vlan-test.8.rst @@ -10,12 +10,6 @@ Synopsis Description =========== -The :program:`ovs-vlan-test` utility has some limitations, for example, it does -not use TCP in its tests. Also it does not take into account MTU to detect -potential edge cases. To overcome those limitations a new tool was developed - -:program:`ovs-test`. :program:`ovs-test` is currently supported only on Debian -so, if possible, try to use that on instead of :program:`ovs-vlan-test`. - The :program:`ovs-vlan-test` program may be used to check for problems sending 802.1Q traffic which may occur when running Open vSwitch. These problems can occur when Open vSwitch is used to send 802.1Q traffic through physical @@ -109,5 +103,4 @@ Run an :program:`ovs-vlan-test` client with a control server located at See Also ======== -`ovs-vswitchd(8)`, `ovs-ofctl(8)`, `ovs-vsctl(8)`, :program:`ovs-test`, -`ethtool(8)`, `uname(1)` +`ovs-vswitchd(8)`, `ovs-ofctl(8)`, `ovs-vsctl(8)`, `ethtool(8)`, `uname(1)` diff --git a/NEWS b/NEWS index 1a3044cbf..c14f987db 100644 --- a/NEWS +++ b/NEWS @@ -1,5 +1,8 @@ Post-v3.7.0 -------------------- + - Removed ovs-test, ovs-l3ping utilities and the ovstest Python module. + Standard tools like iperf are preferred for performance testing, and + OVS system tests cover basic connectivity use cases. - Userspace datapath: * ARP/ND lookups for native tunnel are now rate limited. The holdout timer can be configured with 'tnl/neigh/retrans_time'. diff --git a/debian/control.in b/debian/control.in index 836e2564a..1189b4bf3 100644 --- a/debian/control.in +++ b/debian/control.in @@ -210,15 +210,8 @@ Description: Open vSwitch switch implementations Package: openvswitch-test Architecture: all Depends: - python3-twisted, ${misc:Depends}, ${python3:Depends}, -Breaks: - python3-openvswitch (<< 2.17~), - openvswitch-common (<< 2.17~), -Replaces: - python3-openvswitch (<< 2.17~), - openvswitch-common (<< 2.17~), Description: Open vSwitch test package Open vSwitch is a production quality, multilayer, software-based, Ethernet virtual switch. It is designed to enable massive network diff --git a/debian/openvswitch-test.install b/debian/openvswitch-test.install index dfc8ebf30..3790b8f55 100644 --- a/debian/openvswitch-test.install +++ b/debian/openvswitch-test.install @@ -1,6 +1 @@ -usr/bin/ovs-l3ping -usr/bin/ovs-test -usr/share/man/man8/ovs-l3ping.8 -usr/share/man/man8/ovs-test.8 -usr/share/openvswitch/python/ovstest usr/lib/python3/dist-packages/ usr/share/openvswitch/scripts/usdt/* diff --git a/python/automake.mk b/python/automake.mk index 060d76cb7..3caf39140 100644 --- a/python/automake.mk +++ b/python/automake.mk @@ -1,13 +1,3 @@ -ovstest_pyfiles = \ - python/ovstest/__init__.py \ - python/ovstest/args.py \ - python/ovstest/rpcserver.py \ - python/ovstest/tcp.py \ - python/ovstest/tests.py \ - python/ovstest/udp.py \ - python/ovstest/util.py \ - python/ovstest/vswitch.py - ovs_pyfiles = \ python/ovs/__init__.py \ python/ovs/compat/__init__.py \ @@ -100,7 +90,7 @@ EXTRA_DIST += \ # C extension support. EXTRA_DIST += python/ovs/_json.c -PYFILES = $(ovs_pyfiles) python/ovs/dirs.py python/setup.py $(ovstest_pyfiles) $(ovs_pytests) \ +PYFILES = $(ovs_pyfiles) python/ovs/dirs.py python/setup.py $(ovs_pytests) \ $(ovs_flowviz) EXTRA_DIST += $(PYFILES) @@ -115,7 +105,7 @@ FLAKE8_PYFILES += \ python/ovs/dirs.py.template \ python/setup.py.template -nobase_pkgdata_DATA = $(ovs_pyfiles) $(ovstest_pyfiles) $(ovs_flowviz) +nobase_pkgdata_DATA = $(ovs_pyfiles) $(ovs_flowviz) nobase_pkgdata_DATA += python/ovs/flowviz/ovs-flowviz.conf ovs-install-data-local: diff --git a/python/ovstest/__init__.py b/python/ovstest/__init__.py deleted file mode 100644 index 218d8921e..000000000 --- a/python/ovstest/__init__.py +++ /dev/null @@ -1 +0,0 @@ -# This file intentionally left blank. diff --git a/python/ovstest/args.py b/python/ovstest/args.py deleted file mode 100644 index 975d1880b..000000000 --- a/python/ovstest/args.py +++ /dev/null @@ -1,283 +0,0 @@ -# Copyright (c) 2011, 2012 Nicira, Inc. -# -# 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. - -""" -ovsargs provide argument parsing for ovs-test utility -""" - -import argparse -import re -import socket -import sys - -CONTROL_PORT = 15531 -DATA_PORT = 15532 - - -def ip_address(string): - """Verifies if string is a valid IP address""" - try: - socket.inet_aton(string) - except socket.error: - raise argparse.ArgumentTypeError("Not a valid IPv4 address") - return string - - -def ip_optional_mask(string): - """ - Verifies if string contains a valid IP address and an optional mask in - CIDR notation. - """ - token = string.split("/") - if len(token) > 2: - raise argparse.ArgumentTypeError("IP address and netmask must be " - "separated by a single slash") - elif len(token) == 2: - try: - mask = int(token[1]) - except ValueError: - raise argparse.ArgumentTypeError("Netmask is not a valid integer") - if mask < 0 or mask > 31: - raise argparse.ArgumentTypeError("Netmask must be in range 0..31") - ip_address(token[0]) - return string - - -def port(string): - """Convert a string into a TCP/UDP Port (integer)""" - try: - port_number = int(string) - if port_number < 1 or port_number > 65535: - raise argparse.ArgumentTypeError("Port is out of range") - except ValueError: - raise argparse.ArgumentTypeError("Port is not an integer") - return port_number - - -def ip_optional_port(string, default_port, ip_callback): - """Convert a string into IP and Port pair. If port was absent then use - default_port as the port. The third argument is a callback that verifies - whether IP address is given in correct format.""" - value = string.split(':') - if len(value) == 1: - return (ip_callback(value[0]), default_port) - elif len(value) == 2: - return (ip_callback(value[0]), port(value[1])) - else: - raise argparse.ArgumentTypeError("IP address from the optional Port " - "must be colon-separated") - - -def ip_optional_port_port(string, default_port1, default_port2, ip_callback): - """Convert a string into IP, Port1, Port2 tuple. If any of ports were - missing, then default ports will be used. The fourth argument is a - callback that verifies whether IP address is given in the expected - format.""" - value = string.split(':') - if len(value) == 1: - return (ip_callback(value[0]), default_port1, default_port2) - elif len(value) == 2: - return (ip_callback(value[0]), port(value[1]), default_port2) - elif len(value) == 3: - return (ip_callback(value[0]), port(value[1]), port(value[2])) - else: - raise argparse.ArgumentTypeError("Expected IP address and at most " - "two colon-separated ports") - - -def vlan_tag(string): - """ - This function verifies whether given string is a correct VLAN tag. - """ - try: - value = int(string) - except ValueError: - raise argparse.ArgumentTypeError("VLAN tag is not a valid integer") - if value < 1 or value > 4094: - raise argparse.ArgumentTypeError("Not a valid VLAN tag. " - "VLAN tag should be in the " - "range 1..4094.") - return string - - -def server_endpoint(string): - """Converts a string OuterIP[:OuterPort],InnerIP[/Mask][:InnerPort] - into a 4-tuple, where: - 1. First element is OuterIP - 2. Second element is OuterPort (if omitted will use default value 15531) - 3 Third element is InnerIP with optional mask - 4. Fourth element is InnerPort (if omitted will use default value 15532) - """ - value = string.split(',') - if len(value) == 2: - ret1 = ip_optional_port(value[0], CONTROL_PORT, ip_address) - ret2 = ip_optional_port(value[1], DATA_PORT, ip_optional_mask) - return (ret1[0], ret1[1], ret2[0], ret2[1]) - else: - raise argparse.ArgumentTypeError("OuterIP:OuterPort and InnerIP/Mask:" - "InnerPort must be comma separated") - - -class UniqueServerAction(argparse.Action): - """ - This custom action class will prevent user from entering multiple ovs-test - servers with the same OuterIP. If there is an server with 127.0.0.1 outer - IP address then it will be inserted in the front of the list. - """ - def __call__(self, parser, namespace, values, option_string=None): - outer_ips = set() - endpoints = [] - for server in values: - try: - endpoint = server_endpoint(server) - except argparse.ArgumentTypeError: - raise argparse.ArgumentError(self, str(sys.exc_info()[1])) - if endpoint[0] in outer_ips: - raise argparse.ArgumentError(self, "Duplicate OuterIPs found") - else: - outer_ips.add(endpoint[0]) - if endpoint[0] == "127.0.0.1": - endpoints.insert(0, endpoint) - else: - endpoints.append(endpoint) - setattr(namespace, self.dest, endpoints) - - -def bandwidth(string): - """Convert a string (given in bits/second with optional magnitude for - units) into a long (bytes/second)""" - if re.match("^[1-9][0-9]*[MK]?$", string) is None: - raise argparse.ArgumentTypeError("Not a valid target bandwidth") - bwidth = string.replace("M", "000000") - bwidth = bwidth.replace("K", "000") - return int(bwidth) / 8 # Convert from bits to bytes - - -def tunnel_types(string): - """ - This function converts a string into a list that contains all tunnel types - that user intended to test. - """ - return string.split(',') - - -def l3_endpoint_client(string): - """ - This function parses command line argument string in - remoteIP,localInnerIP[/mask][:ControlPort[:TestPort]],remoteInnerIP[: - ControlPort[:TestPort]] format. - """ - try: - remote_ip, me, he = string.split(',') - except ValueError: - raise argparse.ArgumentTypeError("All 3 IP addresses must be comma " - "separated.") - r = (ip_address(remote_ip), - ip_optional_port_port(me, CONTROL_PORT, DATA_PORT, ip_optional_mask), - ip_optional_port_port(he, CONTROL_PORT, DATA_PORT, ip_address)) - return r - - -def l3_endpoint_server(string): - """ - This function parses a command line argument string in - remoteIP,localInnerIP[/mask][:ControlPort] format. - """ - try: - remote_ip, me = string.split(',') - except ValueError: - raise argparse.ArgumentTypeError("Both IP addresses must be comma " - "separated.") - return (ip_address(remote_ip), - ip_optional_port(me, CONTROL_PORT, ip_optional_mask)) - - -def ovs_initialize_args(): - """ - Initialize argument parsing for ovs-test utility. - """ - parser = argparse.ArgumentParser(description='Test connectivity ' - 'between two Open vSwitches.') - - parser.add_argument('-v', '--version', action='version', - version='ovs-test (Open vSwitch) @VERSION@') - - parser.add_argument("-b", "--bandwidth", action='store', - dest="targetBandwidth", default="1M", type=bandwidth, - help='Target bandwidth for UDP tests in bits/second. Use ' - 'postfix M or K to alter unit magnitude.') - parser.add_argument("-i", "--interval", action='store', - dest="testInterval", default=5, type=int, - help='Interval for how long to run each test in seconds.') - - parser.add_argument("-t", "--tunnel-modes", action='store', - dest="tunnelModes", default=(), type=tunnel_types, - help='Do L3 tests with the given tunnel modes.') - parser.add_argument("-l", "--vlan-tag", action='store', - dest="vlanTag", default=None, type=vlan_tag, - help='Do VLAN tests and use the given VLAN tag.') - parser.add_argument("-d", "--direct", action='store_true', - dest="direct", default=None, - help='Do direct tests between both ovs-test servers.') - - group = parser.add_mutually_exclusive_group(required=True) - group.add_argument("-s", "--server", action="store", dest="port", - type=port, - help='Run in server mode and wait for the client to ' - 'connect to this port.') - group.add_argument('-c', "--client", nargs=2, - dest="servers", action=UniqueServerAction, - metavar=("SERVER1", "SERVER2"), - help='Run in client mode and do tests between these ' - 'two ovs-test servers. Each server must be specified in ' - 'following format - OuterIP:OuterPort,InnerIP[/mask] ' - ':InnerPort. It is possible to start local instance of ' - 'ovs-test server in the client mode by using 127.0.0.1 as ' - 'OuterIP.') - return parser.parse_args() - - -def l3_initialize_args(): - """ - Initialize argument parsing for ovs-l3ping utility. - """ - parser = argparse.ArgumentParser(description='Test L3 tunnel ' - 'connectivity between two Open vSwitch instances.') - - parser.add_argument('-v', '--version', action='version', - version='ovs-l3ping (Open vSwitch) @VERSION@') - - parser.add_argument("-b", "--bandwidth", action='store', - dest="targetBandwidth", default="1M", type=bandwidth, - help='Target bandwidth for UDP tests in bits/second. Use ' - 'postfix M or K to alter unit magnitude.') - parser.add_argument("-i", "--interval", action='store', - dest="testInterval", default=5, type=int, - help='Interval for how long to run each test in seconds.') - - parser.add_argument("-t", "--tunnel-mode", action='store', - dest="tunnelMode", required=True, - help='Do L3 tests with this tunnel type.') - - group = parser.add_mutually_exclusive_group(required=True) - group.add_argument("-s", "--server", action="store", dest="server", - metavar="TUNNELIP,SERVER", - type=l3_endpoint_server, - help='Run in server mode and wait for the client to ' - 'connect.') - group.add_argument('-c', "--client", action="store", dest="client", - metavar="TUNNELIP,CLIENT,SERVER", - type=l3_endpoint_client, - help='Run in client mode and connect to the server.') - return parser.parse_args() diff --git a/python/ovstest/rpcserver.py b/python/ovstest/rpcserver.py deleted file mode 100644 index 05b6b1be2..000000000 --- a/python/ovstest/rpcserver.py +++ /dev/null @@ -1,372 +0,0 @@ -# Copyright (c) 2011, 2012 Nicira, Inc. -# -# 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. - -""" -rpcserver is an XML RPC server that allows RPC client to initiate tests -""" - -import sys - -import xmlrpc.client - -from twisted.internet import reactor -from twisted.internet.error import CannotListenError -from twisted.web import server -from twisted.web import xmlrpc - -from . import tcp, udp, util, vswitch - - -class TestArena(xmlrpc.XMLRPC): - """ - This class contains all the functions that ovs-test client will call - remotely. The caller is responsible to use designated handleIds - for designated methods (e.g. do not mix UDP and TCP handles). - """ - - def __init__(self): - xmlrpc.XMLRPC.__init__(self, allowNone=True) - self.handle_id = 1 - self.handle_map = {} - self.bridges = set() - self.pbridges = set() - self.ports = set() - self.request = None - - def __acquire_handle(self, value): - """ - Allocates new handle and assigns value object to it - """ - handle = self.handle_id - self.handle_map[handle] = value - self.handle_id += 1 - return handle - - def __get_handle_resources(self, handle): - """ - Return resources that were assigned to handle - """ - return self.handle_map[handle] - - def __delete_handle(self, handle): - """ - Releases handle from handle_map - """ - del self.handle_map[handle] - - def cleanup(self): - """ - Delete all remaining bridges and ports if ovs-test client did not had - a chance to remove them. It is necessary to call this function if - ovs-test server is abruptly terminated when doing the tests. - """ - for port in self.ports: - # Remove ports that were added to existing bridges - vswitch.ovs_vsctl_del_port_from_bridge(port) - - for bridge in self.bridges: - # Remove bridges that were added for L3 tests - vswitch.ovs_vsctl_del_bridge(bridge) - - for pbridge in self.pbridges: - # Remove bridges that were added for VLAN tests - vswitch.ovs_vsctl_del_pbridge(pbridge[0], pbridge[1]) - - def render(self, request): - """ - This method overrides the original XMLRPC.render method so that it - would be possible to get the XML RPC client IP address from the - request object. - """ - self.request = request - return xmlrpc.XMLRPC.render(self, request) - - def xmlrpc_get_my_address(self): - """ - Returns the RPC client's IP address. - """ - return self.request.getClientIP() - - def xmlrpc_get_my_address_from(self, his_ip, his_port): - """ - Returns the ovs-test server IP address that the other ovs-test server - with the given ip will see. - """ - server1 = xmlrpc.client.Server("http://%s:%u/" % (his_ip, his_port)) - return server1.get_my_address() - - def xmlrpc_create_udp_listener(self, port): - """ - Creates a UDP listener that will receive packets from UDP sender - """ - try: - listener = udp.UdpListener() - reactor.listenUDP(port, listener) - handle_id = self.__acquire_handle(listener) - except CannotListenError: - return -1 - return handle_id - - def xmlrpc_create_udp_sender(self, host, count, size, duration): - """ - Send UDP datagrams to UDP listener - """ - sender = udp.UdpSender(tuple(host), count, size, duration) - reactor.listenUDP(0, sender) - handle_id = self.__acquire_handle(sender) - return handle_id - - def xmlrpc_get_udp_listener_results(self, handle): - """ - Returns number of datagrams that were received - """ - listener = self.__get_handle_resources(handle) - return listener.getResults() - - def xmlrpc_get_udp_sender_results(self, handle): - """ - Returns number of datagrams that were sent - """ - sender = self.__get_handle_resources(handle) - return sender.getResults() - - def xmlrpc_close_udp_listener(self, handle): - """ - Releases UdpListener and all its resources - """ - listener = self.__get_handle_resources(handle) - listener.transport.stopListening() - self.__delete_handle(handle) - return 0 - - def xmlrpc_close_udp_sender(self, handle): - """ - Releases UdpSender and all its resources - """ - sender = self.__get_handle_resources(handle) - sender.transport.stopListening() - self.__delete_handle(handle) - return 0 - - def xmlrpc_create_tcp_listener(self, port): - """ - Creates a TcpListener that will accept connection from TcpSender - """ - try: - listener = tcp.TcpListenerFactory() - port = reactor.listenTCP(port, listener) - handle_id = self.__acquire_handle((listener, port)) - return handle_id - except CannotListenError: - return -1 - - def xmlrpc_create_tcp_sender(self, his_ip, his_port, duration): - """ - Creates a TcpSender that will connect to TcpListener - """ - sender = tcp.TcpSenderFactory(duration) - connector = reactor.connectTCP(his_ip, his_port, sender) - handle_id = self.__acquire_handle((sender, connector)) - return handle_id - - def xmlrpc_get_tcp_listener_results(self, handle): - """ - Returns number of bytes received - """ - (listener, _) = self.__get_handle_resources(handle) - return listener.getResults() - - def xmlrpc_get_tcp_sender_results(self, handle): - """ - Returns number of bytes sent - """ - (sender, _) = self.__get_handle_resources(handle) - return sender.getResults() - - def xmlrpc_close_tcp_listener(self, handle): - """ - Releases TcpListener and all its resources - """ - try: - (_, port) = self.__get_handle_resources(handle) - port.loseConnection() - self.__delete_handle(handle) - except KeyError: - return -1 - return 0 - - def xmlrpc_close_tcp_sender(self, handle): - """ - Releases TcpSender and all its resources - """ - try: - (_, connector) = self.__get_handle_resources(handle) - connector.disconnect() - self.__delete_handle(handle) - except KeyError: - return -1 - return 0 - - def xmlrpc_create_test_bridge(self, bridge, iface): - """ - This function creates a physical bridge from iface. It moves the - IP configuration from the physical interface to the bridge. - """ - ret = vswitch.ovs_vsctl_add_bridge(bridge) - if ret == 0: - self.pbridges.add((bridge, iface)) - util.interface_up(bridge) - (ip_addr, mask) = util.interface_get_ip(iface) - util.interface_assign_ip(bridge, ip_addr, mask) - util.interface_up(bridge) - util.move_routes(iface, bridge) - util.interface_remove_ip(iface, ip_addr, mask) - ret = vswitch.ovs_vsctl_add_port_to_bridge(bridge, iface) - if ret == 0: - self.ports.add(iface) - else: - util.interface_assign_ip(iface, ip_addr, mask) - util.interface_up(iface) - util.move_routes(bridge, iface) - vswitch.ovs_vsctl_del_bridge(bridge) - - return ret - - def xmlrpc_del_test_bridge(self, bridge, iface): - """ - This function deletes the test bridge and moves its IP configuration - back to the physical interface. - """ - ret = vswitch.ovs_vsctl_del_pbridge(bridge, iface) - self.pbridges.discard((bridge, iface)) - return ret - - def xmlrpc_get_iface_from_bridge(self, brname): - """ - Tries to figure out physical interface from bridge. - """ - return vswitch.ovs_get_physical_interface(brname) - - def xmlrpc_create_bridge(self, brname): - """ - Creates an OVS bridge. - """ - ret = vswitch.ovs_vsctl_add_bridge(brname) - if ret == 0: - self.bridges.add(brname) - return ret - - def xmlrpc_del_bridge(self, brname): - """ - Deletes an OVS bridge. - """ - ret = vswitch.ovs_vsctl_del_bridge(brname) - if ret == 0: - self.bridges.discard(brname) - return ret - - def xmlrpc_is_ovs_bridge(self, bridge): - """ - This function verifies whether given interface is an ovs bridge. - """ - return vswitch.ovs_vsctl_is_ovs_bridge(bridge) - - def xmlrpc_add_port_to_bridge(self, bridge, port): - """ - Adds a port to the OVS bridge. - """ - ret = vswitch.ovs_vsctl_add_port_to_bridge(bridge, port) - if ret == 0: - self.ports.add(port) - return ret - - def xmlrpc_del_port_from_bridge(self, port): - """ - Removes a port from OVS bridge. - """ - ret = vswitch.ovs_vsctl_del_port_from_bridge(port) - if ret == 0: - self.ports.discard(port) - return ret - - def xmlrpc_ovs_vsctl_set(self, table, record, column, key, value): - """ - This function allows to alter OVS database. - """ - return vswitch.ovs_vsctl_set(table, record, column, key, value) - - def xmlrpc_interface_up(self, iface): - """ - This function brings up given interface. - """ - return util.interface_up(iface) - - def xmlrpc_interface_assign_ip(self, iface, ip_address, mask): - """ - This function allows to assing ip address to the given interface. - """ - return util.interface_assign_ip(iface, ip_address, mask) - - def xmlrpc_interface_remove_ip(self, iface, ip_address, mask): - """ - This function allows to assing ip address to the given interface. - """ - return util.interface_remove_ip(iface, ip_address, mask) - - def xmlrpc_get_interface(self, address): - """ - Finds first interface that has given address - """ - return util.get_interface(address) - - def xmlrpc_get_interface_mtu(self, iface): - """ - Returns MTU of the given interface - """ - return util.get_interface_mtu(iface) - - def xmlrpc_uname(self): - """ - Return information about running kernel - """ - return util.uname() - - def xmlrpc_get_driver(self, iface): - """ - Returns driver version - """ - return util.get_driver(iface) - - def xmlrpc_get_interface_from_routing_decision(self, ip): - """ - Returns driver version - """ - return util.get_interface_from_routing_decision(ip) - - -def start_rpc_server(port): - """ - This function creates a RPC server and adds it to the Twisted Reactor. - """ - rpc_server = TestArena() - reactor.listenTCP(port, server.Site(rpc_server)) - try: - print("Starting RPC server\n") - sys.stdout.flush() - # If this server was started from ovs-test client then we must flush - # STDOUT so that client would know that server is ready to accept - # XML RPC connections. - reactor.run() - finally: - rpc_server.cleanup() diff --git a/python/ovstest/tcp.py b/python/ovstest/tcp.py deleted file mode 100644 index 098c6cba3..000000000 --- a/python/ovstest/tcp.py +++ /dev/null @@ -1,120 +0,0 @@ -# Copyright (c) 2011, 2012 Nicira, Inc. -# -# 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. - -""" -tcp module contains listener and sender classes for TCP protocol -""" - -import time - -from twisted.internet import interfaces -from twisted.internet.protocol import ClientFactory, Factory, Protocol - -from zope.interface.declarations import implementer - - -class TcpListenerConnection(Protocol): - """ - This per-connection class is instantiated each time sender connects - """ - def __init__(self): - self.stats = 0 - - def dataReceived(self, data): - self.stats += len(data) - - def connectionLost(self, reason): - self.factory.stats += self.stats - - -class TcpListenerFactory(Factory): - """ - This per-listening socket class is used to - instantiate TcpListenerConnections - """ - protocol = TcpListenerConnection - - def __init__(self): - self.stats = 0 - - def getResults(self): - """ returns the number of bytes received as string""" - # XML RPC does not support 64bit int (http://bugs.python.org/issue2985) - # so we have to convert the amount of bytes into a string - return str(self.stats) - - -@implementer(interfaces.IPushProducer) -class Producer(object): - """ - This producer class generates infinite byte stream for a specified time - duration - """ - def __init__(self, proto, duration): - self.proto = proto - self.start = time.time() - self.produced = 0 - self.paused = False - self.data = "X" * 65535 - self.duration = duration - - def pauseProducing(self): - """This function is called whenever write() to socket would block""" - self.paused = True - - def resumeProducing(self): - """This function is called whenever socket becomes writable""" - self.paused = False - current = time.time() - while (not self.paused) and (current < self.start + self.duration): - self.proto.transport.write(self.data) - self.produced += len(self.data) - current = time.time() - if current >= self.start + self.duration: - self.proto.factory.stats += self.produced - self.proto.transport.unregisterProducer() - self.proto.transport.loseConnection() - - def stopProducing(self): - pass - - -class TcpSenderConnection(Protocol): - """ - TCP connection instance class that sends all traffic at full speed. - """ - - def connectionMade(self): - producer = Producer(self, self.factory.duration) - self.transport.registerProducer(producer, True) - producer.resumeProducing() - - def dataReceived(self, data): - self.transport.loseConnection() - - -class TcpSenderFactory(ClientFactory): - """ - This factory is responsible to instantiate TcpSenderConnection classes - each time sender initiates connection - """ - protocol = TcpSenderConnection - - def __init__(self, duration): - self.duration = duration - self.stats = 0 - - def getResults(self): - """Returns amount of bytes sent to the Listener (as a string)""" - return str(self.stats) diff --git a/python/ovstest/tests.py b/python/ovstest/tests.py deleted file mode 100644 index f959f945e..000000000 --- a/python/ovstest/tests.py +++ /dev/null @@ -1,248 +0,0 @@ -# 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. - -import math -import time - -import ovstest.util as util - -DEFAULT_TEST_BRIDGE = "ovstestbr0" -DEFAULT_TEST_PORT = "ovstestport0" -DEFAULT_TEST_TUN = "ovstestport1" -NO_HANDLE = -1 - - -def do_udp_tests(receiver, sender, tbwidth, duration, port_sizes): - """Schedule UDP tests between receiver and sender""" - server1 = util.rpc_client(receiver[0], receiver[1]) - server2 = util.rpc_client(sender[0], sender[1]) - - udpformat = '{0:>15} {1:>15} {2:>15} {3:>15} {4:>15}' - - print("UDP test from %s:%u to %s:%u with target bandwidth %s" % - (sender[0], sender[1], receiver[0], receiver[1], - util.bandwidth_to_string(tbwidth))) - print(udpformat.format("Datagram Size", "Snt Datagrams", "Rcv Datagrams", - "Datagram Loss", "Bandwidth")) - - for size in port_sizes: - listen_handle = NO_HANDLE - send_handle = NO_HANDLE - try: - packetcnt = (tbwidth * duration) / size - - listen_handle = server1.create_udp_listener(receiver[3]) - if listen_handle == NO_HANDLE: - print("Server could not open UDP listening socket on port" - " %u. Try to restart the server.\n" % receiver[3]) - return - send_handle = server2.create_udp_sender( - (util.ip_from_cidr(receiver[2]), - receiver[3]), packetcnt, size, - duration) - - # Using sleep here because there is no other synchronization - # source that would notify us when all sent packets were received - time.sleep(duration + 1) - - rcv_packets = server1.get_udp_listener_results(listen_handle) - snt_packets = server2.get_udp_sender_results(send_handle) - - loss = math.ceil(((snt_packets - rcv_packets) * 10000.0) / - snt_packets) / 100 - bwidth = (rcv_packets * size) / duration - - print(udpformat.format(size, snt_packets, rcv_packets, - '%.2f%%' % loss, util.bandwidth_to_string(bwidth))) - finally: - if listen_handle != NO_HANDLE: - server1.close_udp_listener(listen_handle) - if send_handle != NO_HANDLE: - server2.close_udp_sender(send_handle) - print("\n") - - -def do_tcp_tests(receiver, sender, duration): - """Schedule TCP tests between receiver and sender""" - server1 = util.rpc_client(receiver[0], receiver[1]) - server2 = util.rpc_client(sender[0], sender[1]) - - tcpformat = '{0:>15} {1:>15} {2:>15}' - print("TCP test from %s:%u to %s:%u (full speed)" % (sender[0], sender[1], - receiver[0], receiver[1])) - print(tcpformat.format("Snt Bytes", "Rcv Bytes", "Bandwidth")) - - listen_handle = NO_HANDLE - send_handle = NO_HANDLE - try: - listen_handle = server1.create_tcp_listener(receiver[3]) - if listen_handle == NO_HANDLE: - print("Server was unable to open TCP listening socket on port" - " %u. Try to restart the server.\n" % receiver[3]) - return - send_handle = server2.create_tcp_sender(util.ip_from_cidr(receiver[2]), - receiver[3], duration) - - time.sleep(duration + 1) - - rcv_bytes = int(server1.get_tcp_listener_results(listen_handle)) - snt_bytes = int(server2.get_tcp_sender_results(send_handle)) - - bwidth = rcv_bytes / duration - - print(tcpformat.format(snt_bytes, rcv_bytes, - util.bandwidth_to_string(bwidth))) - finally: - if listen_handle != NO_HANDLE: - server1.close_tcp_listener(listen_handle) - if send_handle != NO_HANDLE: - server2.close_tcp_sender(send_handle) - print("\n") - - -def do_l3_tests(node1, node2, bandwidth, duration, ps, type): - """ - Do L3 tunneling tests. Each node is given as 4 tuple - physical - interface IP, control port, test IP and test port. - """ - server1 = util.rpc_client(node1[0], node1[1]) - server2 = util.rpc_client(node2[0], node2[1]) - servers_with_bridges = [] - try: - server1.create_bridge(DEFAULT_TEST_BRIDGE) - servers_with_bridges.append(server1) - server2.create_bridge(DEFAULT_TEST_BRIDGE) - servers_with_bridges.append(server2) - - server1.interface_up(DEFAULT_TEST_BRIDGE) - server2.interface_up(DEFAULT_TEST_BRIDGE) - - server1.interface_assign_ip(DEFAULT_TEST_BRIDGE, node1[2], None) - server2.interface_assign_ip(DEFAULT_TEST_BRIDGE, node2[2], None) - - server1.add_port_to_bridge(DEFAULT_TEST_BRIDGE, DEFAULT_TEST_TUN) - server2.add_port_to_bridge(DEFAULT_TEST_BRIDGE, DEFAULT_TEST_TUN) - - server1.ovs_vsctl_set("Interface", DEFAULT_TEST_TUN, "type", - None, type) - server2.ovs_vsctl_set("Interface", DEFAULT_TEST_TUN, "type", - None, type) - server1.ovs_vsctl_set("Interface", DEFAULT_TEST_TUN, "options", - "remote_ip", node2[0]) - server2.ovs_vsctl_set("Interface", DEFAULT_TEST_TUN, "options", - "remote_ip", node1[0]) - - do_udp_tests(node1, node2, bandwidth, duration, ps) - do_udp_tests(node2, node1, bandwidth, duration, ps) - do_tcp_tests(node1, node2, duration) - do_tcp_tests(node2, node1, duration) - - finally: - for server in servers_with_bridges: - server.del_bridge(DEFAULT_TEST_BRIDGE) - - -def do_vlan_tests(node1, node2, bandwidth, duration, ps, tag): - """ - Do VLAN tests between node1 and node2. Each node is given - as 4 tuple - physical interface IP, control port, test IP and - test port. - """ - server1 = util.rpc_client(node1[0], node1[1]) - server2 = util.rpc_client(node2[0], node2[1]) - - br_name1 = None - br_name2 = None - - servers_with_test_ports = [] - - try: - interface_node1 = server1.get_interface(node1[0]) - interface_node2 = server2.get_interface(node2[0]) - - if server1.is_ovs_bridge(interface_node1): - br_name1 = interface_node1 - else: - br_name1 = DEFAULT_TEST_BRIDGE - server1.create_test_bridge(br_name1, interface_node1) - - if server2.is_ovs_bridge(interface_node2): - br_name2 = interface_node2 - else: - br_name2 = DEFAULT_TEST_BRIDGE - server2.create_test_bridge(br_name2, interface_node2) - - server1.add_port_to_bridge(br_name1, DEFAULT_TEST_PORT) - servers_with_test_ports.append(server1) - server2.add_port_to_bridge(br_name2, DEFAULT_TEST_PORT) - servers_with_test_ports.append(server2) - - server1.ovs_vsctl_set("Port", DEFAULT_TEST_PORT, "tag", None, tag) - server2.ovs_vsctl_set("Port", DEFAULT_TEST_PORT, "tag", None, tag) - - server1.ovs_vsctl_set("Interface", DEFAULT_TEST_PORT, "type", None, - "internal") - server2.ovs_vsctl_set("Interface", DEFAULT_TEST_PORT, "type", None, - "internal") - - server1.interface_assign_ip(DEFAULT_TEST_PORT, node1[2], None) - server2.interface_assign_ip(DEFAULT_TEST_PORT, node2[2], None) - - server1.interface_up(DEFAULT_TEST_PORT) - server2.interface_up(DEFAULT_TEST_PORT) - - do_udp_tests(node1, node2, bandwidth, duration, ps) - do_udp_tests(node2, node1, bandwidth, duration, ps) - do_tcp_tests(node1, node2, duration) - do_tcp_tests(node2, node1, duration) - - finally: - for server in servers_with_test_ports: - server.del_port_from_bridge(DEFAULT_TEST_PORT) - if br_name1 == DEFAULT_TEST_BRIDGE: - server1.del_test_bridge(br_name1, interface_node1) - if br_name2 == DEFAULT_TEST_BRIDGE: - server2.del_test_bridge(br_name2, interface_node2) - - -def do_direct_tests(node1, node2, bandwidth, duration, ps): - """ - Do tests between outer IPs without involving Open vSwitch. Each - node is given as 4 tuple - physical interface IP, control port, - test IP and test port. Direct tests will use physical interface - IP as the test IP address. - """ - n1 = (node1[0], node1[1], node1[0], node1[3]) - n2 = (node2[0], node2[1], node2[0], node2[3]) - - do_udp_tests(n1, n2, bandwidth, duration, ps) - do_udp_tests(n2, n1, bandwidth, duration, ps) - do_tcp_tests(n1, n2, duration) - do_tcp_tests(n2, n1, duration) - - -def configure_l3(conf, tunnel_mode): - """ - This function creates a temporary test bridge and adds an L3 tunnel. - """ - s = util.start_local_server(conf[1][1]) - server = util.rpc_client("127.0.0.1", conf[1][1]) - server.create_bridge(DEFAULT_TEST_BRIDGE) - server.add_port_to_bridge(DEFAULT_TEST_BRIDGE, DEFAULT_TEST_PORT) - server.interface_up(DEFAULT_TEST_BRIDGE) - server.interface_assign_ip(DEFAULT_TEST_BRIDGE, conf[1][0], - None) - server.ovs_vsctl_set("Interface", DEFAULT_TEST_PORT, "type", - None, tunnel_mode) - server.ovs_vsctl_set("Interface", DEFAULT_TEST_PORT, "options", - "remote_ip", conf[0]) - return s diff --git a/python/ovstest/udp.py b/python/ovstest/udp.py deleted file mode 100644 index acd28d575..000000000 --- a/python/ovstest/udp.py +++ /dev/null @@ -1,85 +0,0 @@ -# Copyright (c) 2011, 2012 Nicira, Inc. -# -# 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. - -""" -ovsudp contains listener and sender classes for UDP protocol -""" - -import array -import struct -import time - -from twisted.internet.protocol import DatagramProtocol -from twisted.internet.task import LoopingCall - - -class UdpListener(DatagramProtocol): - """ - Class that will listen for incoming UDP packets - """ - def __init__(self): - self.stats = [] - - def datagramReceived(self, data, _1_2): - """This function is called each time datagram is received""" - try: - self.stats.append(struct.unpack_from("Q", data, 0)) - except struct.error: - pass # ignore packets that are less than 8 bytes of size - - def getResults(self): - """Returns number of packets that were actually received""" - return len(self.stats) - - -class UdpSender(DatagramProtocol): - """ - Class that will send UDP packets to UDP Listener - """ - def __init__(self, host, count, size, duration): - # LoopingCall does not know whether UDP socket is actually writable - self.looper = None - self.host = host - self.count = count - self.duration = duration - self.start = time.time() - self.sent = 0 - self.data = array.array('c', 'X' * size) - - def startProtocol(self): - self.looper = LoopingCall(self.sendData) - period = self.duration / float(self.count) - self.looper.start(period, now=False) - - def stopProtocol(self): - if (self.looper is not None): - self.looper.stop() - self.looper = None - - def datagramReceived(self, data, host_port): - pass - - def sendData(self): - """This function is called from LoopingCall""" - if self.start + self.duration < time.time(): - self.looper.stop() - self.looper = None - - self.sent += 1 - struct.pack_into('Q', self.data, 0, self.sent) - self.transport.write(self.data, self.host) - - def getResults(self): - """Returns number of packets that were sent""" - return self.sent diff --git a/python/ovstest/util.py b/python/ovstest/util.py deleted file mode 100644 index 270d6a037..000000000 --- a/python/ovstest/util.py +++ /dev/null @@ -1,249 +0,0 @@ -# Copyright (c) 2011, 2012, 2017 Nicira, Inc. -# -# 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. - -""" -util module contains some helper function -""" -import array -import fcntl - -import os -import re -import select -import signal -import socket -import struct -import subprocess - -import xmlrpc.client - - -def str_ip(ip_address): - """ - Converts an IP address from binary format to a string. - """ - (x1, x2, x3, x4) = struct.unpack("BBBB", ip_address) - return ("%u.%u.%u.%u") % (x1, x2, x3, x4) - - -def get_interface_mtu(iface): - """ - Returns MTU of the given interface. - """ - s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) - indata = iface + ('\0' * (32 - len(iface))) - try: - outdata = fcntl.ioctl(s.fileno(), 0x8921, indata) # socket.SIOCGIFMTU - mtu = struct.unpack("16si12x", outdata)[1] - except: - return 0 - - return mtu - - -def get_interface(address): - """ - Finds first interface that has given address - """ - bytes = 256 * 32 - s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) - names = array.array('B', '\0' * bytes) - outbytes = struct.unpack('iL', fcntl.ioctl( - s.fileno(), - 0x8912, # SIOCGIFCONF - struct.pack('iL', bytes, names.buffer_info()[0]) - ))[0] - namestr = names.tostring() - - for i in range(0, outbytes, 40): - name = namestr[i:i + 16].split('\0', 1)[0] - if address == str_ip(namestr[i + 20:i + 24]): - return name - return None # did not find interface we were looking for - - -def uname(): - os_info = os.uname() - return os_info[2] # return only the kernel version number - - -def start_process(args): - try: - p = subprocess.Popen(args, - stdin=subprocess.PIPE, - stdout=subprocess.PIPE, - stderr=subprocess.PIPE) - out, err = p.communicate() - return (p.returncode, out, err) - except OSError: - return (-1, None, None) - - -def get_driver(iface): - ret, out, _err = start_process(["ethtool", "-i", iface]) - if ret == 0: - lines = out.splitlines() - driver = "%s(%s)" % (lines[0], lines[1]) # driver name + version - else: - driver = None - return driver - - -def interface_up(iface): - """ - This function brings given iface up. - """ - ret, _out, _err = start_process(["ip", "link", "set", iface, "up"]) - return ret - - -def interface_assign_ip(iface, ip_addr, mask): - """ - This function adds an IP address to an interface. If mask is None - then a mask will be selected automatically. In case of success - this function returns 0. - """ - interface_ip_op(iface, ip_addr, mask, "add") - - -def interface_remove_ip(iface, ip_addr, mask): - """ - This function removes an IP address from an interface. If mask is - None then a mask will be selected automatically. In case of - success this function returns 0. - """ - interface_ip_op(iface, ip_addr, mask, "del") - - -def interface_ip_op(iface, ip_addr, mask, op): - if mask is not None: - arg = "%s/%s" % (ip_addr, mask) - elif '/' in ip_addr: - arg = ip_addr - else: - (x1, x2, x3, x4) = struct.unpack("BBBB", socket.inet_aton(ip_addr)) - if x1 < 128: - arg = "%s/8" % ip_addr - elif x1 < 192: - arg = "%s/16" % ip_addr - else: - arg = "%s/24" % ip_addr - ret, _out, _err = start_process(["ip", "addr", op, arg, "dev", iface]) - return ret - - -def interface_get_ip(iface): - """ - This function returns tuple - ip and mask that was assigned to the - interface. - """ - args = ["ip", "addr", "show", iface] - ret, out, _err = start_process(args) - - if ret == 0: - ip = re.search(r'inet (\S+)/(\S+)', out) - if ip is not None: - return (ip.group(1), ip.group(2)) - else: - return ret - - -def move_routes(iface1, iface2): - """ - This function moves routes from iface1 to iface2. - """ - args = ["ip", "route", "show", "dev", iface1] - ret, out, _err = start_process(args) - if ret == 0: - for route in out.splitlines(): - args = ["ip", "route", "replace", "dev", iface2] + route.split() - start_process(args) - - -def get_interface_from_routing_decision(ip): - """ - This function returns the interface through which the given ip address - is reachable. - """ - args = ["ip", "route", "get", ip] - ret, out, _err = start_process(args) - if ret == 0: - iface = re.search(r'dev (\S+)', out) - if iface: - return iface.group(1) - return None - - -def rpc_client(ip, port): - return xmlrpc.client.Server("http://%s:%u/" % (ip, port), allow_none=True) - - -def sigint_intercept(): - """ - Intercept SIGINT from child (the local ovs-test server process). - """ - signal.signal(signal.SIGINT, signal.SIG_IGN) - - -def start_local_server(port): - """ - This function spawns an ovs-test server that listens on specified port - and blocks till the spawned ovs-test server is ready to accept XML RPC - connections. - """ - p = subprocess.Popen(["ovs-test", "-s", str(port)], - stdout=subprocess.PIPE, stderr=subprocess.PIPE, - preexec_fn=sigint_intercept) - fcntl.fcntl(p.stdout.fileno(), fcntl.F_SETFL, - fcntl.fcntl(p.stdout.fileno(), fcntl.F_GETFL) | os.O_NONBLOCK) - - while p.poll() is None: - fd = select.select([p.stdout.fileno()], [], [])[0] - if fd: - out = p.stdout.readline() - if out.startswith("Starting RPC server"): - break - if p.poll() is not None: - raise RuntimeError("Couldn't start local instance of ovs-test server") - return p - - -def get_datagram_sizes(mtu1, mtu2): - """ - This function calculates all the "interesting" datagram sizes so that - we test both - receive and send side with different packets sizes. - """ - s1 = set([8, mtu1 - 100, mtu1 - 28, mtu1]) - s2 = set([8, mtu2 - 100, mtu2 - 28, mtu2]) - return sorted(s1.union(s2)) - - -def ip_from_cidr(string): - """ - This function removes the netmask (if present) from the given string and - returns the IP address. - """ - token = string.split("/") - return token[0] - - -def bandwidth_to_string(bwidth): - """Convert bandwidth from long to string and add units.""" - bwidth = bwidth * 8 # Convert back to bits/second - if bwidth >= 10000000: - return str(int(bwidth / 1000000)) + "Mbps" - elif bwidth > 10000: - return str(int(bwidth / 1000)) + "Kbps" - else: - return str(int(bwidth)) + "bps" diff --git a/python/ovstest/vswitch.py b/python/ovstest/vswitch.py deleted file mode 100644 index 45c9587ee..000000000 --- a/python/ovstest/vswitch.py +++ /dev/null @@ -1,107 +0,0 @@ -# Copyright (c) 2012 Nicira, Inc. -# -# 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. - -""" -vswitch module allows its callers to interact with OVS DB. -""" -from . import util - - -def ovs_vsctl_add_bridge(bridge): - """ - This function creates an OVS bridge. - """ - ret, _out, _err = util.start_process(["ovs-vsctl", "add-br", bridge]) - return ret - - -def ovs_vsctl_del_bridge(bridge): - """ - This function deletes the OVS bridge. - """ - ret, _out, _err = util.start_process(["ovs-vsctl", "del-br", bridge]) - return ret - - -def ovs_vsctl_del_pbridge(bridge, iface): - """ - This function deletes the OVS bridge and assigns the bridge IP address - back to the iface. - """ - (ip_addr, mask) = util.interface_get_ip(bridge) - util.interface_assign_ip(iface, ip_addr, mask) - util.interface_up(iface) - util.move_routes(bridge, iface) - return ovs_vsctl_del_bridge(bridge) - - -def ovs_vsctl_is_ovs_bridge(bridge): - """ - This function verifies whether given port is an OVS bridge. If it is an - OVS bridge then it will return True. - """ - ret, _out, _err = util.start_process(["ovs-vsctl", "br-exists", bridge]) - return ret == 0 - - -def ovs_vsctl_add_port_to_bridge(bridge, iface): - """ - This function adds given interface to the bridge. - """ - ret, _out, _err = util.start_process(["ovs-vsctl", "add-port", bridge, - iface]) - return ret - - -def ovs_vsctl_del_port_from_bridge(port): - """ - This function removes given port from a OVS bridge. - """ - ret, _out, _err = util.start_process(["ovs-vsctl", "del-port", port]) - return ret - - -def ovs_vsctl_set(table, record, column, key, value): - """ - This function allows to alter the OVS database. If column is a map, then - caller should also set the key, otherwise the key should be left as an - empty string. - """ - if key is None: - index = column - else: - index = "%s:%s" % (column, key) - index_value = "%s=%s" % (index, value) - ret, _out, _err = util.start_process(["ovs-vsctl", "set", table, record, - index_value]) - return ret - - -def ovs_get_physical_interface(bridge): - """ - This function tries to figure out which is the physical interface that - belongs to the bridge. If there are multiple physical interfaces assigned - to this bridge then it will return the first match. - """ - ret, out, _err = util.start_process(["ovs-vsctl", "list-ifaces", bridge]) - - if ret == 0: - ifaces = out.splitlines() - for iface in ifaces: - ret, out, _err = util.start_process(["ovs-vsctl", "get", - "Interface", iface, "type"]) - if ret == 0: - if ('""' in out) or ('system' in out): - return iface # this should be the physical interface - return None diff --git a/rhel/openvswitch-fedora.spec.in b/rhel/openvswitch-fedora.spec.in index 88bb734ad..72bd676e8 100644 --- a/rhel/openvswitch-fedora.spec.in +++ b/rhel/openvswitch-fedora.spec.in @@ -418,20 +418,15 @@ fi %{python3_sitelib}/ovs %files test -%{_bindir}/ovs-test %{_bindir}/ovs-vlan-test -%{_bindir}/ovs-l3ping %{_bindir}/ovs-pcap %{_bindir}/ovs-tcpdump %{_bindir}/ovs-tcpundump %{_datadir}/openvswitch/scripts/usdt/* -%{_mandir}/man8/ovs-test.8* %{_mandir}/man8/ovs-vlan-test.8* -%{_mandir}/man8/ovs-l3ping.8* %{_mandir}/man1/ovs-pcap.1* %{_mandir}/man8/ovs-tcpdump.8* %{_mandir}/man1/ovs-tcpundump.1* -%{python3_sitelib}/ovstest %files devel %{_libdir}/lib*.so diff --git a/rhel/openvswitch.spec.in b/rhel/openvswitch.spec.in index 6212729bc..2879998a9 100644 --- a/rhel/openvswitch.spec.in +++ b/rhel/openvswitch.spec.in @@ -96,11 +96,7 @@ install -p -m 644 -D selinux/openvswitch-custom.pp \ # Get rid of stuff we don't want to make RPM happy. rm \ $RPM_BUILD_ROOT/usr/bin/ovs-testcontroller \ - $RPM_BUILD_ROOT/usr/share/man/man8/ovs-testcontroller.8 \ - $RPM_BUILD_ROOT/usr/bin/ovs-test \ - $RPM_BUILD_ROOT/usr/bin/ovs-l3ping \ - $RPM_BUILD_ROOT/usr/share/man/man8/ovs-test.8 \ - $RPM_BUILD_ROOT/usr/share/man/man8/ovs-l3ping.8 + $RPM_BUILD_ROOT/usr/share/man/man8/ovs-testcontroller.8 (cd "$RPM_BUILD_ROOT" && rm -rf usr/%{_lib}/*.la) (cd "$RPM_BUILD_ROOT" && rm -rf usr/include) diff --git a/utilities/.gitignore b/utilities/.gitignore index 035ff386d..3f140a744 100644 --- a/utilities/.gitignore +++ b/utilities/.gitignore @@ -14,8 +14,6 @@ /ovs-dpctl-top /ovs-dpctl-top.8 /ovs-kmod-ctl -/ovs-l3ping -/ovs-l3ping.8 /ovs-lib /ovs-ofctl /ovs-ofctl.8 @@ -24,8 +22,6 @@ /ovs-pki /ovs-pki-cgi /ovs-pki.8 -/ovs-test -/ovs-test.8 /ovs-tcpdump /ovs-tcpdump.8 /ovs-tcpundump diff --git a/utilities/automake.mk b/utilities/automake.mk index 45fcdff2c..e83c283b8 100644 --- a/utilities/automake.mk +++ b/utilities/automake.mk @@ -10,8 +10,6 @@ bin_SCRIPTS += utilities/ovs-docker \ utilities/ovs-tcpdump \ utilities/ovs-tcpundump \ utilities/ovs-dpctl-top \ - utilities/ovs-l3ping \ - utilities/ovs-test \ utilities/ovs-vlan-test scripts_SCRIPTS += \ utilities/ovs-check-dead-ifs \ @@ -52,7 +50,6 @@ EXTRA_DIST += \ utilities/ovs-docker \ utilities/ovs-dpctl-top.in \ utilities/ovs-kmod-ctl.in \ - utilities/ovs-l3ping.in \ utilities/ovs-lib.in \ utilities/ovs-pcap.in \ utilities/ovs-pipegen.py \ @@ -60,7 +57,6 @@ EXTRA_DIST += \ utilities/ovs-save \ utilities/ovs-tcpdump.in \ utilities/ovs-tcpundump.in \ - utilities/ovs-test.in \ utilities/ovs-vlan-test.in \ utilities/ovs-vsctl-bashcomp.bash \ utilities/checkpatch.py \ @@ -97,7 +93,6 @@ CLEANFILES += \ utilities/ovs-dpctl-top \ utilities/ovs-dpctl-top.8 \ utilities/ovs-kmod-ctl \ - utilities/ovs-l3ping \ utilities/ovs-lib \ utilities/ovs-ofctl.8 \ utilities/ovs-pcap \ @@ -106,7 +101,6 @@ CLEANFILES += \ utilities/ovs-sim \ utilities/ovs-tcpdump \ utilities/ovs-tcpundump \ - utilities/ovs-test \ utilities/ovs-vlan-test \ utilities/ovs-vsctl.8 diff --git a/utilities/ovs-l3ping.in b/utilities/ovs-l3ping.in deleted file mode 100644 index 1ece06457..000000000 --- a/utilities/ovs-l3ping.in +++ /dev/null @@ -1,76 +0,0 @@ -#! @PYTHON3@ -# -# 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. - -""" -ovs L3 ping utility allows to do tests between two remote hosts without -opening holes in the firewall for the XML RPC control connection. This is -achieved by tunneling the control connection inside the tunnel itself. -""" - -import socket -import xmlrpc.client - -import ovstest.args as args -import ovstest.tests as tests -import ovstest.util as util - - -def get_packet_sizes(me, he, remote_ip): - """ - This function retrieves MTUs from both hosts and returns a list of - packet sizes, that are more likely to uncover possible configuration - issues. - """ - mtu_node1 = 1500 - mtu_node2 = 1500 - server1 = util.rpc_client(me[0], me[1]) - server2 = util.rpc_client(he[0], he[1]) - iface1 = server2.get_interface(remote_ip) - iface2 = server1.get_interface_from_routing_decision(remote_ip) - if iface1: - mtu_node1 = server2.get_interface_mtu(iface1) - if iface2: - mtu_node2 = server1.get_interface_mtu(iface2) - return util.get_datagram_sizes(mtu_node1, mtu_node2) - - -if __name__ == '__main__': - local_server = None - try: - args = args.l3_initialize_args() - tunnel_mode = args.tunnelMode - if args.server is not None: # Start in server mode - local_server = tests.configure_l3(args.server, tunnel_mode) - local_server.wait() - elif args.client is not None: # Run in client mode - bandwidth = args.targetBandwidth - interval = args.testInterval - me = (util.ip_from_cidr(args.client[1][0]), args.client[1][1], - args.client[1][0], args.client[1][2]) - he = (args.client[2][0], args.client[2][1], - args.client[2][0], args.client[2][2]) - local_server = tests. configure_l3(args.client, tunnel_mode) - ps = get_packet_sizes(me, he, args.client[0]) - tests.do_direct_tests(me, he, bandwidth, interval, ps) - except KeyboardInterrupt: - print("Terminating") - except xmlrpc.client.Fault: - print("Couldn't contact peer") - except socket.error: - print("Couldn't contact peer") - except xmlrpc.client.ProtocolError: - print("XMLRPC control channel was abruptly terminated") - finally: - if local_server is not None: - local_server.terminate() diff --git a/utilities/ovs-test.in b/utilities/ovs-test.in deleted file mode 100644 index eb712ffe8..000000000 --- a/utilities/ovs-test.in +++ /dev/null @@ -1,141 +0,0 @@ -#! @PYTHON3@ -# -# 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. - -""" -ovs test utility that allows to do tests between remote hosts -""" - -import fcntl -import math -import os -import select -import signal -import socket -import subprocess -import sys -import time -import xmlrpclib - -import argparse -import twisted - -import ovstest.args as args -import ovstest.rpcserver as rpcserver -import ovstest.tests as tests -import ovstest.util as util - -DEFAULT_TEST_BRIDGE = "ovstestbr0" -DEFAULT_TEST_PORT = "ovstestport0" -DEFAULT_TEST_TUN = "ovstestport1" - - -def collect_information(node): - """Print information about hosts that will do testing""" - print "Node %s:%u " % (node[0], node[1]) - server = util.rpc_client(node[0], node[1]) - interface_name = server.get_interface(node[0]) - phys_iface = None - uname = server.uname() - mtu = 1500 - - if not interface_name: - print ("Could not find interface that has %s IP address." - "Make sure that you specified correct Outer IP." % (node[0])) - else: - if server.is_ovs_bridge(interface_name): - phys_iface = server.get_iface_from_bridge(interface_name) - else: - phys_iface = interface_name - - if phys_iface: - driver = server.get_driver(phys_iface) - mtu = server.get_interface_mtu(phys_iface) - - print "Will be using %s (%s) with MTU %u" % (phys_iface, node[0], - mtu) - if not driver: - print "Unable to get driver information from ethtool." - else: - print "On this host %s has %s." % (phys_iface, driver) - - if not uname: - print "Unable to retrieve kernel information. Is this Linux?" - else: - print "Running kernel %s." % uname - print "\n" - - return mtu - - -if __name__ == '__main__': - local_server = None - try: - ovs_args = args.ovs_initialize_args() - - if ovs_args.port is not None: # Start in pure server mode - rpcserver.start_rpc_server(ovs_args.port) - - elif ovs_args.servers is not None: # Run in client mode - node1 = ovs_args.servers[0] - node2 = ovs_args.servers[1] - - # Verify whether client will need to spawn a local instance of - # ovs-test server by looking at the first OuterIP. if it is a - # 127.0.0.1 then spawn local ovs-test server. - if node1[0] == "127.0.0.1": - local_server = util.start_local_server(node1[1]) - # We must determine the IP address that local ovs-test server - # will use: - me = util.rpc_client(node1[0], node1[1]) - my_ip = me.get_my_address_from(node2[0], node2[1]) - node1 = (my_ip, node1[1], node1[2], node1[3]) - - mtu_node2 = collect_information(node2) - mtu_node1 = collect_information(node1) - - bandwidth = ovs_args.targetBandwidth - interval = ovs_args.testInterval - ps = util.get_datagram_sizes(mtu_node1, mtu_node2) - - direct = ovs_args.direct - vlan_tag = ovs_args.vlanTag - tunnel_modes = ovs_args.tunnelModes - - if direct is not None: - print "Performing direct tests" - tests.do_direct_tests(node2, node1, bandwidth, interval, ps) - - if vlan_tag is not None: - print "Performing VLAN tests" - tests.do_vlan_tests(node2, node1, bandwidth, interval, ps, - vlan_tag) - - for tmode in tunnel_modes: - print "Performing", tmode, "tests" - tests.do_l3_tests(node2, node1, bandwidth, interval, ps, - tmode) - - except KeyboardInterrupt: - pass - except xmlrpclib.Fault: - print "Couldn't establish XMLRPC control channel" - except socket.error: - print "Couldn't establish XMLRPC control channel" - except xmlrpclib.ProtocolError: - print "XMLRPC control channel was abruptly terminated" - except twisted.internet.error.CannotListenError: - print "Couldn't start XMLRPC server on port %u" % ovs_args.port - finally: - if local_server is not None: - local_server.terminate() -- 2.54.0 _______________________________________________ dev mailing list [email protected] https://mail.openvswitch.org/mailman/listinfo/ovs-dev
