Looks good.

Ethan

On Fri, Sep 23, 2011 at 14:24, Ben Pfaff <[email protected]> wrote:
> ---
>  debian/ovs-monitor-ipsec   |   52 ++++++-----
>  tests/automake.mk          |    1 +
>  tests/ovs-monitor-ipsec.at |  222 
> ++++++++++++++++++++++++++++++++++++++++++++
>  tests/testsuite.at         |    1 +
>  4 files changed, 254 insertions(+), 22 deletions(-)
>  create mode 100644 tests/ovs-monitor-ipsec.at
>
> diff --git a/debian/ovs-monitor-ipsec b/debian/ovs-monitor-ipsec
> index c123188..1eefa8e 100755
> --- a/debian/ovs-monitor-ipsec
> +++ b/debian/ovs-monitor-ipsec
> @@ -52,7 +52,9 @@ try:
>  except socket.error, e:
>     logging.basicConfig()
>     s_log.warn("failed to connect to syslog (%s)" % e)
> +s_log.addHandler(logging.StreamHandler())
>
> +root_prefix = ''                # Prefix for absolute file names, for 
> testing.
>  setkey = "/usr/sbin/setkey"
>
>  # Class to configure the racoon daemon, which handles IKE negotiation
> @@ -121,11 +123,12 @@ path certificate "%s";
>         self.psk_hosts = {}
>         self.cert_hosts = {}
>
> -        if not os.path.isdir(self.cert_dir):
> +        if not os.path.isdir(root_prefix + self.cert_dir):
>             os.mkdir(self.cert_dir)
>
>         # Clean out stale peer certs from previous runs
> -        for ovs_cert in glob.glob("%s/ovs-*.pem" % self.cert_dir):
> +        for ovs_cert in glob.glob("%s%s/ovs-*.pem"
> +                                  % (root_prefix, self.cert_dir)):
>             try:
>                 os.remove(ovs_cert)
>             except OSError:
> @@ -135,20 +138,22 @@ path certificate "%s";
>         self.commit()
>
>     def reload(self):
> -        exitcode = subprocess.call(["/etc/init.d/racoon", "reload"])
> +        exitcode = subprocess.call([root_prefix + "/etc/init.d/racoon",
> +                                    "reload"])
>         if exitcode != 0:
>             # Racoon is finicky about its configuration file and will
>             # refuse to start if it sees something it doesn't like
>             # (e.g., a certificate file doesn't exist).  Try restarting
>             # the process before giving up.
>             s_log.warning("attempting to restart racoon")
> -            exitcode = subprocess.call(["/etc/init.d/racoon", "restart"])
> +            exitcode = subprocess.call([root_prefix + "/etc/init.d/racoon",
> +                                        "restart"])
>             if exitcode != 0:
>                 s_log.warning("couldn't reload racoon")
>
>     def commit(self):
>         # Rewrite the Racoon configuration file
> -        conf_file = open(self.conf_file, 'w')
> +        conf_file = open(root_prefix + self.conf_file, 'w')
>         conf_file.write(Racoon.conf_header % (self.psk_file, self.cert_dir))
>
>         for host, vals in self.cert_hosts.iteritems():
> @@ -163,7 +168,7 @@ path certificate "%s";
>
>         # Rewrite the pre-shared keys file; it must only be readable by root.
>         orig_umask = os.umask(0077)
> -        psk_file = open(Racoon.psk_file, 'w')
> +        psk_file = open(root_prefix + Racoon.psk_file, 'w')
>         os.umask(orig_umask)
>
>         psk_file.write("# Generated by Open vSwitch...do not modify by hand!")
> @@ -184,10 +189,10 @@ path certificate "%s";
>     def _verify_certs(self, vals):
>         # Racoon will refuse to start if the certificate files don't
>         # exist, so verify that they're there.
> -        if not os.path.isfile(vals["certificate"]):
> +        if not os.path.isfile(root_prefix + vals["certificate"]):
>             raise error.Error("'certificate' file does not exist: %s"
>                     % vals["certificate"])
> -        elif not os.path.isfile(vals["private_key"]):
> +        elif not os.path.isfile(root_prefix + vals["private_key"]):
>             raise error.Error("'private_key' file does not exist: %s"
>                     % vals["private_key"])
>
> @@ -197,11 +202,11 @@ path certificate "%s";
>         if vals["peer_cert"].find("-----BEGIN CERTIFICATE-----") == -1:
>             raise error.Error("'peer_cert' is not in valid PEM format")
>
> -        cert = open(vals["certificate"]).read()
> +        cert = open(root_prefix + vals["certificate"]).read()
>         if cert.find("-----BEGIN CERTIFICATE-----") == -1:
>             raise error.Error("'certificate' is not in valid PEM format")
>
> -        cert = open(vals["private_key"]).read()
> +        cert = open(root_prefix + vals["private_key"]).read()
>         if cert.find("-----BEGIN RSA PRIVATE KEY-----") == -1:
>             raise error.Error("'private_key' is not in valid PEM format")
>
> @@ -226,7 +231,7 @@ path certificate "%s";
>         # The peer's certificate comes to us in PEM format as a string.
>         # Write that string to a file for Racoon to use.
>         peer_cert_file = "%s/ovs-%s.pem" % (self.cert_dir, host)
> -        f = open(peer_cert_file, "w")
> +        f = open(root_prefix + peer_cert_file, "w")
>         f.write(vals["peer_cert"])
>         f.close()
>
> @@ -240,7 +245,7 @@ path certificate "%s";
>         del self.cert_hosts[host]
>         self.commit()
>         try:
> -            os.remove(peer_cert_file)
> +            os.remove(root_prefix + peer_cert_file)
>         except OSError:
>             pass
>
> @@ -270,10 +275,11 @@ class IPsec:
>
>     def call_setkey(self, cmds):
>         try:
> -            p = subprocess.Popen([setkey, "-c"], stdin=subprocess.PIPE,
> -                    stdout=subprocess.PIPE)
> +            p = subprocess.Popen([root_prefix + setkey, "-c"],
> +                                 stdin=subprocess.PIPE,
> +                                 stdout=subprocess.PIPE)
>         except:
> -            s_log.error("could not call setkey")
> +            s_log.error("could not call %s%s" % (root_prefix, setkey))
>             sys.exit(1)
>
>         # xxx It is safer to pass the string into the communicate()
> @@ -289,7 +295,7 @@ class IPsec:
>         # older entry could be in a "dying" state.
>         spi_list = []
>         host_line = "%s %s" % (local_ip, remote_ip)
> -        results = self.call_setkey("dump ;").split("\n")
> +        results = self.call_setkey("dump ;\n").split("\n")
>         for i in range(len(results)):
>             if results[i].strip() == host_line:
>                 # The SPI is in the line following the host pair
> @@ -300,7 +306,7 @@ class IPsec:
>         return spi_list
>
>     def sad_flush(self):
> -        self.call_setkey("flush;")
> +        self.call_setkey("flush;\n")
>
>     def sad_del(self, local_ip, remote_ip):
>         # To delete all SAD entries, we should be able to use setkey's
> @@ -322,18 +328,18 @@ class IPsec:
>             self.call_setkey(cmds)
>
>     def spd_flush(self):
> -        self.call_setkey("spdflush;")
> +        self.call_setkey("spdflush;\n")
>
>     def spd_add(self, local_ip, remote_ip):
>         cmds = ("spdadd %s %s gre -P out ipsec esp/transport//require;\n" %
>                     (local_ip, remote_ip))
> -        cmds += ("spdadd %s %s gre -P in ipsec esp/transport//require;" %
> +        cmds += ("spdadd %s %s gre -P in ipsec esp/transport//require;\n" %
>                     (remote_ip, local_ip))
>         self.call_setkey(cmds)
>
>     def spd_del(self, local_ip, remote_ip):
>         cmds = "spddelete %s %s gre -P out;\n" % (local_ip, remote_ip)
> -        cmds += "spddelete %s %s gre -P in;" % (remote_ip, local_ip)
> +        cmds += "spddelete %s %s gre -P in;\n" % (remote_ip, local_ip)
>         self.call_setkey(cmds)
>
>     def add_entry(self, local_ip, remote_ip, vals):
> @@ -401,8 +407,10 @@ def usage():
>     print "usage: %s [OPTIONS] DATABASE" % sys.argv[0]
>     print "where DATABASE is a socket on which ovsdb-server is listening."
>     ovs.daemon.usage()
> -    print "Other options:"
> -    print "  -h, --help               display this help message"
> +    print """\
> +Other options:
> +    --root-prefix=DIR   Use DIR as alternate root directory (for testing).
> +    -h, --help          Display this help message."""
>     sys.exit(0)
>
>  def update_ipsec(ipsec, interfaces, new_interfaces):
> diff --git a/tests/automake.mk b/tests/automake.mk
> index 9b094de..dcf6026 100644
> --- a/tests/automake.mk
> +++ b/tests/automake.mk
> @@ -51,6 +51,7 @@ TESTSUITE_AT = \
>        tests/ovsdb-monitor.at \
>        tests/ovsdb-idl.at \
>        tests/ovs-vsctl.at \
> +       tests/ovs-monitor-ipsec.at \
>        tests/interface-reconfigure.at
>  TESTSUITE = $(srcdir)/tests/testsuite
>  DISTCLEANFILES += tests/atconfig tests/atlocal
> diff --git a/tests/ovs-monitor-ipsec.at b/tests/ovs-monitor-ipsec.at
> new file mode 100644
> index 0000000..ad1e96e
> --- /dev/null
> +++ b/tests/ovs-monitor-ipsec.at
> @@ -0,0 +1,222 @@
> +AT_BANNER([ovs-monitor-ipsec])
> +
> +AT_SETUP([ovs-monitor-ipsec])
> +AT_SKIP_IF([test $HAVE_PYTHON = no])
> +
> +OVS_PKGDATADIR=`pwd`; export OVS_PKGDATADIR
> +cp "$top_srcdir/vswitchd/vswitch.ovsschema" .
> +
> +trap 'kill `cat pid ovs-monitor-ipsec.pid`' 0
> +
> +mkdir etc etc/init.d etc/racoon etc/racoon/certs
> +mkdir usr usr/sbin
> +
> +AT_DATA([etc/init.d/racoon], [dnl
> +#! /bin/sh
> +echo "racoon: $@" >&3
> +exit 0
> +])
> +chmod +x etc/init.d/racoon
> +
> +AT_DATA([usr/sbin/setkey], [dnl
> +#! /bin/sh
> +exec >&3
> +echo "setkey:"
> +while read line; do
> +      echo "> $line"
> +done
> +])
> +chmod +x usr/sbin/setkey
> +
> +touch etc/racoon/certs/ovs-stale.pem
> +
> +ovs_vsctl () {
> +    ovs-vsctl --timeout=5 --no-wait -vreconnect:ANY:emer --db=unix:socket 
> "$@"
> +}
> +trim () {  # Removes blank lines and lines starting with # from input.
> +    sed -e '/^#/d' -e '/^[       ]*$/d' "$@"
> +}
> +
> +###
> +### Start ovsdb-server.
> +###
> +OVS_VSCTL_SETUP
> +
> +###
> +### Start ovs-monitor-ipsec and wait for it to delete the stale cert.
> +###
> +AT_CHECK(
> +  [$PYTHON $top_srcdir/debian/ovs-monitor-ipsec "--root-prefix=`pwd`" \
> +        "--pidfile-name=`pwd`/ovs-monitor-ipsec.pid" \
> +        unix:socket 2>log 3>actions &])
> +AT_CAPTURE_FILE([log])
> +AT_CAPTURE_FILE([actions])
> +OVS_WAIT_UNTIL([test ! -f etc/racoon/certs/ovs-stale.pem])
> +
> +###
> +### Add an ipsec_gre psk interface and check what ovs-monitor-ipsec does
> +###
> +AT_CHECK([ovs_vsctl \
> +              -- add-br br0 \
> +              -- add-port br0 gre0 \
> +              -- set interface gre0 type=ipsec_gre \
> +                                    options:remote_ip=1.2.3.4 \
> +                                    options:psk=swordfish])
> +OVS_WAIT_UNTIL([test -f actions && grep 'spdadd 1.2.3.4' actions >/dev/null])
> +AT_CHECK([cat actions], [0], [dnl
> +setkey:
> +> flush;
> +setkey:
> +> spdflush;
> +racoon: reload
> +racoon: reload
> +setkey:
> +> spdadd 0.0.0.0/0 1.2.3.4 gre -P out ipsec esp/transport//require;
> +> spdadd 1.2.3.4 0.0.0.0/0 gre -P in ipsec esp/transport//require;
> +])
> +AT_CHECK([trim etc/racoon/psk.txt], [0], [1.2.3.4   swordfish
> +])
> +AT_CHECK([trim etc/racoon/racoon.conf], [0], [dnl
> +path pre_shared_key "/etc/racoon/psk.txt";
> +path certificate "/etc/racoon/certs";
> +remote 1.2.3.4 {
> +        exchange_mode main;
> +        nat_traversal on;
> +        proposal {
> +                encryption_algorithm aes;
> +                hash_algorithm sha1;
> +                authentication_method pre_shared_key;
> +                dh_group 2;
> +        }
> +}
> +sainfo anonymous {
> +        pfs_group 2;
> +        lifetime time 1 hour;
> +        encryption_algorithm aes;
> +        authentication_algorithm hmac_sha1, hmac_md5;
> +        compression_algorithm deflate;
> +}
> +])
> +
> +###
> +### Delete the ipsec_gre interface and check what ovs-monitor-ipsec does
> +###
> +AT_CHECK([ovs_vsctl del-port gre0])
> +OVS_WAIT_UNTIL([test `wc -l < actions` -ge 17])
> +AT_CHECK([sed '1,9d' actions], [0], [dnl
> +racoon: reload
> +setkey:
> +> spddelete 0.0.0.0/0 1.2.3.4 gre -P out;
> +> spddelete 1.2.3.4 0.0.0.0/0 gre -P in;
> +setkey:
> +> dump ;
> +setkey:
> +> dump ;
> +])
> +AT_CHECK([trim etc/racoon/psk.txt], [0], [])
> +AT_CHECK([trim etc/racoon/racoon.conf], [0], [dnl
> +path pre_shared_key "/etc/racoon/psk.txt";
> +path certificate "/etc/racoon/certs";
> +sainfo anonymous {
> +        pfs_group 2;
> +        lifetime time 1 hour;
> +        encryption_algorithm aes;
> +        authentication_algorithm hmac_sha1, hmac_md5;
> +        compression_algorithm deflate;
> +}
> +])
> +
> +###
> +### Add ipsec_gre certificate interface and check what ovs-monitor-ipsec does
> +###
> +AT_DATA([cert.pem], [dnl
> +-----BEGIN CERTIFICATE-----
> +(not a real certificate)
> +-----END CERTIFICATE-----
> +])
> +AT_DATA([key.pem], [dnl
> +-----BEGIN RSA PRIVATE KEY-----
> +(not a real private key)
> +-----END RSA PRIVATE KEY-----
> +])
> +AT_CHECK([ovs_vsctl \
> +              -- add-port br0 gre1 \
> +              -- set Interface gre1 type=ipsec_gre \
> +                 options:remote_ip=2.3.4.5 \
> +                 options:peer_cert='"-----BEGIN CERTIFICATE-----
> +(not a real peer certificate)
> +-----END CERTIFICATE-----
> +"' \
> +                 options:certificate='"/cert.pem"' \
> +                 options:private_key='"/key.pem"'])
> +OVS_WAIT_UNTIL([test `wc -l < actions` -ge 21])
> +AT_CHECK([sed '1,17d' actions], [0], [dnl
> +racoon: reload
> +setkey:
> +> spdadd 0.0.0.0/0 2.3.4.5 gre -P out ipsec esp/transport//require;
> +> spdadd 2.3.4.5 0.0.0.0/0 gre -P in ipsec esp/transport//require;
> +])
> +AT_CHECK([trim etc/racoon/psk.txt], [0], [])
> +AT_CHECK([trim etc/racoon/racoon.conf], [0], [dnl
> +path pre_shared_key "/etc/racoon/psk.txt";
> +path certificate "/etc/racoon/certs";
> +remote 2.3.4.5 {
> +        exchange_mode main;
> +        nat_traversal on;
> +        ike_frag on;
> +        certificate_type x509 "/cert.pem" "/key.pem";
> +        my_identifier asn1dn;
> +        peers_identifier asn1dn;
> +        peers_certfile x509 "/etc/racoon/certs/ovs-2.3.4.5.pem";
> +        verify_identifier on;
> +        proposal {
> +                encryption_algorithm aes;
> +                hash_algorithm sha1;
> +                authentication_method rsasig;
> +                dh_group 2;
> +        }
> +}
> +sainfo anonymous {
> +        pfs_group 2;
> +        lifetime time 1 hour;
> +        encryption_algorithm aes;
> +        authentication_algorithm hmac_sha1, hmac_md5;
> +        compression_algorithm deflate;
> +}
> +])
> +AT_CHECK([cat etc/racoon/certs/ovs-2.3.4.5.pem], [0], [dnl
> +-----BEGIN CERTIFICATE-----
> +(not a real peer certificate)
> +-----END CERTIFICATE-----
> +])
> +
> +###
> +### Delete the ipsec_gre certificate interface.
> +###
> +AT_CHECK([ovs_vsctl del-port gre1])
> +OVS_WAIT_UNTIL([test `wc -l < actions` -ge 29])
> +AT_CHECK([sed '1,21d' actions], [0], [dnl
> +racoon: reload
> +setkey:
> +> spddelete 0.0.0.0/0 2.3.4.5 gre -P out;
> +> spddelete 2.3.4.5 0.0.0.0/0 gre -P in;
> +setkey:
> +> dump ;
> +setkey:
> +> dump ;
> +])
> +AT_CHECK([trim etc/racoon/psk.txt], [0], [])
> +AT_CHECK([trim etc/racoon/racoon.conf], [0], [dnl
> +path pre_shared_key "/etc/racoon/psk.txt";
> +path certificate "/etc/racoon/certs";
> +sainfo anonymous {
> +        pfs_group 2;
> +        lifetime time 1 hour;
> +        encryption_algorithm aes;
> +        authentication_algorithm hmac_sha1, hmac_md5;
> +        compression_algorithm deflate;
> +}
> +])
> +AT_CHECK([test ! -f etc/racoon/certs/ovs-2.3.4.5.pem])
> +
> +AT_CLEANUP
> diff --git a/tests/testsuite.at b/tests/testsuite.at
> index ea5208f..19b7802 100644
> --- a/tests/testsuite.at
> +++ b/tests/testsuite.at
> @@ -64,4 +64,5 @@ m4_include([tests/ofproto.at])
>  m4_include([tests/ofproto-dpif.at])
>  m4_include([tests/ovsdb.at])
>  m4_include([tests/ovs-vsctl.at])
> +m4_include([tests/ovs-monitor-ipsec.at])
>  m4_include([tests/interface-reconfigure.at])
> --
> 1.7.4.4
>
> _______________________________________________
> dev mailing list
> [email protected]
> http://openvswitch.org/mailman/listinfo/dev
>
_______________________________________________
dev mailing list
[email protected]
http://openvswitch.org/mailman/listinfo/dev

Reply via email to