[ovs-dev] [PATCH] ovs-l3ping: A new test utility that allows to detect L3 tunneling issues

Reid Price reid at nicira.com
Fri Jun 29 00:06:05 UTC 2012


Looks good from a quick read-through, skimmed the documentation
additions, a few minor comments inline.

  -Reid

On Thu, Jun 28, 2012 at 4:02 PM, Ansis Atteka <aatteka at nicira.com> wrote:

> ovs-l3ping is similar to ovs-test, but the main difference
> is that it does not require administrator to open firewall
> holes for the XML/RPC control connection. This is achieved
> by encapsulating the Control Connection over the L3 tunnel
> itself.
>
> This tool is not intended as a replacement for ovs-test,
> because ovs-test covers much broader set of test cases.
>
> Sample usage:
> Node1: ovs-l3ping -s 192.168.122.236,10.1.1.1 -t gre
> Node2: ovs-l3ping -c 192.168.122.220,10.1.1.2,10.1.1.1 -t gre
>
> Issue#11791
> Signed-off-by: Ansis Atteka <aatteka at nicira.com>
> ---
>  NEWS                              |    5 +
>  debian/openvswitch-test.install   |    1 +
>  debian/openvswitch-test.manpages  |    1 +
>  manpages.mk                       |    8 ++
>  python/automake.mk                |    1 +
>  python/ovstest/args.py            |   74 ++++++++++
>  python/ovstest/rpcserver.py       |    6 +
>  python/ovstest/tests.py           |  230 +++++++++++++++++++++++++++++
>  python/ovstest/util.py            |   82 +++++++++++
>  rhel/openvswitch.spec.in          |    2 +
>  utilities/.gitignore              |    2 +
>  utilities/automake.mk             |    6 +
>  utilities/ovs-l3ping.8.in         |  108 ++++++++++++++
>  utilities/ovs-l3ping.in           |   76 ++++++++++
>  utilities/ovs-test.in             |  286
> ++-----------------------------------
>  xenserver/openvswitch-xen.spec.in |    6 +-
>  16 files changed, 617 insertions(+), 277 deletions(-)
>  create mode 100644 python/ovstest/tests.py
>  create mode 100644 utilities/ovs-l3ping.8.in
>  create mode 100644 utilities/ovs-l3ping.in
>
> diff --git a/NEWS b/NEWS
> index f0b2490..d71daf7 100644
> --- a/NEWS
> +++ b/NEWS
> @@ -1,6 +1,11 @@
>  post-v1.7.0
>  ------------------------
>     - New FAQ.  Please send updates and additions!
> +    - ovs-l3ping:
> +        - A new test utility that can create L3 tunnel between two Open
> +          vSwitches and detect connectivity issues.  This utility does
> +          not require administrator to open firewall hole for the XML/RPC
> +          control channel.
>     - ovs-ofctl:
>         - "mod-port" command can now control all OpenFlow config flags.
>     - OpenFlow:
> diff --git a/debian/openvswitch-test.install
> b/debian/openvswitch-test.install
> index a36c828..2b0f8de 100644
> --- a/debian/openvswitch-test.install
> +++ b/debian/openvswitch-test.install
> @@ -1,2 +1,3 @@
>  usr/share/openvswitch/python/ovstest usr/lib/python2.6/dist-packages/
>  usr/bin/ovs-test
> +usr/bin/ovs-l3ping
> \ No newline at end of file
> diff --git a/debian/openvswitch-test.manpages
> b/debian/openvswitch-test.manpages
> index 683c978..1a7f6d4 100644
> --- a/debian/openvswitch-test.manpages
> +++ b/debian/openvswitch-test.manpages
> @@ -1 +1,2 @@
>  _debian/utilities/ovs-test.8
> +_debian/utilities/ovs-l3ping.8
> diff --git a/manpages.mk b/manpages.mk
> index 1773263..f391fdf 100644
> --- a/manpages.mk
> +++ b/manpages.mk
> @@ -120,6 +120,14 @@ utilities/ovs-dpctl.8.in:
>  lib/common.man:
>  lib/vlog.man:
>
> +utilities/ovs-l3ping.8: \
> +       utilities/ovs-l3ping.8.in \
> +       lib/common-syn.man \
> +       lib/common.man
> +utilities/ovs-l3ping.8.in:
> +lib/common-syn.man:
> +lib/common.man:
> +
>  utilities/ovs-ofctl.8: \
>        utilities/ovs-ofctl.8.in \
>        lib/common.man \
> diff --git a/python/automake.mk b/python/automake.mk
> index 96869e3..b656f08 100644
> --- a/python/automake.mk
> +++ b/python/automake.mk
> @@ -3,6 +3,7 @@ ovstest_pyfiles = \
>        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
> diff --git a/python/ovstest/args.py b/python/ovstest/args.py
> index 8e23a89..1dd97c1 100644
> --- a/python/ovstest/args.py
> +++ b/python/ovstest/args.py
> @@ -78,6 +78,23 @@ def ip_optional_port(string, default_port, ip_callback):
>                                          "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("IP address from optional ports "
> +                                         "must be colon-separated")
> +
> +
>  def vlan_tag(string):
>     """
>     This function verifies whether given string is a correct VLAN tag.
> @@ -154,6 +171,29 @@ def tunnel_types(string):
>     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.
> +    """
> +    remote_ip, me, he = string.split(',')
> +    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.
> +    """
> +    remote_ip, me = string.split(',')
> +    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.
> @@ -197,3 +237,37 @@ def ovs_initialize_args():
>                 '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
> index 82bec3b..5c92014 100644
> --- a/python/ovstest/rpcserver.py
> +++ b/python/ovstest/rpcserver.py
> @@ -343,6 +343,12 @@ class TestArena(xmlrpc.XMLRPC):
>         """
>         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):
>     """
> diff --git a/python/ovstest/tests.py b/python/ovstest/tests.py
> new file mode 100644
> index 0000000..866c207
> --- /dev/null
> +++ b/python/ovstest/tests.py
> @@ -0,0 +1,230 @@
> +import math
> +import time
> +
> +import ovstest.util as util
> +
> +DEFAULT_TEST_BRIDGE = "ovstestbr0"
> +DEFAULT_TEST_PORT = "ovstestport0"
> +DEFAULT_TEST_TUN = "ovstestport1"
> +
> +
> +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 = -1
> +        send_handle = -1
>
It seems like a constant for NO_HANDLE might be friendly throughout, fine
as-is.


> +        try:
> +            packetcnt = (tbwidth * duration) / size
> +
> +            listen_handle = server1.create_udp_listener(receiver[3])
> +            if listen_handle == -1:
> +                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 != -1:
> +                server1.close_udp_listener(listen_handle)
> +            if send_handle != -1:
> +                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 = -1
> +    send_handle = -1
> +    try:
> +        listen_handle = server1.create_tcp_listener(receiver[3])
> +        if listen_handle == -1:
> +            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 = long(server1.get_tcp_listener_results(listen_handle))
> +        snt_bytes = long(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 != -1:
> +            server1.close_tcp_listener(listen_handle)
> +        if send_handle != -1:
> +            server2.close_tcp_sender(send_handle)
> +    print "\n"
> +
> +
> +def do_l3_tests(node1, node2, bandwidth, duration, ps, type):
> +    """
> +    Do L3 tunneling tests.
> +    """
> +    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.

+    """
>
Marking what node1 and node2 are might be useful in these functions, it's
not obvious what the indices are supposed to represent in passing.

+    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
> +    """
> +    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 L3 tunnel.
>
s/adds L3/adds an L3/


> +    """
> +    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/util.py b/python/ovstest/util.py
> index ee2a878..138a8f4 100644
> --- a/python/ovstest/util.py
> +++ b/python/ovstest/util.py
> @@ -19,11 +19,15 @@ import array
>  import exceptions
>  import fcntl
>  import os
> +import select
>  import socket
>  import struct
> +import signal
>  import subprocess
>


>  import re
>
> +import xmlrpclib
> +
>
You can drop the newline between re and xmlrpclib


>
>  def str_ip(ip_address):
>     """
> @@ -147,3 +151,81 @@ def move_routes(iface1, iface2):
>         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 xmlrpclib.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)
>
No spaces around = in kwargs


> +    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/rhel/openvswitch.spec.in b/rhel/openvswitch.spec.in
> index 54442fb..de22c86 100644
> --- a/rhel/openvswitch.spec.in
> +++ b/rhel/openvswitch.spec.in
> @@ -59,7 +59,9 @@ rm \
>     $RPM_BUILD_ROOT/usr/bin/ovs-controller \
>     $RPM_BUILD_ROOT/usr/share/man/man8/ovs-controller.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/sbin/ovs-vlan-bug-workaround \
>     $RPM_BUILD_ROOT/usr/share/man/man8/ovs-vlan-bug-workaround.8
>
> diff --git a/utilities/.gitignore b/utilities/.gitignore
> index 90f47ff..4f96a4f 100644
> --- a/utilities/.gitignore
> +++ b/utilities/.gitignore
> @@ -13,6 +13,8 @@
>  /ovs-ctl
>  /ovs-dpctl
>  /ovs-dpctl.8
> +/ovs-l3ping
> +/ovs-l3ping.8
>  /ovs-lib
>  /ovs-ofctl
>  /ovs-ofctl.8
> diff --git a/utilities/automake.mk b/utilities/automake.mk
> index f3da1b1..04a7fdc 100644
> --- a/utilities/automake.mk
> +++ b/utilities/automake.mk
> @@ -7,6 +7,7 @@ bin_PROGRAMS += \
>  bin_SCRIPTS += utilities/ovs-pki utilities/ovs-vsctl
> utilities/ovs-parse-leaks
>  if HAVE_PYTHON
>  bin_SCRIPTS += \
> +       utilities/ovs-l3ping \
>        utilities/ovs-pcap \
>        utilities/ovs-tcpundump \
>        utilities/ovs-test \
> @@ -22,6 +23,7 @@ scripts_DATA += utilities/ovs-lib
>  EXTRA_DIST += \
>        utilities/ovs-check-dead-ifs.in \
>        utilities/ovs-ctl.in \
> +       utilities/ovs-l3ping.in \
>        utilities/ovs-lib.in \
>        utilities/ovs-parse-leaks.in \
>        utilities/ovs-pcap.in \
> @@ -37,6 +39,7 @@ MAN_ROOTS += \
>        utilities/ovs-controller.8.in \
>        utilities/ovs-ctl.8 \
>        utilities/ovs-dpctl.8.in \
> +       utilities/ovs-l3ping.8.in \
>        utilities/ovs-ofctl.8.in \
>        utilities/ovs-parse-leaks.8 \
>        utilities/ovs-pcap.1.in \
> @@ -54,6 +57,8 @@ DISTCLEANFILES += \
>        utilities/ovs-check-dead-ifs \
>        utilities/ovs-controller.8 \
>        utilities/ovs-dpctl.8 \
> +       utilities/ovs-l3ping \
> +       utilities/ovs-l3ping.8 \
>        utilities/ovs-lib \
>        utilities/ovs-ofctl.8 \
>        utilities/ovs-parse-leaks \
> @@ -76,6 +81,7 @@ man_MANS += \
>        utilities/ovs-benchmark.1 \
>        utilities/ovs-controller.8 \
>        utilities/ovs-dpctl.8 \
> +       utilities/ovs-l3ping.8 \
>        utilities/ovs-ofctl.8 \
>        utilities/ovs-parse-leaks.8 \
>        utilities/ovs-pcap.1 \
> diff --git a/utilities/ovs-l3ping.8.in b/utilities/ovs-l3ping.8.in
> new file mode 100644
> index 0000000..69da80f
> --- /dev/null
> +++ b/utilities/ovs-l3ping.8.in
> @@ -0,0 +1,108 @@
> +.de IQ
> +.  br
> +.  ns
> +.  IP "\\$1"
> +..
> +.TH ovs\-l3ping 1 "June 2012" "Open vSwitch" "Open vSwitch Manual"
> +.
> +.SH NAME
> +\fBovs\-l3ping\fR \- check network deployment for L3 tunneling
> +problems
> +.
> +.SH SYNOPSIS
> +\fBovs\-l3ping\fR \fB\-s\fR
> \fITunnelRemoteIP,InnerIP[/mask][:ControlPort]\fR
> +.PP
> +\fBovs\-l3ping\fR \fB\-c\fR \fITunnelRemoteIP,InnerIP[/mask][:ControlPort\
> +[:DataPort]],RemoteInnerIP[:ControlPort[:DataPort]]\fR
> +[\fB\-b\fR \fItargetbandwidth\fR] [\fB\-i\fR \fItestinterval\fR]
> +\fB\-t\fR \fItunnelmode\fR
> +.so lib/common-syn.man
> +.
> +.SH DESCRIPTION
> +The \fBovs\-l3ping\fR 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 \fBovs\-l3ping\fR 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 \fBovs\-l3ping\fR client will perform UDP and TCP tests.
> +This tool is different from \fBovs\-test\fR that it encapsulates XML/RPC
> +control connection over the tunnel, so there is no need to open special
> holes
> +in firewall.
> +.PP
> +UDP tests can report packet loss and achieved bandwidth for various
> +datagram sizes. By default target bandwidth for UDP tests is 1Mbit/s.
> +.PP
> +TCP tests report only achieved bandwidth, because kernel TCP stack
> +takes care of flow control and packet loss.
> +.
> +.SS "Client Mode"
> +An \fBovs\-l3ping\fR client will create a L3 tunnel and connect over it
> to the
> +\fBovs\-l3ping\fR server to schedule the tests. \fITunnelRemoteIP\fR is
> the
> +peer's IP address, where tunnel will be terminated. \fIInnerIP\fR is the
> +address that will be temporarily assigned during testing.  All test
> traffic
> +originating from this IP address to the \fIRemoteInnerIP\fR will be
> tunneled.
> +It is possible to override default \fIControlPort\fR and \fIDataPort\fR,
> if
> +there is any other application that already listens on those two ports.
> +.
> +.SS "Server Mode"
> +To conduct tests, \fBovs\-l3ping\fR server must be running.  It is
> required
> +that both client and server \fIInnerIP\fR addresses are in the same
> subnet.
> +It is possible to specify \fIInnerIP\fR with netmask in CIDR format.
> +.
> +.SH OPTIONS
> +.
> +.IP "\fB\-s \fITunnelRemoteIP,InnerIP[/mask][:ControlPort]\fR"
> +.IQ "\fB\-\-server\fR \fITunnelRemoteIP,InnerIP[/mask][:ControlPort]\fR"
> +Run in server mode and create L3 tunnel with the client that will be
> +accepting tunnel at \fITunnelRemoteIP\fR address.  The socket on
> +\fIInnerIP[:ControlPort]\fR will be used to receive further instructions
> +from the client.
> +.
> +.IP "\fB\-c \fITunnelRemoteIP,InnerIP[/mask][:ControlPort\
> +[:DataPort]],RemoteInnerIP[:ControlPort[:DataPort]]\fR"
> +.IQ "\fB\-\-client \fITunnelRemoteIP,InnerIP[/mask][:ControlPort\
> +[:DataPort]],RemoteInnerIP[:ControlPort[:DataPort]]\fR"
> +Run in client mode and create L3 tunnel with the server on
> +\fITunnelRemoteIP\fR.  The client will use \fIInnerIP\fR to generate test
> +traffic with the server's \fIRemoteInnerIP\fR.
> +.
> +.IP "\fB\-b \fItargetbandwidth\fR"
> +.IQ "\fB\-\-bandwidth\fR \fItargetbandwidth\fR"
> +Target bandwidth for UDP tests. The \fItargetbandwidth\fR must be given in
> +bits per second. It is possible to use postfix M or K to alter the target
> +bandwidth magnitude.
> +.
> +.IP "\fB\-i \fItestinterval\fR"
> +.IQ "\fB\-\-interval\fR \fItestinterval\fR"
> +How long each test should run. By default 5 seconds.
> +.
> +.IP "\fB\-t \fItunnelmode\fR"
> +.IQ "\fB\-\-fItunnel\-mode\fR \fItunnelmode\fR"
> +Specify the tunnel type. This option must match on server and client.
> +.
> +.so lib/common.man
> +.
> +.SH EXAMPLES
> +.PP
> +On host 192.168.122.220 start \fBovs\-l3ping\fR 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:
> +.IP
> +.B ovs\-l3ping -s 192.168.122.236,10.1.1.1/28 -t gre
> +.
> +.PP
> +On host 192.168.122.236 start \fBovs\-l3ping\fR 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.
> +.IP
> +.B ovs\-l3ping -c 192.168.122.220,10.1.1.2/28,10.1.1.1 -t gre
> +.
> +.SH SEE ALSO
> +.
> +.BR ovs\-vswitchd (8),
> +.BR ovs\-ofctl (8),
> +.BR ovs\-vsctl (8),
> +.BR ovs\-vlan\-test (8),
> +.BR ovs\-test (8),
> +.BR ethtool (8),
> +.BR uname (1)
> \ No newline at end of file
> diff --git a/utilities/ovs-l3ping.in b/utilities/ovs-l3ping.in
> new file mode 100644
> index 0000000..35e5fdd
> --- /dev/null
> +++ b/utilities/ovs-l3ping.in
> @@ -0,0 +1,76 @@
> +#! @PYTHON@
> +#
> +# 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 xmlrpclib
> +
> +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:
> +        pass
>
Might be friendly to add something here to distinguish from normal
termination


> +    except xmlrpclib.Fault:
> +        print "Couldn't contact peer"
> +    except socket.error:
> +        print "Couldn't contact peer"
> +    except xmlrpclib.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
> index b53302f..fb1f9ad 100644
> --- a/utilities/ovs-test.in
> +++ b/utilities/ovs-test.in
> @@ -32,80 +32,18 @@ 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 rpc_client(ip, port):
> -    return xmlrpclib.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"
> -
> -
>  def collect_information(node):
>     """Print information about hosts that will do testing"""
>     print "Node %s:%u " % (node[0], node[1])
> -    server = rpc_client(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()
> @@ -140,210 +78,6 @@ def collect_information(node):
>     return mtu
>
>
> -def do_udp_tests(receiver, sender, tbwidth, duration, port_sizes):
> -    """Schedule UDP tests between receiver and sender"""
> -    server1 = rpc_client(receiver[0], receiver[1])
> -    server2 = 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],
> -                             bandwidth_to_string(tbwidth)))
> -    print udpformat.format("Datagram Size", "Snt Datagrams", "Rcv
> Datagrams",
> -                            "Datagram Loss", "Bandwidth")
> -
> -    for size in port_sizes:
> -        listen_handle = -1
> -        send_handle = -1
> -        try:
> -            packetcnt = (tbwidth * duration) / size
> -
> -            listen_handle = server1.create_udp_listener(receiver[3])
> -            if listen_handle == -1:
> -                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(
> -                                            (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,
> bandwidth_to_string(bwidth))
> -        finally:
> -            if listen_handle != -1:
> -                server1.close_udp_listener(listen_handle)
> -            if send_handle != -1:
> -                server2.close_udp_sender(send_handle)
> -    print "\n"
> -
> -
> -def do_tcp_tests(receiver, sender, duration):
> -    """Schedule TCP tests between receiver and sender"""
> -    server1 = rpc_client(receiver[0], receiver[1])
> -    server2 = 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 = -1
> -    send_handle = -1
> -    try:
> -        listen_handle = server1.create_tcp_listener(receiver[3])
> -        if listen_handle == -1:
> -            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(ip_from_cidr(receiver[2]),
> -                                                receiver[3], duration)
> -
> -        time.sleep(duration + 1)
> -
> -        rcv_bytes = long(server1.get_tcp_listener_results(listen_handle))
> -        snt_bytes = long(server2.get_tcp_sender_results(send_handle))
> -
> -        bwidth = rcv_bytes / duration
> -
> -        print tcpformat.format(snt_bytes, rcv_bytes,
> -                               bandwidth_to_string(bwidth))
> -    finally:
> -        if listen_handle != -1:
> -            server1.close_tcp_listener(listen_handle)
> -        if send_handle != -1:
> -            server2.close_tcp_sender(send_handle)
> -    print "\n"
> -
> -
> -def do_l3_tests(node1, node2, bandwidth, duration, ps, type):
> -    """
> -    Do L3 tunneling tests.
> -    """
> -    server1 = rpc_client(node1[0], node1[1])
> -    server2 = 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.
> -    """
> -    server1 = rpc_client(node1[0], node1[1])
> -    server2 = 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
> -    """
> -    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)
> -
> -
>  if __name__ == '__main__':
>     local_server = None
>     try:
> @@ -360,10 +94,10 @@ if __name__ == '__main__':
>             # 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 = start_local_server(node1[1])
> +                local_server = util.start_local_server(node1[1])
>                 # We must determine the IP address that local ovs-test
> server
>                 # will use:
> -                me = rpc_client(node1[0], node1[1])
> +                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])
>
> @@ -372,7 +106,7 @@ if __name__ == '__main__':
>
>             bandwidth = ovs_args.targetBandwidth
>             interval = ovs_args.testInterval
> -            ps = get_datagram_sizes(mtu_node1, mtu_node2)
> +            ps = util.get_datagram_sizes(mtu_node1, mtu_node2)
>
>             direct = ovs_args.direct
>             vlan_tag = ovs_args.vlanTag
> @@ -380,15 +114,17 @@ if __name__ == '__main__':
>
>             if direct is not None:
>                 print "Performing direct tests"
> -                do_direct_tests(node2, node1, bandwidth, interval, ps)
> +                tests.do_direct_tests(node2, node1, bandwidth, interval,
> ps)
>
>             if vlan_tag is not None:
>                 print "Performing VLAN tests"
> -                do_vlan_tests(node2, node1, bandwidth, interval, ps,
> vlan_tag)
> +                tests.do_vlan_tests(node2, node1, bandwidth, interval, ps,
> +                                    vlan_tag)
>
>             for tmode in tunnel_modes:
>                 print "Performing", tmode, "tests"
> -                do_l3_tests(node2, node1, bandwidth, interval, ps, tmode)
> +                tests.do_l3_tests(node2, node1, bandwidth, interval, ps,
> +                                  tmode)
>
>     except KeyboardInterrupt:
>         pass
> diff --git a/xenserver/openvswitch-xen.spec.in b/xenserver/
> openvswitch-xen.spec.in
> index e051b31..3b9582e 100644
> --- a/xenserver/openvswitch-xen.spec.in
> +++ b/xenserver/openvswitch-xen.spec.in
> @@ -125,13 +125,15 @@ rm \
>     $RPM_BUILD_ROOT/usr/bin/ovs-benchmark \
>     $RPM_BUILD_ROOT/usr/sbin/ovs-bugtool \
>     $RPM_BUILD_ROOT/usr/bin/ovs-controller \
> +    $RPM_BUILD_ROOT/usr/bin/ovs-l3ping \
>     $RPM_BUILD_ROOT/usr/bin/ovs-pki \
>     $RPM_BUILD_ROOT/usr/bin/ovs-test \
> -    $RPM_BUILD_ROOT/usr/share/man/man8/ovs-test.8 \
>     $RPM_BUILD_ROOT/usr/share/man/man1/ovs-benchmark.1 \
>     $RPM_BUILD_ROOT/usr/share/man/man8/ovs-bugtool.8 \
>     $RPM_BUILD_ROOT/usr/share/man/man8/ovs-controller.8 \
> -    $RPM_BUILD_ROOT/usr/share/man/man8/ovs-pki.8
> +    $RPM_BUILD_ROOT/usr/share/man/man8/ovs-l3ping.8
> +    $RPM_BUILD_ROOT/usr/share/man/man8/ovs-pki.8 \
> +    $RPM_BUILD_ROOT/usr/share/man/man8/ovs-test.8
>
>  install -d -m 755 $RPM_BUILD_ROOT/var/lib/openvswitch
>
> --
> 1.7.9.5
>
> _______________________________________________
> dev mailing list
> dev at openvswitch.org
> http://openvswitch.org/mailman/listinfo/dev
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.openvswitch.org/pipermail/ovs-dev/attachments/20120628/edbe231e/attachment-0003.html>


More information about the dev mailing list