From bcc8f7ca7fd8e8ff6e8a4d579251458313133598 Mon Sep 17 00:00:00 2001 From: Rene Mayrhofer Date: Thu, 7 Feb 2008 13:56:17 +0000 Subject: [svn-upgrade] Integrating new upstream version, strongswan (4.1.10) --- NEWS | 43 +- TODO | 21 +- configure | 378 ++++- configure.in | 87 +- src/Makefile.am | 42 +- src/Makefile.in | 53 +- src/_updown/Makefile.am | 1 + src/_updown/Makefile.in | 1 + src/_updown/_updown.in | 184 ++- src/charon/Makefile.am | 90 +- src/charon/Makefile.in | 373 +++-- src/charon/bus/bus.c | 306 ++--- src/charon/bus/bus.h | 52 +- src/charon/config/backends/sqlite_backend.c | 19 +- .../config/credentials/local_credential_store.c | 4 +- src/charon/config/peer_cfg.c | 104 +- src/charon/config/peer_cfg.h | 53 +- src/charon/control/interface_manager.c | 656 +++++---- src/charon/control/interfaces/stroke_interface.c | 61 +- src/charon/control/interfaces/xml_interface.c | 273 +++- src/charon/daemon.c | 2 +- .../encoding/payloads/configuration_attribute.c | 2 +- src/charon/encoding/payloads/eap_payload.c | 19 +- src/charon/encoding/payloads/eap_payload.h | 5 +- src/charon/encoding/payloads/endpoint_notify.c | 29 +- src/charon/encoding/payloads/endpoint_notify.h | 17 + src/charon/encoding/payloads/ike_header.c | 3 +- src/charon/encoding/payloads/notify_payload.c | 26 +- src/charon/encoding/payloads/notify_payload.h | 5 +- src/charon/network/socket-raw.c | 771 +++++++++++ src/charon/network/socket.c | 455 ++----- src/charon/network/socket.h | 4 +- src/charon/processing/jobs/callback_job.c | 14 +- .../processing/jobs/initiate_mediation_job.c | 32 +- src/charon/processing/jobs/mediation_job.c | 6 +- src/charon/processing/jobs/process_message_job.c | 7 +- src/charon/processing/scheduler.c | 8 +- src/charon/sa/authenticators/eap/eap_aka.c | 1440 ++++++++++++++++++++ src/charon/sa/authenticators/eap/eap_aka.h | 141 ++ src/charon/sa/authenticators/eap/eap_md5.c | 282 ++++ src/charon/sa/authenticators/eap/eap_md5.h | 59 + src/charon/sa/authenticators/eap/eap_method.c | 42 +- src/charon/sa/authenticators/eap/eap_method.h | 11 +- src/charon/sa/authenticators/eap/eap_sim.c | 8 +- src/charon/sa/authenticators/eap_authenticator.c | 105 +- src/charon/sa/authenticators/eap_authenticator.h | 9 +- src/charon/sa/child_sa.c | 2 +- src/charon/sa/connect_manager.c | 77 +- src/charon/sa/ike_sa.c | 217 ++- src/charon/sa/ike_sa.h | 45 +- src/charon/sa/mediation_manager.c | 4 +- src/charon/sa/task_manager.c | 16 +- src/charon/sa/tasks/ike_auth.c | 16 +- src/charon/sa/tasks/ike_auth_lifetime.c | 200 +++ src/charon/sa/tasks/ike_auth_lifetime.h | 61 + src/charon/sa/tasks/ike_mobike.c | 8 +- src/charon/sa/tasks/ike_p2p.c | 97 +- src/charon/sa/tasks/task.c | 1 + src/charon/sa/tasks/task.h | 2 + src/ipsec/ipsec.in | 163 ++- src/libstrongswan/crypto/ac.c | 8 +- src/libstrongswan/crypto/ca.c | 6 +- src/libstrongswan/crypto/crl.c | 6 +- src/libstrongswan/crypto/x509.c | 8 +- src/libstrongswan/library.c | 19 +- src/libstrongswan/printf_hook.c | 23 + src/libstrongswan/printf_hook.h | 3 +- src/libstrongswan/utils/lexparser.c | 32 +- src/libstrongswan/utils/lexparser.h | 9 +- src/manager/Makefile.am | 25 +- src/manager/Makefile.in | 188 ++- src/manager/controller/auth_controller.c | 2 +- src/manager/controller/config_controller.c | 214 +++ src/manager/controller/config_controller.h | 47 + src/manager/controller/control_controller.c | 211 +++ src/manager/controller/control_controller.h | 47 + src/manager/controller/gateway_controller.c | 2 +- src/manager/controller/ikesa_controller.c | 238 ++++ src/manager/controller/ikesa_controller.h | 47 + src/manager/controller/status_controller.c | 238 ---- src/manager/controller/status_controller.h | 47 - src/manager/gateway.c | 180 ++- src/manager/gateway.h | 25 + src/manager/lib/dispatcher.c | 23 +- src/manager/lib/request.c | 25 +- src/manager/lib/request.h | 14 +- src/manager/main.c | 10 +- src/manager/templates/config/list.cs | 104 ++ src/manager/templates/control/result.cs | 14 + src/manager/templates/header.cs | 4 +- src/manager/templates/ikesa/list.cs | 111 ++ src/manager/templates/static/close.png | Bin 0 -> 825 bytes src/manager/templates/static/initiate.png | Bin 0 -> 601 bytes src/manager/templates/static/pipe-thin-green.png | Bin 0 -> 372 bytes .../templates/static/pipe-thin-left-green.png | Bin 0 -> 449 bytes .../templates/static/pipe-thin-right-green.png | Bin 0 -> 460 bytes src/manager/templates/static/script.js | 5 +- src/manager/templates/static/style.css | 11 + src/manager/templates/status/ikesalist.cs | 101 -- src/pluto/Makefile.am | 12 - src/pluto/Makefile.in | 18 +- src/pluto/connections.c | 3 +- src/pluto/vendor.c | 6 +- src/pluto/vendor.h | 4 +- src/starter/confread.c | 35 +- src/starter/confread.h | 5 +- src/starter/invokecharon.c | 9 +- src/starter/ipsec.conf.5 | 18 +- src/starter/starter.c | 36 +- src/starter/starterstroke.c | 5 +- src/starter/starterwhack.c | 15 +- src/stroke/stroke.h | 5 +- testing/INSTALL | 8 +- testing/do-tests.in | 13 +- testing/hosts/winnetou/etc/apache2/httpd.conf | 1103 --------------- .../etc/apache2/modules.d/00_mod_mime.conf | 61 + .../etc/apache2/vhosts.d/01_ocsp_vhost.conf | 21 +- testing/hosts/winnetou/etc/conf.d/apache2 | 52 - testing/hosts/winnetou/etc/init.d/apache2 | 137 +- .../hosts/winnetou/etc/runlevels/default/apache2 | 137 +- testing/images/a-m-c-w-d-ip6.png | Bin 0 -> 23726 bytes testing/images/a-m-c-w-ip6.png | Bin 0 -> 18734 bytes testing/images/a-m-c-w-s-b-med.png | Bin 0 -> 28066 bytes testing/images/a-m-w-s-b-ip6.png | Bin 0 -> 23041 bytes testing/images/a-v-m-c-w-med.png | Bin 0 -> 23462 bytes testing/images/m-w-s-ip6.png | Bin 0 -> 12067 bytes testing/images/m-w-s.png | Bin 12340 -> 12508 bytes testing/scripts/build-umlrootfs | 13 +- testing/testing.conf | 10 +- .../tests/ikev1/host2host-transport/evaltest.dat | 2 + .../tests/ikev2/host2host-transport/evaltest.dat | 3 + .../host2host-transport/hosts/moon/etc/ipsec.conf | 1 + .../host2host-transport/hosts/sun/etc/ipsec.conf | 1 + testing/tests/ikev2/reauth-early/description.txt | 7 + testing/tests/ikev2/reauth-early/evaltest.dat | 6 + .../ikev2/reauth-early/hosts/carol/etc/ipsec.conf | 23 + .../ikev2/reauth-early/hosts/moon/etc/ipsec.conf | 22 + testing/tests/ikev2/reauth-early/posttest.dat | 4 + testing/tests/ikev2/reauth-early/pretest.dat | 7 + testing/tests/ikev2/reauth-early/test.conf | 21 + testing/tests/ikev2/reauth-late/description.txt | 8 + testing/tests/ikev2/reauth-late/evaltest.dat | 7 + .../ikev2/reauth-late/hosts/carol/etc/ipsec.conf | 23 + .../ikev2/reauth-late/hosts/moon/etc/ipsec.conf | 22 + testing/tests/ikev2/reauth-late/posttest.dat | 4 + testing/tests/ikev2/reauth-late/pretest.dat | 7 + testing/tests/ikev2/reauth-late/test.conf | 21 + testing/tests/ikev2/rw-eap-aka-rsa/description.txt | 7 + testing/tests/ikev2/rw-eap-aka-rsa/evaltest.dat | 10 + .../rw-eap-aka-rsa/hosts/carol/etc/ipsec.conf | 23 + .../rw-eap-aka-rsa/hosts/carol/etc/ipsec.secrets | 3 + .../ikev2/rw-eap-aka-rsa/hosts/moon/etc/ipsec.conf | 24 + .../rw-eap-aka-rsa/hosts/moon/etc/ipsec.secrets | 5 + testing/tests/ikev2/rw-eap-aka-rsa/posttest.dat | 4 + testing/tests/ikev2/rw-eap-aka-rsa/pretest.dat | 7 + testing/tests/ikev2/rw-eap-aka-rsa/test.conf | 21 + testing/tests/ipv6/host2host-ikev1/description.txt | 6 +- .../host2host-ikev1/hosts/moon/etc/init.d/iptables | 100 ++ .../ipv6/host2host-ikev1/hosts/moon/etc/ipsec.conf | 3 - .../host2host-ikev1/hosts/sun/etc/init.d/iptables | 100 ++ .../ipv6/host2host-ikev1/hosts/sun/etc/ipsec.conf | 2 - testing/tests/ipv6/host2host-ikev1/posttest.dat | 2 + testing/tests/ipv6/host2host-ikev1/pretest.dat | 2 + testing/tests/ipv6/host2host-ikev1/test.conf | 2 +- testing/tests/ipv6/host2host-ikev2/description.txt | 6 +- .../host2host-ikev2/hosts/moon/etc/init.d/iptables | 107 ++ .../ipv6/host2host-ikev2/hosts/moon/etc/ipsec.conf | 3 +- .../host2host-ikev2/hosts/sun/etc/init.d/iptables | 107 ++ .../ipv6/host2host-ikev2/hosts/sun/etc/ipsec.conf | 3 +- testing/tests/ipv6/host2host-ikev2/posttest.dat | 2 + testing/tests/ipv6/host2host-ikev2/pretest.dat | 2 + testing/tests/ipv6/host2host-ikev2/test.conf | 2 +- testing/tests/ipv6/net2net-ikev1/description.txt | 6 + testing/tests/ipv6/net2net-ikev1/evaltest.dat | 5 + .../net2net-ikev1/hosts/moon/etc/init.d/iptables | 100 ++ .../ipv6/net2net-ikev1/hosts/moon/etc/ipsec.conf | 28 + .../net2net-ikev1/hosts/sun/etc/init.d/iptables | 100 ++ .../ipv6/net2net-ikev1/hosts/sun/etc/ipsec.conf | 27 + testing/tests/ipv6/net2net-ikev1/posttest.dat | 8 + testing/tests/ipv6/net2net-ikev1/pretest.dat | 10 + testing/tests/ipv6/net2net-ikev1/test.conf | 21 + testing/tests/ipv6/net2net-ikev2/description.txt | 6 + testing/tests/ipv6/net2net-ikev2/evaltest.dat | 5 + .../net2net-ikev2/hosts/moon/etc/init.d/iptables | 107 ++ .../ipv6/net2net-ikev2/hosts/moon/etc/ipsec.conf | 28 + .../net2net-ikev2/hosts/sun/etc/init.d/iptables | 107 ++ .../ipv6/net2net-ikev2/hosts/sun/etc/ipsec.conf | 28 + testing/tests/ipv6/net2net-ikev2/posttest.dat | 8 + testing/tests/ipv6/net2net-ikev2/pretest.dat | 10 + testing/tests/ipv6/net2net-ikev2/test.conf | 21 + testing/tests/ipv6/rw-ikev1/description.txt | 7 + testing/tests/ipv6/rw-ikev1/evaltest.dat | 5 + .../ipv6/rw-ikev1/hosts/carol/etc/init.d/iptables | 100 ++ .../tests/ipv6/rw-ikev1/hosts/carol/etc/ipsec.conf | 27 + .../ipv6/rw-ikev1/hosts/moon/etc/init.d/iptables | 100 ++ .../tests/ipv6/rw-ikev1/hosts/moon/etc/ipsec.conf | 22 + testing/tests/ipv6/rw-ikev1/posttest.dat | 6 + testing/tests/ipv6/rw-ikev1/pretest.dat | 8 + testing/tests/ipv6/rw-ikev1/test.conf | 21 + testing/tests/ipv6/rw-ikev2/description.txt | 7 + testing/tests/ipv6/rw-ikev2/evaltest.dat | 10 + .../ipv6/rw-ikev2/hosts/carol/etc/init.d/iptables | 107 ++ .../tests/ipv6/rw-ikev2/hosts/carol/etc/ipsec.conf | 23 + .../ipv6/rw-ikev2/hosts/dave/etc/init.d/iptables | 107 ++ .../tests/ipv6/rw-ikev2/hosts/dave/etc/ipsec.conf | 23 + .../ipv6/rw-ikev2/hosts/moon/etc/init.d/iptables | 107 ++ .../tests/ipv6/rw-ikev2/hosts/moon/etc/ipsec.conf | 22 + testing/tests/ipv6/rw-ikev2/posttest.dat | 9 + testing/tests/ipv6/rw-ikev2/pretest.dat | 12 + testing/tests/ipv6/rw-ikev2/test.conf | 21 + testing/tests/ipv6/rw-psk-ikev1/description.txt | 5 + testing/tests/ipv6/rw-psk-ikev1/evaltest.dat | 5 + .../rw-psk-ikev1/hosts/carol/etc/init.d/iptables | 100 ++ .../ipv6/rw-psk-ikev1/hosts/carol/etc/ipsec.conf | 19 + .../rw-psk-ikev1/hosts/carol/etc/ipsec.secrets | 3 + .../rw-psk-ikev1/hosts/moon/etc/init.d/iptables | 100 ++ .../ipv6/rw-psk-ikev1/hosts/moon/etc/ipsec.conf | 19 + .../ipv6/rw-psk-ikev1/hosts/moon/etc/ipsec.secrets | 3 + testing/tests/ipv6/rw-psk-ikev1/posttest.dat | 6 + testing/tests/ipv6/rw-psk-ikev1/pretest.dat | 10 + testing/tests/ipv6/rw-psk-ikev1/test.conf | 21 + testing/tests/ipv6/rw-psk-ikev2/description.txt | 7 + testing/tests/ipv6/rw-psk-ikev2/evaltest.dat | 10 + .../rw-psk-ikev2/hosts/carol/etc/init.d/iptables | 107 ++ .../ipv6/rw-psk-ikev2/hosts/carol/etc/ipsec.conf | 19 + .../rw-psk-ikev2/hosts/carol/etc/ipsec.secrets | 3 + .../rw-psk-ikev2/hosts/dave/etc/init.d/iptables | 107 ++ .../ipv6/rw-psk-ikev2/hosts/dave/etc/ipsec.conf | 20 + .../ipv6/rw-psk-ikev2/hosts/dave/etc/ipsec.secrets | 3 + .../rw-psk-ikev2/hosts/moon/etc/init.d/iptables | 107 ++ .../ipv6/rw-psk-ikev2/hosts/moon/etc/ipsec.conf | 19 + .../ipv6/rw-psk-ikev2/hosts/moon/etc/ipsec.secrets | 5 + testing/tests/ipv6/rw-psk-ikev2/posttest.dat | 9 + testing/tests/ipv6/rw-psk-ikev2/pretest.dat | 15 + testing/tests/ipv6/rw-psk-ikev2/test.conf | 21 + testing/tests/ipv6/transport-ikev1/description.txt | 5 + testing/tests/ipv6/transport-ikev1/evaltest.dat | 7 + .../transport-ikev1/hosts/moon/etc/init.d/iptables | 100 ++ .../ipv6/transport-ikev1/hosts/moon/etc/ipsec.conf | 23 + .../transport-ikev1/hosts/sun/etc/init.d/iptables | 100 ++ .../ipv6/transport-ikev1/hosts/sun/etc/ipsec.conf | 23 + testing/tests/ipv6/transport-ikev1/posttest.dat | 4 + testing/tests/ipv6/transport-ikev1/pretest.dat | 6 + testing/tests/ipv6/transport-ikev1/test.conf | 21 + testing/tests/ipv6/transport-ikev2/description.txt | 5 + testing/tests/ipv6/transport-ikev2/evaltest.dat | 8 + .../transport-ikev2/hosts/moon/etc/init.d/iptables | 107 ++ .../ipv6/transport-ikev2/hosts/moon/etc/ipsec.conf | 24 + .../transport-ikev2/hosts/sun/etc/init.d/iptables | 107 ++ .../ipv6/transport-ikev2/hosts/sun/etc/ipsec.conf | 24 + testing/tests/ipv6/transport-ikev2/posttest.dat | 4 + testing/tests/ipv6/transport-ikev2/pretest.dat | 6 + testing/tests/ipv6/transport-ikev2/test.conf | 21 + .../tests/p2pnat/behind-same-nat/description.txt | 6 + testing/tests/p2pnat/behind-same-nat/evaltest.dat | 11 + .../hosts/alice/etc/init.d/iptables | 78 ++ .../behind-same-nat/hosts/alice/etc/ipsec.conf | 36 + .../behind-same-nat/hosts/alice/etc/ipsec.secrets | 7 + .../hosts/carol/etc/init.d/iptables | 77 ++ .../behind-same-nat/hosts/carol/etc/ipsec.conf | 25 + .../behind-same-nat/hosts/carol/etc/ipsec.secrets | 11 + .../hosts/venus/etc/init.d/iptables | 78 ++ .../behind-same-nat/hosts/venus/etc/ipsec.conf | 36 + .../behind-same-nat/hosts/venus/etc/ipsec.secrets | 7 + testing/tests/p2pnat/behind-same-nat/posttest.dat | 8 + testing/tests/p2pnat/behind-same-nat/pretest.dat | 14 + testing/tests/p2pnat/behind-same-nat/test.conf | 21 + testing/tests/p2pnat/medsrv-psk/description.txt | 7 + testing/tests/p2pnat/medsrv-psk/evaltest.dat | 12 + .../medsrv-psk/hosts/alice/etc/init.d/iptables | 74 + .../p2pnat/medsrv-psk/hosts/alice/etc/ipsec.conf | 36 + .../medsrv-psk/hosts/alice/etc/ipsec.secrets | 7 + .../p2pnat/medsrv-psk/hosts/bob/etc/ipsec.conf | 36 + .../p2pnat/medsrv-psk/hosts/bob/etc/ipsec.secrets | 7 + .../medsrv-psk/hosts/carol/etc/init.d/iptables | 77 ++ .../p2pnat/medsrv-psk/hosts/carol/etc/ipsec.conf | 25 + .../medsrv-psk/hosts/carol/etc/ipsec.secrets | 9 + testing/tests/p2pnat/medsrv-psk/posttest.dat | 10 + testing/tests/p2pnat/medsrv-psk/pretest.dat | 19 + testing/tests/p2pnat/medsrv-psk/test.conf | 21 + 280 files changed, 11729 insertions(+), 3460 deletions(-) create mode 100644 src/charon/network/socket-raw.c create mode 100644 src/charon/sa/authenticators/eap/eap_aka.c create mode 100644 src/charon/sa/authenticators/eap/eap_aka.h create mode 100644 src/charon/sa/authenticators/eap/eap_md5.c create mode 100644 src/charon/sa/authenticators/eap/eap_md5.h create mode 100644 src/charon/sa/tasks/ike_auth_lifetime.c create mode 100644 src/charon/sa/tasks/ike_auth_lifetime.h create mode 100644 src/manager/controller/config_controller.c create mode 100644 src/manager/controller/config_controller.h create mode 100644 src/manager/controller/control_controller.c create mode 100644 src/manager/controller/control_controller.h create mode 100644 src/manager/controller/ikesa_controller.c create mode 100644 src/manager/controller/ikesa_controller.h delete mode 100644 src/manager/controller/status_controller.c delete mode 100644 src/manager/controller/status_controller.h create mode 100644 src/manager/templates/config/list.cs create mode 100644 src/manager/templates/control/result.cs create mode 100644 src/manager/templates/ikesa/list.cs create mode 100644 src/manager/templates/static/close.png create mode 100644 src/manager/templates/static/initiate.png create mode 100644 src/manager/templates/static/pipe-thin-green.png create mode 100644 src/manager/templates/static/pipe-thin-left-green.png create mode 100644 src/manager/templates/static/pipe-thin-right-green.png delete mode 100644 src/manager/templates/status/ikesalist.cs delete mode 100644 testing/hosts/winnetou/etc/apache2/httpd.conf create mode 100644 testing/hosts/winnetou/etc/apache2/modules.d/00_mod_mime.conf delete mode 100644 testing/hosts/winnetou/etc/conf.d/apache2 create mode 100644 testing/images/a-m-c-w-d-ip6.png create mode 100644 testing/images/a-m-c-w-ip6.png create mode 100644 testing/images/a-m-c-w-s-b-med.png create mode 100644 testing/images/a-m-w-s-b-ip6.png create mode 100644 testing/images/a-v-m-c-w-med.png create mode 100644 testing/images/m-w-s-ip6.png create mode 100644 testing/tests/ikev2/reauth-early/description.txt create mode 100644 testing/tests/ikev2/reauth-early/evaltest.dat create mode 100755 testing/tests/ikev2/reauth-early/hosts/carol/etc/ipsec.conf create mode 100755 testing/tests/ikev2/reauth-early/hosts/moon/etc/ipsec.conf create mode 100644 testing/tests/ikev2/reauth-early/posttest.dat create mode 100644 testing/tests/ikev2/reauth-early/pretest.dat create mode 100644 testing/tests/ikev2/reauth-early/test.conf create mode 100644 testing/tests/ikev2/reauth-late/description.txt create mode 100644 testing/tests/ikev2/reauth-late/evaltest.dat create mode 100755 testing/tests/ikev2/reauth-late/hosts/carol/etc/ipsec.conf create mode 100755 testing/tests/ikev2/reauth-late/hosts/moon/etc/ipsec.conf create mode 100644 testing/tests/ikev2/reauth-late/posttest.dat create mode 100644 testing/tests/ikev2/reauth-late/pretest.dat create mode 100644 testing/tests/ikev2/reauth-late/test.conf create mode 100644 testing/tests/ikev2/rw-eap-aka-rsa/description.txt create mode 100644 testing/tests/ikev2/rw-eap-aka-rsa/evaltest.dat create mode 100755 testing/tests/ikev2/rw-eap-aka-rsa/hosts/carol/etc/ipsec.conf create mode 100644 testing/tests/ikev2/rw-eap-aka-rsa/hosts/carol/etc/ipsec.secrets create mode 100755 testing/tests/ikev2/rw-eap-aka-rsa/hosts/moon/etc/ipsec.conf create mode 100644 testing/tests/ikev2/rw-eap-aka-rsa/hosts/moon/etc/ipsec.secrets create mode 100644 testing/tests/ikev2/rw-eap-aka-rsa/posttest.dat create mode 100644 testing/tests/ikev2/rw-eap-aka-rsa/pretest.dat create mode 100644 testing/tests/ikev2/rw-eap-aka-rsa/test.conf create mode 100755 testing/tests/ipv6/host2host-ikev1/hosts/moon/etc/init.d/iptables create mode 100755 testing/tests/ipv6/host2host-ikev1/hosts/sun/etc/init.d/iptables create mode 100755 testing/tests/ipv6/host2host-ikev2/hosts/moon/etc/init.d/iptables create mode 100755 testing/tests/ipv6/host2host-ikev2/hosts/sun/etc/init.d/iptables create mode 100644 testing/tests/ipv6/net2net-ikev1/description.txt create mode 100644 testing/tests/ipv6/net2net-ikev1/evaltest.dat create mode 100755 testing/tests/ipv6/net2net-ikev1/hosts/moon/etc/init.d/iptables create mode 100755 testing/tests/ipv6/net2net-ikev1/hosts/moon/etc/ipsec.conf create mode 100755 testing/tests/ipv6/net2net-ikev1/hosts/sun/etc/init.d/iptables create mode 100755 testing/tests/ipv6/net2net-ikev1/hosts/sun/etc/ipsec.conf create mode 100644 testing/tests/ipv6/net2net-ikev1/posttest.dat create mode 100644 testing/tests/ipv6/net2net-ikev1/pretest.dat create mode 100644 testing/tests/ipv6/net2net-ikev1/test.conf create mode 100644 testing/tests/ipv6/net2net-ikev2/description.txt create mode 100644 testing/tests/ipv6/net2net-ikev2/evaltest.dat create mode 100755 testing/tests/ipv6/net2net-ikev2/hosts/moon/etc/init.d/iptables create mode 100755 testing/tests/ipv6/net2net-ikev2/hosts/moon/etc/ipsec.conf create mode 100755 testing/tests/ipv6/net2net-ikev2/hosts/sun/etc/init.d/iptables create mode 100755 testing/tests/ipv6/net2net-ikev2/hosts/sun/etc/ipsec.conf create mode 100644 testing/tests/ipv6/net2net-ikev2/posttest.dat create mode 100644 testing/tests/ipv6/net2net-ikev2/pretest.dat create mode 100644 testing/tests/ipv6/net2net-ikev2/test.conf create mode 100644 testing/tests/ipv6/rw-ikev1/description.txt create mode 100644 testing/tests/ipv6/rw-ikev1/evaltest.dat create mode 100755 testing/tests/ipv6/rw-ikev1/hosts/carol/etc/init.d/iptables create mode 100755 testing/tests/ipv6/rw-ikev1/hosts/carol/etc/ipsec.conf create mode 100755 testing/tests/ipv6/rw-ikev1/hosts/moon/etc/init.d/iptables create mode 100755 testing/tests/ipv6/rw-ikev1/hosts/moon/etc/ipsec.conf create mode 100644 testing/tests/ipv6/rw-ikev1/posttest.dat create mode 100644 testing/tests/ipv6/rw-ikev1/pretest.dat create mode 100644 testing/tests/ipv6/rw-ikev1/test.conf create mode 100644 testing/tests/ipv6/rw-ikev2/description.txt create mode 100644 testing/tests/ipv6/rw-ikev2/evaltest.dat create mode 100755 testing/tests/ipv6/rw-ikev2/hosts/carol/etc/init.d/iptables create mode 100755 testing/tests/ipv6/rw-ikev2/hosts/carol/etc/ipsec.conf create mode 100755 testing/tests/ipv6/rw-ikev2/hosts/dave/etc/init.d/iptables create mode 100755 testing/tests/ipv6/rw-ikev2/hosts/dave/etc/ipsec.conf create mode 100755 testing/tests/ipv6/rw-ikev2/hosts/moon/etc/init.d/iptables create mode 100755 testing/tests/ipv6/rw-ikev2/hosts/moon/etc/ipsec.conf create mode 100644 testing/tests/ipv6/rw-ikev2/posttest.dat create mode 100644 testing/tests/ipv6/rw-ikev2/pretest.dat create mode 100644 testing/tests/ipv6/rw-ikev2/test.conf create mode 100644 testing/tests/ipv6/rw-psk-ikev1/description.txt create mode 100644 testing/tests/ipv6/rw-psk-ikev1/evaltest.dat create mode 100755 testing/tests/ipv6/rw-psk-ikev1/hosts/carol/etc/init.d/iptables create mode 100755 testing/tests/ipv6/rw-psk-ikev1/hosts/carol/etc/ipsec.conf create mode 100644 testing/tests/ipv6/rw-psk-ikev1/hosts/carol/etc/ipsec.secrets create mode 100755 testing/tests/ipv6/rw-psk-ikev1/hosts/moon/etc/init.d/iptables create mode 100755 testing/tests/ipv6/rw-psk-ikev1/hosts/moon/etc/ipsec.conf create mode 100644 testing/tests/ipv6/rw-psk-ikev1/hosts/moon/etc/ipsec.secrets create mode 100644 testing/tests/ipv6/rw-psk-ikev1/posttest.dat create mode 100644 testing/tests/ipv6/rw-psk-ikev1/pretest.dat create mode 100644 testing/tests/ipv6/rw-psk-ikev1/test.conf create mode 100644 testing/tests/ipv6/rw-psk-ikev2/description.txt create mode 100644 testing/tests/ipv6/rw-psk-ikev2/evaltest.dat create mode 100755 testing/tests/ipv6/rw-psk-ikev2/hosts/carol/etc/init.d/iptables create mode 100755 testing/tests/ipv6/rw-psk-ikev2/hosts/carol/etc/ipsec.conf create mode 100644 testing/tests/ipv6/rw-psk-ikev2/hosts/carol/etc/ipsec.secrets create mode 100755 testing/tests/ipv6/rw-psk-ikev2/hosts/dave/etc/init.d/iptables create mode 100755 testing/tests/ipv6/rw-psk-ikev2/hosts/dave/etc/ipsec.conf create mode 100644 testing/tests/ipv6/rw-psk-ikev2/hosts/dave/etc/ipsec.secrets create mode 100755 testing/tests/ipv6/rw-psk-ikev2/hosts/moon/etc/init.d/iptables create mode 100755 testing/tests/ipv6/rw-psk-ikev2/hosts/moon/etc/ipsec.conf create mode 100644 testing/tests/ipv6/rw-psk-ikev2/hosts/moon/etc/ipsec.secrets create mode 100644 testing/tests/ipv6/rw-psk-ikev2/posttest.dat create mode 100644 testing/tests/ipv6/rw-psk-ikev2/pretest.dat create mode 100644 testing/tests/ipv6/rw-psk-ikev2/test.conf create mode 100644 testing/tests/ipv6/transport-ikev1/description.txt create mode 100644 testing/tests/ipv6/transport-ikev1/evaltest.dat create mode 100755 testing/tests/ipv6/transport-ikev1/hosts/moon/etc/init.d/iptables create mode 100755 testing/tests/ipv6/transport-ikev1/hosts/moon/etc/ipsec.conf create mode 100755 testing/tests/ipv6/transport-ikev1/hosts/sun/etc/init.d/iptables create mode 100755 testing/tests/ipv6/transport-ikev1/hosts/sun/etc/ipsec.conf create mode 100644 testing/tests/ipv6/transport-ikev1/posttest.dat create mode 100644 testing/tests/ipv6/transport-ikev1/pretest.dat create mode 100644 testing/tests/ipv6/transport-ikev1/test.conf create mode 100644 testing/tests/ipv6/transport-ikev2/description.txt create mode 100644 testing/tests/ipv6/transport-ikev2/evaltest.dat create mode 100755 testing/tests/ipv6/transport-ikev2/hosts/moon/etc/init.d/iptables create mode 100755 testing/tests/ipv6/transport-ikev2/hosts/moon/etc/ipsec.conf create mode 100755 testing/tests/ipv6/transport-ikev2/hosts/sun/etc/init.d/iptables create mode 100755 testing/tests/ipv6/transport-ikev2/hosts/sun/etc/ipsec.conf create mode 100644 testing/tests/ipv6/transport-ikev2/posttest.dat create mode 100644 testing/tests/ipv6/transport-ikev2/pretest.dat create mode 100644 testing/tests/ipv6/transport-ikev2/test.conf create mode 100644 testing/tests/p2pnat/behind-same-nat/description.txt create mode 100644 testing/tests/p2pnat/behind-same-nat/evaltest.dat create mode 100755 testing/tests/p2pnat/behind-same-nat/hosts/alice/etc/init.d/iptables create mode 100755 testing/tests/p2pnat/behind-same-nat/hosts/alice/etc/ipsec.conf create mode 100644 testing/tests/p2pnat/behind-same-nat/hosts/alice/etc/ipsec.secrets create mode 100755 testing/tests/p2pnat/behind-same-nat/hosts/carol/etc/init.d/iptables create mode 100755 testing/tests/p2pnat/behind-same-nat/hosts/carol/etc/ipsec.conf create mode 100644 testing/tests/p2pnat/behind-same-nat/hosts/carol/etc/ipsec.secrets create mode 100755 testing/tests/p2pnat/behind-same-nat/hosts/venus/etc/init.d/iptables create mode 100755 testing/tests/p2pnat/behind-same-nat/hosts/venus/etc/ipsec.conf create mode 100644 testing/tests/p2pnat/behind-same-nat/hosts/venus/etc/ipsec.secrets create mode 100644 testing/tests/p2pnat/behind-same-nat/posttest.dat create mode 100644 testing/tests/p2pnat/behind-same-nat/pretest.dat create mode 100644 testing/tests/p2pnat/behind-same-nat/test.conf create mode 100644 testing/tests/p2pnat/medsrv-psk/description.txt create mode 100644 testing/tests/p2pnat/medsrv-psk/evaltest.dat create mode 100755 testing/tests/p2pnat/medsrv-psk/hosts/alice/etc/init.d/iptables create mode 100755 testing/tests/p2pnat/medsrv-psk/hosts/alice/etc/ipsec.conf create mode 100644 testing/tests/p2pnat/medsrv-psk/hosts/alice/etc/ipsec.secrets create mode 100755 testing/tests/p2pnat/medsrv-psk/hosts/bob/etc/ipsec.conf create mode 100644 testing/tests/p2pnat/medsrv-psk/hosts/bob/etc/ipsec.secrets create mode 100755 testing/tests/p2pnat/medsrv-psk/hosts/carol/etc/init.d/iptables create mode 100755 testing/tests/p2pnat/medsrv-psk/hosts/carol/etc/ipsec.conf create mode 100644 testing/tests/p2pnat/medsrv-psk/hosts/carol/etc/ipsec.secrets create mode 100644 testing/tests/p2pnat/medsrv-psk/posttest.dat create mode 100644 testing/tests/p2pnat/medsrv-psk/pretest.dat create mode 100644 testing/tests/p2pnat/medsrv-psk/test.conf diff --git a/NEWS b/NEWS index 0c3b6e311..37a70e5e2 100644 --- a/NEWS +++ b/NEWS @@ -1,7 +1,48 @@ +strongswan-4.1.10 +----------------- + +- Fixed error in the ordering of the certinfo_t records in the ocsp cache that + caused multiple entries of the same serial number to be created. + +- Implementation of a simple EAP-MD5 module which provides CHAP + authentication. This may be interesting in conjunction with certificate + based server authentication, as weak passwords can't be brute forced + (in contradiction to traditional IKEv2 PSK). + +- A complete software based implementation of EAP-AKA, using algorithms + specified in 3GPP2 (S.S0055). This implementation does not use an USIM, + but reads the secrets from ipsec.secrets. Make sure to read eap_aka.h + before using it. + +- Support for vendor specific EAP methods using Expanded EAP types. The + interface to EAP modules has been slightly changed, so make sure to + check the changes if you're already rolling your own modules. + +strongswan-4.1.9 +---------------- + +- The default _updown script now dynamically inserts and removes ip6tables + firewall rules if leftfirewall=yes is set in IPv6 connections. New IPv6 + net-net and roadwarrior (PSK/RSA) scenarios for both IKEv1 and IKEV2 were + added. + +- Implemented RFC4478 repeated authentication to force EAP/Virtual-IP clients + to reestablish an IKE_SA within a given timeframe. + +- strongSwan Manager supports configuration listing, initiation and termination + of IKE and CHILD_SAs. + +- Fixes and improvements to multithreading code. + +- IKEv2 plugins have been renamed to libcharon-* to avoid naming conflicts. + Make sure to remove the old plugins in $libexecdir/ipsec, otherwise they get + loaded twice. + + strongswan-4.1.8 ---------------- -- Removed recursive pthread mutexes since uClib doesn't support them. +- Removed recursive pthread mutexes since uClibc doesn't support them. strongswan-4.1.7 diff --git a/TODO b/TODO index 2ee7713f6..975db468f 100644 --- a/TODO +++ b/TODO @@ -7,15 +7,10 @@ migrate IKEv1 into charon. It's hard to say how much effort is needed to do that, and how much code we can reuse from pluto. But a port IS necessary to gain hassle-free configuration, version negotiation and maintainability. -Roadmap 2007 -============ +Roadmap +======= - Oct ! - modular credential backends - ! - enhance manager/XML interface - ! - Nov ! - Start IKEv1 implementation in charon - ! - Dec ! + Dec ! - complete modular credential framework ! TODO-List @@ -44,3 +39,13 @@ Misc ---- - Address pool/backend for virtual IP assignement - replace iterator by enumerator + +libstrongswan stuff +------------------- +- Header installation support (#include ?) +- move __constructor__/__destructor__ to a library init function +- object style for leak detective, include an API +- Cleanup/Refactor PEM/ASN1 stuff +- replace file reads through chunk_read +- rewrite lexparser in object-oriented style + diff --git a/configure b/configure index 575ea96fb..17efdfc15 100755 --- a/configure +++ b/configure @@ -1,6 +1,6 @@ #! /bin/sh # Guess values for system-dependent variables and create Makefiles. -# Generated by GNU Autoconf 2.61 for strongSwan 4.1.8. +# Generated by GNU Autoconf 2.61 for strongSwan 4.1.10. # # Copyright (C) 1992, 1993, 1994, 1995, 1996, 1998, 1999, 2000, 2001, # 2002, 2003, 2004, 2005, 2006 Free Software Foundation, Inc. @@ -726,8 +726,8 @@ SHELL=${CONFIG_SHELL-/bin/sh} # Identity of this package. PACKAGE_NAME='strongSwan' PACKAGE_TARNAME='strongswan' -PACKAGE_VERSION='4.1.8' -PACKAGE_STRING='strongSwan 4.1.8' +PACKAGE_VERSION='4.1.10' +PACKAGE_STRING='strongSwan 4.1.10' PACKAGE_BUGREPORT='' # Factoring default headers for most tests. @@ -860,6 +860,8 @@ USE_LIBCURL_TRUE USE_LIBCURL_FALSE USE_LIBLDAP_TRUE USE_LIBLDAP_FALSE +USE_STROKE_TRUE +USE_STROKE_FALSE USE_LIBDBUS_TRUE USE_LIBDBUS_FALSE USE_LIBXML_TRUE @@ -872,8 +874,14 @@ USE_CISCO_QUIRKS_TRUE USE_CISCO_QUIRKS_FALSE USE_LEAK_DETECTIVE_TRUE USE_LEAK_DETECTIVE_FALSE -BUILD_EAP_SIM_TRUE -BUILD_EAP_SIM_FALSE +USE_EAP_SIM_TRUE +USE_EAP_SIM_FALSE +USE_EAP_IDENTITY_TRUE +USE_EAP_IDENTITY_FALSE +USE_EAP_MD5_TRUE +USE_EAP_MD5_FALSE +USE_EAP_AKA_TRUE +USE_EAP_AKA_FALSE USE_NAT_TRANSPORT_TRUE USE_NAT_TRANSPORT_FALSE USE_VENDORID_TRUE @@ -890,6 +898,18 @@ USE_INTEGRITY_TEST_TRUE USE_INTEGRITY_TEST_FALSE USE_SELF_TEST_TRUE USE_SELF_TEST_FALSE +USE_PLUTO_TRUE +USE_PLUTO_FALSE +USE_CHARON_TRUE +USE_CHARON_FALSE +USE_TOOLS_TRUE +USE_TOOLS_FALSE +USE_PLUTO_OR_CHARON_TRUE +USE_PLUTO_OR_CHARON_FALSE +USE_LIBSTRONGSWAN_TRUE +USE_LIBSTRONGSWAN_FALSE +USE_FILE_CONFIG_TRUE +USE_FILE_CONFIG_FALSE build build_cpu build_vendor @@ -1453,7 +1473,7 @@ if test "$ac_init_help" = "long"; then # Omit some internal or obsolete options to make the list less imposing. # This message is too long to be a string in the A/UX 3.1 sh. cat <<_ACEOF -\`configure' configures strongSwan 4.1.8 to adapt to many kinds of systems. +\`configure' configures strongSwan 4.1.10 to adapt to many kinds of systems. Usage: $0 [OPTION]... [VAR=VALUE]... @@ -1523,7 +1543,7 @@ fi if test -n "$ac_init_help"; then case $ac_init_help in - short | recursive ) echo "Configuration of strongSwan 4.1.8:";; + short | recursive ) echo "Configuration of strongSwan 4.1.10:";; esac cat <<\_ACEOF @@ -1536,6 +1556,8 @@ Optional Features: over HTTP (default is NO). Requires libcurl. --enable-ldap enable fetching of CRLs from LDAP (default is NO). Requires openLDAP. + --disable-stroke disable charons stroke (pluto compatibility) + configuration backend. (default is NO). --enable-dbus enable DBUS configuration and control interface (default is NO). Requires libdbus. --enable-xml enable XML configuration and control interface @@ -1548,6 +1570,12 @@ Optional Features: NO). --enable-eap-sim build SIM authenication module for EAP (default is NO). + --enable-eap-identity build EAP module providing EAP-Identity helper + (default is NO). + --enable-eap-md5 build MD5 (CHAP) authenication module for EAP + (default is NO). + --enable-eap-aka build AKA authentication module for EAP (default is + NO). --enable-nat-transport enable NAT traversal with IPsec transport mode (default is NO). --disable-vendor-id disable the sending of the strongSwan vendor ID @@ -1561,6 +1589,12 @@ Optional Features: (default is NO). --disable-self-test disable the self-test of the crypto library (default is NO). + --disable-pluto disable the IKEv1 keying daemon pluto. (default is + NO). + --disable-charon disable the IKEv2 keying daemon charon. (default is + NO). + --disable-tools disable additional utilities (openac and + scepclient). (default is NO). --enable-shared[=PKGS] build shared libraries [default=yes] --enable-static[=PKGS] build static libraries [default=yes] --enable-fast-install[=PKGS] @@ -1699,7 +1733,7 @@ fi test -n "$ac_init_help" && exit $ac_status if $ac_init_version; then cat <<\_ACEOF -strongSwan configure 4.1.8 +strongSwan configure 4.1.10 generated by GNU Autoconf 2.61 Copyright (C) 1992, 1993, 1994, 1995, 1996, 1998, 1999, 2000, 2001, @@ -1713,7 +1747,7 @@ cat >config.log <<_ACEOF This file contains any messages produced by compilers while running configure, to aid debugging if configure makes a mistake. -It was created by strongSwan $as_me 4.1.8, which was +It was created by strongSwan $as_me 4.1.10, which was generated by GNU Autoconf 2.61. Invocation command line was $ $0 $@ @@ -2403,7 +2437,7 @@ fi # Define the identity of the package. PACKAGE='strongswan' - VERSION='4.1.8' + VERSION='4.1.10' cat >>confdefs.h <<_ACEOF @@ -4868,6 +4902,27 @@ else fi +# Check whether --enable-stroke was given. +if test "${enable_stroke+set}" = set; then + enableval=$enable_stroke; if test x$enableval = xyes; then + stroke=true + else + stroke=false + fi +else + stroke=true + +fi + + if test x$stroke = xtrue; then + USE_STROKE_TRUE= + USE_STROKE_FALSE='#' +else + USE_STROKE_TRUE='#' + USE_STROKE_FALSE= +fi + + # Check whether --enable-dbus was given. if test "${enable_dbus+set}" = set; then enableval=$enable_dbus; if test x$enableval = xyes; then @@ -4995,11 +5050,62 @@ if test "${enable_eap_sim+set}" = set; then fi if test x$eap_sim = xtrue; then - BUILD_EAP_SIM_TRUE= - BUILD_EAP_SIM_FALSE='#' + USE_EAP_SIM_TRUE= + USE_EAP_SIM_FALSE='#' +else + USE_EAP_SIM_TRUE='#' + USE_EAP_SIM_FALSE= +fi + + +# Check whether --enable-eap-identity was given. +if test "${enable_eap_identity+set}" = set; then + enableval=$enable_eap_identity; if test x$enableval = xyes; then + eap_identity=true + fi + +fi + + if test x$eap_identity = xtrue; then + USE_EAP_IDENTITY_TRUE= + USE_EAP_IDENTITY_FALSE='#' +else + USE_EAP_IDENTITY_TRUE='#' + USE_EAP_IDENTITY_FALSE= +fi + + +# Check whether --enable-eap-md5 was given. +if test "${enable_eap_md5+set}" = set; then + enableval=$enable_eap_md5; if test x$enableval = xyes; then + eap_md5=true + fi + +fi + + if test x$eap_md5 = xtrue; then + USE_EAP_MD5_TRUE= + USE_EAP_MD5_FALSE='#' else - BUILD_EAP_SIM_TRUE='#' - BUILD_EAP_SIM_FALSE= + USE_EAP_MD5_TRUE='#' + USE_EAP_MD5_FALSE= +fi + + +# Check whether --enable-eap-aka was given. +if test "${enable_eap_aka+set}" = set; then + enableval=$enable_eap_aka; if test x$enableval = xyes; then + eap_aka=true + fi + +fi + + if test x$eap_aka = xtrue; then + USE_EAP_AKA_TRUE= + USE_EAP_AKA_FALSE='#' +else + USE_EAP_AKA_TRUE='#' + USE_EAP_AKA_FALSE= fi @@ -5163,6 +5269,94 @@ else fi +# Check whether --enable-pluto was given. +if test "${enable_pluto+set}" = set; then + enableval=$enable_pluto; if test x$enableval = xyes; then + pluto=true + else + pluto=false + fi +else + pluto=true + +fi + + if test x$pluto = xtrue; then + USE_PLUTO_TRUE= + USE_PLUTO_FALSE='#' +else + USE_PLUTO_TRUE='#' + USE_PLUTO_FALSE= +fi + + +# Check whether --enable-charon was given. +if test "${enable_charon+set}" = set; then + enableval=$enable_charon; if test x$enableval = xyes; then + charon=true + else + charon=false + fi +else + charon=true + +fi + + if test x$charon = xtrue; then + USE_CHARON_TRUE= + USE_CHARON_FALSE='#' +else + USE_CHARON_TRUE='#' + USE_CHARON_FALSE= +fi + + +# Check whether --enable-tools was given. +if test "${enable_tools+set}" = set; then + enableval=$enable_tools; if test x$enableval = xyes; then + tools=true + else + tools=false + fi +else + tools=true + +fi + + if test x$tools = xtrue; then + USE_TOOLS_TRUE= + USE_TOOLS_FALSE='#' +else + USE_TOOLS_TRUE='#' + USE_TOOLS_FALSE= +fi + + + if test x$pluto = xtrue -o x$charon = xtrue; then + USE_PLUTO_OR_CHARON_TRUE= + USE_PLUTO_OR_CHARON_FALSE='#' +else + USE_PLUTO_OR_CHARON_TRUE='#' + USE_PLUTO_OR_CHARON_FALSE= +fi + + if test x$charon = xtrue -o x$tools = xtrue; then + USE_LIBSTRONGSWAN_TRUE= + USE_LIBSTRONGSWAN_FALSE='#' +else + USE_LIBSTRONGSWAN_TRUE='#' + USE_LIBSTRONGSWAN_FALSE= +fi + + if test x$pluto = xtrue -o x$stroke = xtrue; then + USE_FILE_CONFIG_TRUE= + USE_FILE_CONFIG_FALSE='#' +else + USE_FILE_CONFIG_TRUE='#' + USE_FILE_CONFIG_FALSE= +fi + + # Find a good install program. We prefer a C program (faster), # so one script is as good as another. But avoid the broken or @@ -5889,7 +6083,7 @@ ia64-*-hpux*) ;; *-*-irix6*) # Find out which ABI we are using. - echo '#line 5892 "configure"' > conftest.$ac_ext + echo '#line 6086 "configure"' > conftest.$ac_ext if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 (eval $ac_compile) 2>&5 ac_status=$? @@ -8210,11 +8404,11 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:8213: $lt_compile\"" >&5) + (eval echo "\"\$as_me:8407: $lt_compile\"" >&5) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&5 - echo "$as_me:8217: \$? = $ac_status" >&5 + echo "$as_me:8411: \$? = $ac_status" >&5 if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. @@ -8500,11 +8694,11 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:8503: $lt_compile\"" >&5) + (eval echo "\"\$as_me:8697: $lt_compile\"" >&5) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&5 - echo "$as_me:8507: \$? = $ac_status" >&5 + echo "$as_me:8701: \$? = $ac_status" >&5 if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. @@ -8604,11 +8798,11 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:8607: $lt_compile\"" >&5) + (eval echo "\"\$as_me:8801: $lt_compile\"" >&5) (eval "$lt_compile" 2>out/conftest.err) ac_status=$? cat out/conftest.err >&5 - echo "$as_me:8611: \$? = $ac_status" >&5 + echo "$as_me:8805: \$? = $ac_status" >&5 if (exit $ac_status) && test -s out/conftest2.$ac_objext then # The compiler can only warn and ignore the option if not recognized @@ -10962,7 +11156,7 @@ else lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_status=$lt_dlunknown cat > conftest.$ac_ext < conftest.$ac_ext <&5) + (eval echo "\"\$as_me:13674: $lt_compile\"" >&5) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&5 - echo "$as_me:13484: \$? = $ac_status" >&5 + echo "$as_me:13678: \$? = $ac_status" >&5 if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. @@ -13581,11 +13775,11 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:13584: $lt_compile\"" >&5) + (eval echo "\"\$as_me:13778: $lt_compile\"" >&5) (eval "$lt_compile" 2>out/conftest.err) ac_status=$? cat out/conftest.err >&5 - echo "$as_me:13588: \$? = $ac_status" >&5 + echo "$as_me:13782: \$? = $ac_status" >&5 if (exit $ac_status) && test -s out/conftest2.$ac_objext then # The compiler can only warn and ignore the option if not recognized @@ -15155,11 +15349,11 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:15158: $lt_compile\"" >&5) + (eval echo "\"\$as_me:15352: $lt_compile\"" >&5) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&5 - echo "$as_me:15162: \$? = $ac_status" >&5 + echo "$as_me:15356: \$? = $ac_status" >&5 if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. @@ -15259,11 +15453,11 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:15262: $lt_compile\"" >&5) + (eval echo "\"\$as_me:15456: $lt_compile\"" >&5) (eval "$lt_compile" 2>out/conftest.err) ac_status=$? cat out/conftest.err >&5 - echo "$as_me:15266: \$? = $ac_status" >&5 + echo "$as_me:15460: \$? = $ac_status" >&5 if (exit $ac_status) && test -s out/conftest2.$ac_objext then # The compiler can only warn and ignore the option if not recognized @@ -17454,11 +17648,11 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:17457: $lt_compile\"" >&5) + (eval echo "\"\$as_me:17651: $lt_compile\"" >&5) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&5 - echo "$as_me:17461: \$? = $ac_status" >&5 + echo "$as_me:17655: \$? = $ac_status" >&5 if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. @@ -17744,11 +17938,11 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:17747: $lt_compile\"" >&5) + (eval echo "\"\$as_me:17941: $lt_compile\"" >&5) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&5 - echo "$as_me:17751: \$? = $ac_status" >&5 + echo "$as_me:17945: \$? = $ac_status" >&5 if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. @@ -17848,11 +18042,11 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:17851: $lt_compile\"" >&5) + (eval echo "\"\$as_me:18045: $lt_compile\"" >&5) (eval "$lt_compile" 2>out/conftest.err) ac_status=$? cat out/conftest.err >&5 - echo "$as_me:17855: \$? = $ac_status" >&5 + echo "$as_me:18049: \$? = $ac_status" >&5 if (exit $ac_status) && test -s out/conftest2.$ac_objext then # The compiler can only warn and ignore the option if not recognized @@ -22888,6 +23082,13 @@ echo "$as_me: error: conditional \"USE_LIBLDAP\" was never defined. Usually this means the macro was only invoked conditionally." >&2;} { (exit 1); exit 1; }; } fi +if test -z "${USE_STROKE_TRUE}" && test -z "${USE_STROKE_FALSE}"; then + { { echo "$as_me:$LINENO: error: conditional \"USE_STROKE\" was never defined. +Usually this means the macro was only invoked conditionally." >&5 +echo "$as_me: error: conditional \"USE_STROKE\" was never defined. +Usually this means the macro was only invoked conditionally." >&2;} + { (exit 1); exit 1; }; } +fi if test -z "${USE_LIBDBUS_TRUE}" && test -z "${USE_LIBDBUS_FALSE}"; then { { echo "$as_me:$LINENO: error: conditional \"USE_LIBDBUS\" was never defined. Usually this means the macro was only invoked conditionally." >&5 @@ -22930,10 +23131,31 @@ echo "$as_me: error: conditional \"USE_LEAK_DETECTIVE\" was never defined. Usually this means the macro was only invoked conditionally." >&2;} { (exit 1); exit 1; }; } fi -if test -z "${BUILD_EAP_SIM_TRUE}" && test -z "${BUILD_EAP_SIM_FALSE}"; then - { { echo "$as_me:$LINENO: error: conditional \"BUILD_EAP_SIM\" was never defined. +if test -z "${USE_EAP_SIM_TRUE}" && test -z "${USE_EAP_SIM_FALSE}"; then + { { echo "$as_me:$LINENO: error: conditional \"USE_EAP_SIM\" was never defined. Usually this means the macro was only invoked conditionally." >&5 -echo "$as_me: error: conditional \"BUILD_EAP_SIM\" was never defined. +echo "$as_me: error: conditional \"USE_EAP_SIM\" was never defined. +Usually this means the macro was only invoked conditionally." >&2;} + { (exit 1); exit 1; }; } +fi +if test -z "${USE_EAP_IDENTITY_TRUE}" && test -z "${USE_EAP_IDENTITY_FALSE}"; then + { { echo "$as_me:$LINENO: error: conditional \"USE_EAP_IDENTITY\" was never defined. +Usually this means the macro was only invoked conditionally." >&5 +echo "$as_me: error: conditional \"USE_EAP_IDENTITY\" was never defined. +Usually this means the macro was only invoked conditionally." >&2;} + { (exit 1); exit 1; }; } +fi +if test -z "${USE_EAP_MD5_TRUE}" && test -z "${USE_EAP_MD5_FALSE}"; then + { { echo "$as_me:$LINENO: error: conditional \"USE_EAP_MD5\" was never defined. +Usually this means the macro was only invoked conditionally." >&5 +echo "$as_me: error: conditional \"USE_EAP_MD5\" was never defined. +Usually this means the macro was only invoked conditionally." >&2;} + { (exit 1); exit 1; }; } +fi +if test -z "${USE_EAP_AKA_TRUE}" && test -z "${USE_EAP_AKA_FALSE}"; then + { { echo "$as_me:$LINENO: error: conditional \"USE_EAP_AKA\" was never defined. +Usually this means the macro was only invoked conditionally." >&5 +echo "$as_me: error: conditional \"USE_EAP_AKA\" was never defined. Usually this means the macro was only invoked conditionally." >&2;} { (exit 1); exit 1; }; } fi @@ -22993,6 +23215,48 @@ echo "$as_me: error: conditional \"USE_SELF_TEST\" was never defined. Usually this means the macro was only invoked conditionally." >&2;} { (exit 1); exit 1; }; } fi +if test -z "${USE_PLUTO_TRUE}" && test -z "${USE_PLUTO_FALSE}"; then + { { echo "$as_me:$LINENO: error: conditional \"USE_PLUTO\" was never defined. +Usually this means the macro was only invoked conditionally." >&5 +echo "$as_me: error: conditional \"USE_PLUTO\" was never defined. +Usually this means the macro was only invoked conditionally." >&2;} + { (exit 1); exit 1; }; } +fi +if test -z "${USE_CHARON_TRUE}" && test -z "${USE_CHARON_FALSE}"; then + { { echo "$as_me:$LINENO: error: conditional \"USE_CHARON\" was never defined. +Usually this means the macro was only invoked conditionally." >&5 +echo "$as_me: error: conditional \"USE_CHARON\" was never defined. +Usually this means the macro was only invoked conditionally." >&2;} + { (exit 1); exit 1; }; } +fi +if test -z "${USE_TOOLS_TRUE}" && test -z "${USE_TOOLS_FALSE}"; then + { { echo "$as_me:$LINENO: error: conditional \"USE_TOOLS\" was never defined. +Usually this means the macro was only invoked conditionally." >&5 +echo "$as_me: error: conditional \"USE_TOOLS\" was never defined. +Usually this means the macro was only invoked conditionally." >&2;} + { (exit 1); exit 1; }; } +fi +if test -z "${USE_PLUTO_OR_CHARON_TRUE}" && test -z "${USE_PLUTO_OR_CHARON_FALSE}"; then + { { echo "$as_me:$LINENO: error: conditional \"USE_PLUTO_OR_CHARON\" was never defined. +Usually this means the macro was only invoked conditionally." >&5 +echo "$as_me: error: conditional \"USE_PLUTO_OR_CHARON\" was never defined. +Usually this means the macro was only invoked conditionally." >&2;} + { (exit 1); exit 1; }; } +fi +if test -z "${USE_LIBSTRONGSWAN_TRUE}" && test -z "${USE_LIBSTRONGSWAN_FALSE}"; then + { { echo "$as_me:$LINENO: error: conditional \"USE_LIBSTRONGSWAN\" was never defined. +Usually this means the macro was only invoked conditionally." >&5 +echo "$as_me: error: conditional \"USE_LIBSTRONGSWAN\" was never defined. +Usually this means the macro was only invoked conditionally." >&2;} + { (exit 1); exit 1; }; } +fi +if test -z "${USE_FILE_CONFIG_TRUE}" && test -z "${USE_FILE_CONFIG_FALSE}"; then + { { echo "$as_me:$LINENO: error: conditional \"USE_FILE_CONFIG\" was never defined. +Usually this means the macro was only invoked conditionally." >&5 +echo "$as_me: error: conditional \"USE_FILE_CONFIG\" was never defined. +Usually this means the macro was only invoked conditionally." >&2;} + { (exit 1); exit 1; }; } +fi if test -z "${am__fastdepCXX_TRUE}" && test -z "${am__fastdepCXX_FALSE}"; then { { echo "$as_me:$LINENO: error: conditional \"am__fastdepCXX\" was never defined. Usually this means the macro was only invoked conditionally." >&5 @@ -23307,7 +23571,7 @@ exec 6>&1 # report actual input values of CONFIG_FILES etc. instead of their # values after options handling. ac_log=" -This file was extended by strongSwan $as_me 4.1.8, which was +This file was extended by strongSwan $as_me 4.1.10, which was generated by GNU Autoconf 2.61. Invocation command line was CONFIG_FILES = $CONFIG_FILES @@ -23354,7 +23618,7 @@ Report bugs to ." _ACEOF cat >>$CONFIG_STATUS <<_ACEOF ac_cs_version="\\ -strongSwan config.status 4.1.8 +strongSwan config.status 4.1.10 configured by $0, generated by GNU Autoconf 2.61, with options \\"`echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`\\" @@ -23635,9 +23899,9 @@ USE_LIBCURL_TRUE!$USE_LIBCURL_TRUE$ac_delim USE_LIBCURL_FALSE!$USE_LIBCURL_FALSE$ac_delim USE_LIBLDAP_TRUE!$USE_LIBLDAP_TRUE$ac_delim USE_LIBLDAP_FALSE!$USE_LIBLDAP_FALSE$ac_delim +USE_STROKE_TRUE!$USE_STROKE_TRUE$ac_delim +USE_STROKE_FALSE!$USE_STROKE_FALSE$ac_delim USE_LIBDBUS_TRUE!$USE_LIBDBUS_TRUE$ac_delim -USE_LIBDBUS_FALSE!$USE_LIBDBUS_FALSE$ac_delim -USE_LIBXML_TRUE!$USE_LIBXML_TRUE$ac_delim _ACEOF if test `sed -n "s/.*$ac_delim\$/X/p" conf$$subs.sed | grep -c X` = 97; then @@ -23679,6 +23943,8 @@ _ACEOF ac_delim='%!_!# ' for ac_last_try in false false false false false :; do cat >conf$$subs.sed <<_ACEOF +USE_LIBDBUS_FALSE!$USE_LIBDBUS_FALSE$ac_delim +USE_LIBXML_TRUE!$USE_LIBXML_TRUE$ac_delim USE_LIBXML_FALSE!$USE_LIBXML_FALSE$ac_delim USE_LIBSQLITE_TRUE!$USE_LIBSQLITE_TRUE$ac_delim USE_LIBSQLITE_FALSE!$USE_LIBSQLITE_FALSE$ac_delim @@ -23688,8 +23954,14 @@ USE_CISCO_QUIRKS_TRUE!$USE_CISCO_QUIRKS_TRUE$ac_delim USE_CISCO_QUIRKS_FALSE!$USE_CISCO_QUIRKS_FALSE$ac_delim USE_LEAK_DETECTIVE_TRUE!$USE_LEAK_DETECTIVE_TRUE$ac_delim USE_LEAK_DETECTIVE_FALSE!$USE_LEAK_DETECTIVE_FALSE$ac_delim -BUILD_EAP_SIM_TRUE!$BUILD_EAP_SIM_TRUE$ac_delim -BUILD_EAP_SIM_FALSE!$BUILD_EAP_SIM_FALSE$ac_delim +USE_EAP_SIM_TRUE!$USE_EAP_SIM_TRUE$ac_delim +USE_EAP_SIM_FALSE!$USE_EAP_SIM_FALSE$ac_delim +USE_EAP_IDENTITY_TRUE!$USE_EAP_IDENTITY_TRUE$ac_delim +USE_EAP_IDENTITY_FALSE!$USE_EAP_IDENTITY_FALSE$ac_delim +USE_EAP_MD5_TRUE!$USE_EAP_MD5_TRUE$ac_delim +USE_EAP_MD5_FALSE!$USE_EAP_MD5_FALSE$ac_delim +USE_EAP_AKA_TRUE!$USE_EAP_AKA_TRUE$ac_delim +USE_EAP_AKA_FALSE!$USE_EAP_AKA_FALSE$ac_delim USE_NAT_TRANSPORT_TRUE!$USE_NAT_TRANSPORT_TRUE$ac_delim USE_NAT_TRANSPORT_FALSE!$USE_NAT_TRANSPORT_FALSE$ac_delim USE_VENDORID_TRUE!$USE_VENDORID_TRUE$ac_delim @@ -23706,6 +23978,18 @@ USE_INTEGRITY_TEST_TRUE!$USE_INTEGRITY_TEST_TRUE$ac_delim USE_INTEGRITY_TEST_FALSE!$USE_INTEGRITY_TEST_FALSE$ac_delim USE_SELF_TEST_TRUE!$USE_SELF_TEST_TRUE$ac_delim USE_SELF_TEST_FALSE!$USE_SELF_TEST_FALSE$ac_delim +USE_PLUTO_TRUE!$USE_PLUTO_TRUE$ac_delim +USE_PLUTO_FALSE!$USE_PLUTO_FALSE$ac_delim +USE_CHARON_TRUE!$USE_CHARON_TRUE$ac_delim +USE_CHARON_FALSE!$USE_CHARON_FALSE$ac_delim +USE_TOOLS_TRUE!$USE_TOOLS_TRUE$ac_delim +USE_TOOLS_FALSE!$USE_TOOLS_FALSE$ac_delim +USE_PLUTO_OR_CHARON_TRUE!$USE_PLUTO_OR_CHARON_TRUE$ac_delim +USE_PLUTO_OR_CHARON_FALSE!$USE_PLUTO_OR_CHARON_FALSE$ac_delim +USE_LIBSTRONGSWAN_TRUE!$USE_LIBSTRONGSWAN_TRUE$ac_delim +USE_LIBSTRONGSWAN_FALSE!$USE_LIBSTRONGSWAN_FALSE$ac_delim +USE_FILE_CONFIG_TRUE!$USE_FILE_CONFIG_TRUE$ac_delim +USE_FILE_CONFIG_FALSE!$USE_FILE_CONFIG_FALSE$ac_delim build!$build$ac_delim build_cpu!$build_cpu$ac_delim build_vendor!$build_vendor$ac_delim @@ -23746,7 +24030,7 @@ LIBOBJS!$LIBOBJS$ac_delim LTLIBOBJS!$LTLIBOBJS$ac_delim _ACEOF - if test `sed -n "s/.*$ac_delim\$/X/p" conf$$subs.sed | grep -c X` = 65; then + if test `sed -n "s/.*$ac_delim\$/X/p" conf$$subs.sed | grep -c X` = 85; then break elif $ac_last_try; then { { echo "$as_me:$LINENO: error: could not make $CONFIG_STATUS" >&5 diff --git a/configure.in b/configure.in index 751375439..4b0b0ed56 100644 --- a/configure.in +++ b/configure.in @@ -16,7 +16,7 @@ dnl =========================== dnl initialize & set some vars dnl =========================== -AC_INIT(strongSwan,4.1.8) +AC_INIT(strongSwan,4.1.10) AM_INIT_AUTOMAKE(tar-ustar) AC_C_BIGENDIAN AC_SUBST(confdir, '${sysconfdir}') @@ -155,6 +155,18 @@ AC_ARG_ENABLE( ) AM_CONDITIONAL(USE_LIBLDAP, test x$ldap = xtrue) +AC_ARG_ENABLE( + [stroke], + AS_HELP_STRING([--disable-stroke],[disable charons stroke (pluto compatibility) configuration backend. (default is NO).]), + [if test x$enableval = xyes; then + stroke=true + else + stroke=false + fi], + stroke=true +) +AM_CONDITIONAL(USE_STROKE, test x$stroke = xtrue) + AC_ARG_ENABLE( [dbus], AS_HELP_STRING([--enable-dbus],[enable DBUS configuration and control interface (default is NO). Requires libdbus.]), @@ -220,7 +232,34 @@ AC_ARG_ENABLE( eap_sim=true fi] ) -AM_CONDITIONAL(BUILD_EAP_SIM, test x$eap_sim = xtrue) +AM_CONDITIONAL(USE_EAP_SIM, test x$eap_sim = xtrue) + +AC_ARG_ENABLE( + [eap-identity], + AS_HELP_STRING([--enable-eap-identity],[build EAP module providing EAP-Identity helper (default is NO).]), + [if test x$enableval = xyes; then + eap_identity=true + fi] +) +AM_CONDITIONAL(USE_EAP_IDENTITY, test x$eap_identity = xtrue) + +AC_ARG_ENABLE( + [eap-md5], + AS_HELP_STRING([--enable-eap-md5],[build MD5 (CHAP) authenication module for EAP (default is NO).]), + [if test x$enableval = xyes; then + eap_md5=true + fi] +) +AM_CONDITIONAL(USE_EAP_MD5, test x$eap_md5 = xtrue) + +AC_ARG_ENABLE( + [eap-aka], + AS_HELP_STRING([--enable-eap-aka],[build AKA authentication module for EAP (default is NO).]), + [if test x$enableval = xyes; then + eap_aka=true + fi] +) +AM_CONDITIONAL(USE_EAP_AKA, test x$eap_aka = xtrue) AC_ARG_ENABLE( [nat-transport], @@ -306,6 +345,46 @@ AC_ARG_ENABLE( ) AM_CONDITIONAL(USE_SELF_TEST, test x$self_test = xtrue) +AC_ARG_ENABLE( + [pluto], + AS_HELP_STRING([--disable-pluto],[disable the IKEv1 keying daemon pluto. (default is NO).]), + [if test x$enableval = xyes; then + pluto=true + else + pluto=false + fi], + pluto=true +) +AM_CONDITIONAL(USE_PLUTO, test x$pluto = xtrue) + +AC_ARG_ENABLE( + [charon], + AS_HELP_STRING([--disable-charon],[disable the IKEv2 keying daemon charon. (default is NO).]), + [if test x$enableval = xyes; then + charon=true + else + charon=false + fi], + charon=true +) +AM_CONDITIONAL(USE_CHARON, test x$charon = xtrue) + +AC_ARG_ENABLE( + [tools], + AS_HELP_STRING([--disable-tools],[disable additional utilities (openac and scepclient). (default is NO).]), + [if test x$enableval = xyes; then + tools=true + else + tools=false + fi], + tools=true +) +AM_CONDITIONAL(USE_TOOLS, test x$tools = xtrue) + +AM_CONDITIONAL(USE_PLUTO_OR_CHARON, test x$pluto = xtrue -o x$charon = xtrue) +AM_CONDITIONAL(USE_LIBSTRONGSWAN, test x$charon = xtrue -o x$tools = xtrue) +AM_CONDITIONAL(USE_FILE_CONFIG, test x$pluto = xtrue -o x$stroke = xtrue) + dnl ========================= dnl check required programs dnl ========================= @@ -335,13 +414,13 @@ if test "$http" = "true"; then fi if test "$xml" = "true"; then - PKG_CHECK_MODULES(xml, libxml-2.0,, AC_MSG_ERROR([No libxml2 package information found])) + PKG_CHECK_MODULES(xml, [libxml-2.0],, AC_MSG_ERROR([No libxml2 package information found])) AC_SUBST(xml_CFLAGS) AC_SUBST(xml_LIBS) fi if test "$dbus" = "true"; then - PKG_CHECK_MODULES(dbus, dbus-1,, AC_MSG_ERROR([No libdbus package information found])) + PKG_CHECK_MODULES(dbus, [dbus-1],, AC_MSG_ERROR([No libdbus package information found])) AC_SUBST(dbus_CFLAGS) AC_SUBST(dbus_LIBS) fi diff --git a/src/Makefile.am b/src/Makefile.am index 4d41ea9e5..e01ad84b4 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -1,4 +1,31 @@ -SUBDIRS = include libfreeswan libcrypto libstrongswan pluto whack charon stroke starter openac scepclient ipsec _updown _updown_espmark _copyright +SUBDIRS = include + +if USE_FILE_CONFIG + SUBDIRS += libfreeswan starter ipsec _copyright +endif + +if USE_LIBSTRONGSWAN + SUBDIRS += libstrongswan +endif + +if USE_PLUTO + SUBDIRS += libcrypto pluto whack +endif +if USE_CHARON + SUBDIRS += charon +endif + +if USE_STROKE + SUBDIRS += stroke +endif + +if USE_PLUTO_OR_CHARON + SUBDIRS += _updown _updown_espmark +endif + +if USE_TOOLS + SUBDIRS += openac scepclient +endif if USE_UML SUBDIRS += dumm @@ -8,3 +35,16 @@ if USE_MANAGER SUBDIRS += manager endif +if USE_FILE_CONFIG +install-exec-local : + mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d + mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/cacerts + mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/ocspcerts + mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/certs + mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/acerts + mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/aacerts + mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/crls + mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/reqs + mkdir -p -m 700 $(DESTDIR)$(confdir)/ipsec.d/private +endif + diff --git a/src/Makefile.in b/src/Makefile.in index aea3c7a2b..f2e6dcefe 100644 --- a/src/Makefile.in +++ b/src/Makefile.in @@ -31,8 +31,15 @@ PRE_UNINSTALL = : POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ -@USE_UML_TRUE@am__append_1 = dumm -@USE_MANAGER_TRUE@am__append_2 = manager +@USE_FILE_CONFIG_TRUE@am__append_1 = libfreeswan starter ipsec _copyright +@USE_LIBSTRONGSWAN_TRUE@am__append_2 = libstrongswan +@USE_PLUTO_TRUE@am__append_3 = libcrypto pluto whack +@USE_CHARON_TRUE@am__append_4 = charon +@USE_STROKE_TRUE@am__append_5 = stroke +@USE_PLUTO_OR_CHARON_TRUE@am__append_6 = _updown _updown_espmark +@USE_TOOLS_TRUE@am__append_7 = openac scepclient +@USE_UML_TRUE@am__append_8 = dumm +@USE_MANAGER_TRUE@am__append_9 = manager subdir = src DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 @@ -54,9 +61,9 @@ RECURSIVE_CLEAN_TARGETS = mostlyclean-recursive clean-recursive \ distclean-recursive maintainer-clean-recursive ETAGS = etags CTAGS = ctags -DIST_SUBDIRS = include libfreeswan libcrypto libstrongswan pluto whack \ - charon stroke starter openac scepclient ipsec _updown \ - _updown_espmark _copyright dumm manager +DIST_SUBDIRS = include libfreeswan starter ipsec _copyright \ + libstrongswan libcrypto pluto whack charon stroke _updown \ + _updown_espmark openac scepclient dumm manager DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) ACLOCAL = @ACLOCAL@ AMTAR = @AMTAR@ @@ -188,9 +195,9 @@ top_builddir = @top_builddir@ top_srcdir = @top_srcdir@ xml_CFLAGS = @xml_CFLAGS@ xml_LIBS = @xml_LIBS@ -SUBDIRS = include libfreeswan libcrypto libstrongswan pluto whack \ - charon stroke starter openac scepclient ipsec _updown \ - _updown_espmark _copyright $(am__append_1) $(am__append_2) +SUBDIRS = include $(am__append_1) $(am__append_2) $(am__append_3) \ + $(am__append_4) $(am__append_5) $(am__append_6) \ + $(am__append_7) $(am__append_8) $(am__append_9) all: all-recursive .SUFFIXES: @@ -433,6 +440,7 @@ distclean-generic: maintainer-clean-generic: @echo "This command is intended for maintainers to use" @echo "it deletes files that may require special tools to rebuild." +@USE_FILE_CONFIG_FALSE@install-exec-local: clean: clean-recursive clean-am: clean-generic clean-libtool mostlyclean-am @@ -455,7 +463,7 @@ install-data-am: install-dvi: install-dvi-recursive -install-exec-am: +install-exec-am: install-exec-local install-html: install-html-recursive @@ -496,14 +504,25 @@ uninstall-am: distclean-libtool distclean-tags distdir dvi dvi-am html \ html-am info info-am install install-am install-data \ install-data-am install-dvi install-dvi-am install-exec \ - install-exec-am install-html install-html-am install-info \ - install-info-am install-man install-pdf install-pdf-am \ - install-ps install-ps-am install-strip installcheck \ - installcheck-am installdirs installdirs-am maintainer-clean \ - maintainer-clean-generic mostlyclean mostlyclean-generic \ - mostlyclean-libtool pdf pdf-am ps ps-am tags tags-recursive \ - uninstall uninstall-am - + install-exec-am install-exec-local install-html \ + install-html-am install-info install-info-am install-man \ + install-pdf install-pdf-am install-ps install-ps-am \ + install-strip installcheck installcheck-am installdirs \ + installdirs-am maintainer-clean maintainer-clean-generic \ + mostlyclean mostlyclean-generic mostlyclean-libtool pdf pdf-am \ + ps ps-am tags tags-recursive uninstall uninstall-am + + +@USE_FILE_CONFIG_TRUE@install-exec-local : +@USE_FILE_CONFIG_TRUE@ mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d +@USE_FILE_CONFIG_TRUE@ mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/cacerts +@USE_FILE_CONFIG_TRUE@ mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/ocspcerts +@USE_FILE_CONFIG_TRUE@ mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/certs +@USE_FILE_CONFIG_TRUE@ mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/acerts +@USE_FILE_CONFIG_TRUE@ mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/aacerts +@USE_FILE_CONFIG_TRUE@ mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/crls +@USE_FILE_CONFIG_TRUE@ mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/reqs +@USE_FILE_CONFIG_TRUE@ mkdir -p -m 700 $(DESTDIR)$(confdir)/ipsec.d/private # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. .NOEXPORT: diff --git a/src/_updown/Makefile.am b/src/_updown/Makefile.am index d0b7a27a4..9fd592797 100644 --- a/src/_updown/Makefile.am +++ b/src/_updown/Makefile.am @@ -5,6 +5,7 @@ EXTRA_DIST = _updown.in _updown : _updown.in sed \ + -e "s:@IPSEC_SBINDIR@:$(sbindir):" \ -e "s:\@IPSEC_ROUTING_TABLE\@:$(IPSEC_ROUTING_TABLE):" \ -e "s:\@IPSEC_ROUTING_TABLE_PRIO\@:$(IPSEC_ROUTING_TABLE_PRIO):" \ $< > $@ diff --git a/src/_updown/Makefile.in b/src/_updown/Makefile.in index 21e38da5d..52f1109e5 100644 --- a/src/_updown/Makefile.in +++ b/src/_updown/Makefile.in @@ -425,6 +425,7 @@ uninstall-man: uninstall-man8 _updown : _updown.in sed \ + -e "s:@IPSEC_SBINDIR@:$(sbindir):" \ -e "s:\@IPSEC_ROUTING_TABLE\@:$(IPSEC_ROUTING_TABLE):" \ -e "s:\@IPSEC_ROUTING_TABLE_PRIO\@:$(IPSEC_ROUTING_TABLE_PRIO):" \ $< > $@ diff --git a/src/_updown/_updown.in b/src/_updown/_updown.in index 4002449dd..cb0404b34 100644 --- a/src/_updown/_updown.in +++ b/src/_updown/_updown.in @@ -16,7 +16,7 @@ # or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License # for more details. # -# RCSID $Id: _updown.in 3268 2007-10-08 19:59:18Z andreas $ +# RCSID $Id: _updown.in 3389 2007-12-12 22:12:10Z andreas $ # CAUTION: Installing a new version of strongSwan will install a new # copy of this script, wiping out any custom changes you make. If @@ -118,6 +118,10 @@ # restricted on the peer side. # +# define a minimum PATH environment in case it is not set +PATH="/sbin:/bin:/usr/sbin:/usr/bin:@IPSEC_SBINDIR@" +export PATH + # uncomment to log VPN connections VPN_LOGGING=1 # @@ -372,11 +376,11 @@ up-host:iptables) # This is used only by the default updown script, not by your custom # ones, so do not mess with it; see CAUTION comment up at top. iptables -I INPUT 1 -i $PLUTO_INTERFACE -p $PLUTO_MY_PROTOCOL \ - -s $PLUTO_PEER_CLIENT_NET/$PLUTO_PEER_CLIENT_MASK $S_PEER_PORT \ + -s $PLUTO_PEER_CLIENT $S_PEER_PORT \ -d $PLUTO_ME $D_MY_PORT $IPSEC_POLICY_IN -j ACCEPT iptables -I OUTPUT 1 -o $PLUTO_INTERFACE -p $PLUTO_PEER_PROTOCOL \ -s $PLUTO_ME $S_MY_PORT $IPSEC_POLICY_OUT \ - -d $PLUTO_PEER_CLIENT_NET/$PLUTO_PEER_CLIENT_MASK $D_PEER_PORT -j ACCEPT + -d $PLUTO_PEER_CLIENT $D_PEER_PORT -j ACCEPT # # log IPsec host connection setup if [ $VPN_LOGGING ] @@ -396,11 +400,11 @@ down-host:iptables) # This is used only by the default updown script, not by your custom # ones, so do not mess with it; see CAUTION comment up at top. iptables -D INPUT -i $PLUTO_INTERFACE -p $PLUTO_MY_PROTOCOL \ - -s $PLUTO_PEER_CLIENT_NET/$PLUTO_PEER_CLIENT_MASK $S_PEER_PORT \ + -s $PLUTO_PEER_CLIENT $S_PEER_PORT \ -d $PLUTO_ME $D_MY_PORT $IPSEC_POLICY_IN -j ACCEPT iptables -D OUTPUT -o $PLUTO_INTERFACE -p $PLUTO_PEER_PROTOCOL \ -s $PLUTO_ME $S_MY_PORT $IPSEC_POLICY_OUT \ - -d $PLUTO_PEER_CLIENT_NET/$PLUTO_PEER_CLIENT_MASK $D_PEER_PORT -j ACCEPT + -d $PLUTO_PEER_CLIENT $D_PEER_PORT -j ACCEPT # # log IPsec host connection teardown if [ $VPN_LOGGING ] @@ -422,13 +426,11 @@ up-client:iptables) if [ "$PLUTO_PEER_CLIENT" != "$PLUTO_MY_SOURCEIP/32" ] then iptables -I FORWARD 1 -o $PLUTO_INTERFACE -p $PLUTO_PEER_PROTOCOL \ - -s $PLUTO_MY_CLIENT_NET/$PLUTO_MY_CLIENT_MASK $S_MY_PORT \ - -d $PLUTO_PEER_CLIENT_NET/$PLUTO_PEER_CLIENT_MASK $D_PEER_PORT \ - $IPSEC_POLICY_OUT -j ACCEPT + -s $PLUTO_MY_CLIENT $S_MY_PORT \ + -d $PLUTO_PEER_CLIENT $D_PEER_PORT $IPSEC_POLICY_OUT -j ACCEPT iptables -I FORWARD 1 -i $PLUTO_INTERFACE -p $PLUTO_MY_PROTOCOL \ - -s $PLUTO_PEER_CLIENT_NET/$PLUTO_PEER_CLIENT_MASK $S_PEER_PORT \ - -d $PLUTO_MY_CLIENT_NET/$PLUTO_MY_CLIENT_MASK $D_MY_PORT \ - $IPSEC_POLICY_IN -j ACCEPT + -s $PLUTO_PEER_CLIENT $S_PEER_PORT \ + -d $PLUTO_MY_CLIENT $D_MY_PORT $IPSEC_POLICY_IN -j ACCEPT fi # # a virtual IP requires an INPUT and OUTPUT rule on the host @@ -436,13 +438,11 @@ up-client:iptables) if [ -n "$PLUTO_MY_SOURCEIP" -o -n "$PLUTO_HOST_ACCESS" ] then iptables -I INPUT 1 -i $PLUTO_INTERFACE -p $PLUTO_MY_PROTOCOL \ - -s $PLUTO_PEER_CLIENT_NET/$PLUTO_PEER_CLIENT_MASK $S_PEER_PORT \ - -d $PLUTO_MY_CLIENT_NET/$PLUTO_MY_CLIENT_MASK $D_MY_PORT \ - $IPSEC_POLICY_IN -j ACCEPT + -s $PLUTO_PEER_CLIENT $S_PEER_PORT \ + -d $PLUTO_MY_CLIENT $D_MY_PORT $IPSEC_POLICY_IN -j ACCEPT iptables -I OUTPUT 1 -o $PLUTO_INTERFACE -p $PLUTO_PEER_PROTOCOL \ - -s $PLUTO_MY_CLIENT_NET/$PLUTO_MY_CLIENT_MASK $S_MY_PORT \ - -d $PLUTO_PEER_CLIENT_NET/$PLUTO_PEER_CLIENT_MASK $D_PEER_PORT \ - $IPSEC_POLICY_OUT -j ACCEPT + -s $PLUTO_MY_CLIENT $S_MY_PORT \ + -d $PLUTO_PEER_CLIENT $D_PEER_PORT $IPSEC_POLICY_OUT -j ACCEPT fi # # log IPsec client connection setup @@ -465,12 +465,12 @@ down-client:iptables) if [ "$PLUTO_PEER_CLIENT" != "$PLUTO_MY_SOURCEIP/32" ] then iptables -D FORWARD -o $PLUTO_INTERFACE -p $PLUTO_PEER_PROTOCOL \ - -s $PLUTO_MY_CLIENT_NET/$PLUTO_MY_CLIENT_MASK $S_MY_PORT \ - -d $PLUTO_PEER_CLIENT_NET/$PLUTO_PEER_CLIENT_MASK $D_PEER_PORT \ + -s $PLUTO_MY_CLIENT $S_MY_PORT \ + -d $PLUTO_PEER_CLIENT $D_PEER_PORT \ $IPSEC_POLICY_OUT -j ACCEPT iptables -D FORWARD -i $PLUTO_INTERFACE -p $PLUTO_MY_PROTOCOL \ - -s $PLUTO_PEER_CLIENT_NET/$PLUTO_PEER_CLIENT_MASK $S_PEER_PORT \ - -d $PLUTO_MY_CLIENT_NET/$PLUTO_MY_CLIENT_MASK $D_MY_PORT \ + -s $PLUTO_PEER_CLIENT $S_PEER_PORT \ + -d $PLUTO_MY_CLIENT $D_MY_PORT \ $IPSEC_POLICY_IN -j ACCEPT fi # @@ -479,12 +479,12 @@ down-client:iptables) if [ -n "$PLUTO_MY_SOURCEIP" -o -n "$PLUTO_HOST_ACCESS" ] then iptables -D INPUT -i $PLUTO_INTERFACE -p $PLUTO_MY_PROTOCOL \ - -s $PLUTO_PEER_CLIENT_NET/$PLUTO_PEER_CLIENT_MASK $S_PEER_PORT \ - -d $PLUTO_MY_CLIENT_NET/$PLUTO_MY_CLIENT_MASK $D_MY_PORT \ + -s $PLUTO_PEER_CLIENT $S_PEER_PORT \ + -d $PLUTO_MY_CLIENT $D_MY_PORT \ $IPSEC_POLICY_IN -j ACCEPT iptables -D OUTPUT -o $PLUTO_INTERFACE -p $PLUTO_PEER_PROTOCOL \ - -s $PLUTO_MY_CLIENT_NET/$PLUTO_MY_CLIENT_MASK $S_MY_PORT \ - -d $PLUTO_PEER_CLIENT_NET/$PLUTO_PEER_CLIENT_MASK $D_PEER_PORT \ + -s $PLUTO_MY_CLIENT $S_MY_PORT \ + -d $PLUTO_PEER_CLIENT $D_PEER_PORT \ $IPSEC_POLICY_OUT -j ACCEPT fi # @@ -514,11 +514,11 @@ unroute-host-v6:*|unroute-client-v6:*) # connection to me or my client subnet being unrouted #downroute_v6 ;; -up-host-v6:*) +up-host-v6:) # connection to me coming up # If you are doing a custom version, firewall commands go here. ;; -down-host-v6:*) +down-host-v6:) # connection to me going down # If you are doing a custom version, firewall commands go here. ;; @@ -530,6 +530,136 @@ down-client-v6:) # connection to my client subnet going down # If you are doing a custom version, firewall commands go here. ;; +up-host-v6:iptables) + # connection to me, with (left/right)firewall=yes, coming up + # This is used only by the default updown script, not by your custom + # ones, so do not mess with it; see CAUTION comment up at top. + ip6tables -I INPUT 1 -i $PLUTO_INTERFACE -p $PLUTO_MY_PROTOCOL \ + -s $PLUTO_PEER_CLIENT $S_PEER_PORT \ + -d $PLUTO_ME $D_MY_PORT $IPSEC_POLICY_IN -j ACCEPT + ip6tables -I OUTPUT 1 -o $PLUTO_INTERFACE -p $PLUTO_PEER_PROTOCOL \ + -s $PLUTO_ME $S_MY_PORT $IPSEC_POLICY_OUT \ + -d $PLUTO_PEER_CLIENT $D_PEER_PORT -j ACCEPT + # + # log IPsec host connection setup + if [ $VPN_LOGGING ] + then + if [ "$PLUTO_PEER_CLIENT" == "$PLUTO_PEER/128" ] + then + logger -t $TAG -p $FAC_PRIO \ + "+ `echo -e $PLUTO_PEER_ID` $PLUTO_PEER -- $PLUTO_ME" + else + logger -t $TAG -p $FAC_PRIO \ + "+ `echo -e $PLUTO_PEER_ID` $PLUTO_PEER_CLIENT == $PLUTO_PEER -- $PLUTO_ME" + fi + fi + ;; +down-host-v6:iptables) + # connection to me, with (left/right)firewall=yes, going down + # This is used only by the default updown script, not by your custom + # ones, so do not mess with it; see CAUTION comment up at top. + ip6tables -D INPUT -i $PLUTO_INTERFACE -p $PLUTO_MY_PROTOCOL \ + -s $PLUTO_PEER_CLIENT $S_PEER_PORT \ + -d $PLUTO_ME $D_MY_PORT $IPSEC_POLICY_IN -j ACCEPT + ip6tables -D OUTPUT -o $PLUTO_INTERFACE -p $PLUTO_PEER_PROTOCOL \ + -s $PLUTO_ME $S_MY_PORT $IPSEC_POLICY_OUT \ + -d $PLUTO_PEER_CLIENT $D_PEER_PORT -j ACCEPT + # + # log IPsec host connection teardown + if [ $VPN_LOGGING ] + then + if [ "$PLUTO_PEER_CLIENT" == "$PLUTO_PEER/128" ] + then + logger -t $TAG -p $FAC_PRIO -- \ + "- `echo -e $PLUTO_PEER_ID` $PLUTO_PEER -- $PLUTO_ME" + else + logger -t $TAG -p $FAC_PRIO -- \ + "- `echo -e $PLUTO_PEER_ID` $PLUTO_PEER_CLIENT == $PLUTO_PEER -- $PLUTO_ME" + fi + fi + ;; +up-client-v6:iptables) + # connection to client subnet, with (left/right)firewall=yes, coming up + # This is used only by the default updown script, not by your custom + # ones, so do not mess with it; see CAUTION comment up at top. + if [ "$PLUTO_PEER_CLIENT" != "$PLUTO_MY_SOURCEIP/128" ] + then + ip6tables -I FORWARD 1 -o $PLUTO_INTERFACE -p $PLUTO_PEER_PROTOCOL \ + -s $PLUTO_MY_CLIENT $S_MY_PORT \ + -d $PLUTO_PEER_CLIENT $D_PEER_PORT $IPSEC_POLICY_OUT -j ACCEPT + ip6tables -I FORWARD 1 -i $PLUTO_INTERFACE -p $PLUTO_MY_PROTOCOL \ + -s $PLUTO_PEER_CLIENT $S_PEER_PORT \ + -d $PLUTO_MY_CLIENT $D_MY_PORT $IPSEC_POLICY_IN -j ACCEPT + fi + # + # a virtual IP requires an INPUT and OUTPUT rule on the host + # or sometimes host access via the internal IP is needed + if [ -n "$PLUTO_MY_SOURCEIP" -o -n "$PLUTO_HOST_ACCESS" ] + then + ip6tables -I INPUT 1 -i $PLUTO_INTERFACE -p $PLUTO_MY_PROTOCOL \ + -s $PLUTO_PEER_CLIENT $S_PEER_PORT \ + -d $PLUTO_MY_CLIENT $D_MY_PORT $IPSEC_POLICY_IN -j ACCEPT + ip6tables -I OUTPUT 1 -o $PLUTO_INTERFACE -p $PLUTO_PEER_PROTOCOL \ + -s $PLUTO_MY_CLIENT $S_MY_PORT \ + -d $PLUTO_PEER_CLIENT $D_PEER_PORT $IPSEC_POLICY_OUT -j ACCEPT + fi + # + # log IPsec client connection setup + if [ $VPN_LOGGING ] + then + if [ "$PLUTO_PEER_CLIENT" == "$PLUTO_PEER/128" ] + then + logger -t $TAG -p $FAC_PRIO \ + "+ `echo -e $PLUTO_PEER_ID` $PLUTO_PEER -- $PLUTO_ME == $PLUTO_MY_CLIENT" + else + logger -t $TAG -p $FAC_PRIO \ + "+ `echo -e $PLUTO_PEER_ID` $PLUTO_PEER_CLIENT == $PLUTO_PEER -- $PLUTO_ME == $PLUTO_MY_CLIENT" + fi + fi + ;; +down-client-v6:iptables) + # connection to client subnet, with (left/right)firewall=yes, going down + # This is used only by the default updown script, not by your custom + # ones, so do not mess with it; see CAUTION comment up at top. + if [ "$PLUTO_PEER_CLIENT" != "$PLUTO_MY_SOURCEIP/128" ] + then + ip6tables -D FORWARD -o $PLUTO_INTERFACE -p $PLUTO_PEER_PROTOCOL \ + -s $PLUTO_MY_CLIENT $S_MY_PORT \ + -d $PLUTO_PEER_CLIENT $D_PEER_PORT \ + $IPSEC_POLICY_OUT -j ACCEPT + ip6tables -D FORWARD -i $PLUTO_INTERFACE -p $PLUTO_MY_PROTOCOL \ + -s $PLUTO_PEER_CLIENT $S_PEER_PORT \ + -d $PLUTO_MY_CLIENT $D_MY_PORT \ + $IPSEC_POLICY_IN -j ACCEPT + fi + # + # a virtual IP requires an INPUT and OUTPUT rule on the host + # or sometimes host access via the internal IP is needed + if [ -n "$PLUTO_MY_SOURCEIP" -o -n "$PLUTO_HOST_ACCESS" ] + then + ip6tables -D INPUT -i $PLUTO_INTERFACE -p $PLUTO_MY_PROTOCOL \ + -s $PLUTO_PEER_CLIENT $S_PEER_PORT \ + -d $PLUTO_MY_CLIENT $D_MY_PORT \ + $IPSEC_POLICY_IN -j ACCEPT + ip6tables -D OUTPUT -o $PLUTO_INTERFACE -p $PLUTO_PEER_PROTOCOL \ + -s $PLUTO_MY_CLIENT $S_MY_PORT \ + -d $PLUTO_PEER_CLIENT $D_PEER_PORT \ + $IPSEC_POLICY_OUT -j ACCEPT + fi + # + # log IPsec client connection teardown + if [ $VPN_LOGGING ] + then + if [ "$PLUTO_PEER_CLIENT" == "$PLUTO_PEER/128" ] + then + logger -t $TAG -p $FAC_PRIO -- \ + "- `echo -e $PLUTO_PEER_ID` $PLUTO_PEER -- $PLUTO_ME == $PLUTO_MY_CLIENT" + else + logger -t $TAG -p $FAC_PRIO -- \ + "- `echo -e $PLUTO_PEER_ID` $PLUTO_PEER_CLIENT == $PLUTO_PEER -- $PLUTO_ME == $PLUTO_MY_CLIENT" + fi + fi + ;; *) echo "$0: unknown verb \`$PLUTO_VERB' or parameter \`$1'" >&2 exit 1 ;; diff --git a/src/charon/Makefile.am b/src/charon/Makefile.am index 0d783cbbb..9111191b6 100644 --- a/src/charon/Makefile.am +++ b/src/charon/Makefile.am @@ -45,7 +45,7 @@ kernel/kernel_interface.c kernel/kernel_interface.h \ network/packet.c network/packet.h \ network/receiver.c network/receiver.h \ network/sender.c network/sender.h \ -network/socket.c network/socket.h \ +network/socket.h \ processing/jobs/job.h \ processing/jobs/acquire_job.c processing/jobs/acquire_job.h \ processing/jobs/callback_job.c processing/jobs/callback_job.h \ @@ -83,8 +83,16 @@ sa/tasks/ike_natd.c sa/tasks/ike_natd.h \ sa/tasks/ike_mobike.c sa/tasks/ike_mobike.h \ sa/tasks/ike_rekey.c sa/tasks/ike_rekey.h \ sa/tasks/ike_reauth.c sa/tasks/ike_reauth.h \ +sa/tasks/ike_auth_lifetime.c sa/tasks/ike_auth_lifetime.h \ sa/tasks/task.c sa/tasks/task.h +# Use RAW socket if pluto gets built +if USE_PLUTO + charon_SOURCES += network/socket-raw.c +else + charon_SOURCES += network/socket.c +endif + if USE_P2P charon_SOURCES += encoding/payloads/endpoint_notify.c encoding/payloads/endpoint_notify.h \ processing/jobs/initiate_mediation_job.c processing/jobs/initiate_mediation_job.h \ @@ -104,56 +112,74 @@ if USE_LIBCURL endif -# build EAP plugins, EAP-Identity is always built -################################################# +# build EAP plugins +################### eap_LTLIBRARIES = -eap_LTLIBRARIES += libeapidentity.la -libeapidentity_la_SOURCES = sa/authenticators/eap/eap_identity.h sa/authenticators/eap/eap_identity.c -libeapidentity_la_LDFLAGS = -module +if USE_EAP_IDENTITY + eap_LTLIBRARIES += libcharon-eapidentity.la + libcharon_eapidentity_la_SOURCES = sa/authenticators/eap/eap_identity.h sa/authenticators/eap/eap_identity.c + libcharon_eapidentity_la_LDFLAGS = -module +endif + +if USE_EAP_SIM + eap_LTLIBRARIES += libcharon-eapsim.la + libcharon_eapsim_la_SOURCES = sa/authenticators/eap/eap_sim.h sa/authenticators/eap/eap_sim.c + libcharon_eapsim_la_LDFLAGS = -module +endif -if BUILD_EAP_SIM - eap_LTLIBRARIES += libeapsim.la - libeapsim_la_SOURCES = sa/authenticators/eap/eap_sim.h sa/authenticators/eap/eap_sim.c - libeapsim_la_LDFLAGS = -module +if USE_EAP_MD5 + eap_LTLIBRARIES += libcharon-eapmd5.la + libcharon_eapmd5_la_SOURCES = sa/authenticators/eap/eap_md5.h sa/authenticators/eap/eap_md5.c + libcharon_eapmd5_la_LDFLAGS = -module endif -# build backends, local backend is always built -############################################### +if USE_EAP_AKA + eap_LTLIBRARIES += libcharon-eapaka.la + libcharon_eapaka_la_SOURCES = sa/authenticators/eap/eap_aka.h sa/authenticators/eap/eap_aka.c + libcharon_eapaka_la_LDFLAGS = -module +endif + +# build backends +################ backend_LTLIBRARIES = -backend_LTLIBRARIES += liblocal.la -liblocal_la_SOURCES = config/backends/local_backend.h config/backends/local_backend.c -liblocal_la_LDFLAGS = -module +if USE_STROKE + backend_LTLIBRARIES += libcharon-local.la + libcharon_local_la_SOURCES = config/backends/local_backend.h config/backends/local_backend.c + libcharon_local_la_LDFLAGS = -module +endif if USE_LIBSQLITE - backend_LTLIBRARIES += libsqlite.la - libsqlite_la_SOURCES = config/backends/sqlite_backend.h config/backends/sqlite_backend.c - libsqlite_la_LIBADD = -lsqlite3 - libsqlite_la_LDFLAGS = -module + backend_LTLIBRARIES += libcharon-sqlite.la + libcharon_sqlite_la_SOURCES = config/backends/sqlite_backend.h config/backends/sqlite_backend.c + libcharon_sqlite_la_LIBADD = -lsqlite3 + libcharon_sqlite_la_LDFLAGS = -module endif -# build control interfaces, stroke interface is always built -############################################################ +# build control interfaces +########################## interface_LTLIBRARIES = -interface_LTLIBRARIES += libstroke.la -libstroke_la_SOURCES = control/interfaces/stroke_interface.h control/interfaces/stroke_interface.c -libstroke_la_LDFLAGS = -module +if USE_STROKE + interface_LTLIBRARIES += libcharon-stroke.la + libcharon_stroke_la_SOURCES = control/interfaces/stroke_interface.h control/interfaces/stroke_interface.c + libcharon_stroke_la_LDFLAGS = -module +endif if USE_LIBDBUS - interface_LTLIBRARIES += libdbus.la - libdbus_la_SOURCES = control/interfaces/dbus_interface.h control/interfaces/dbus_interface.c - libdbus_la_LDFLAGS = -module - libdbus_la_LIBADD = ${dbus_LIBS} + interface_LTLIBRARIES += libcharon-dbus.la + libcharon_dbus_la_SOURCES = control/interfaces/dbus_interface.h control/interfaces/dbus_interface.c + libcharon_dbus_la_LDFLAGS = -module + libcharon_dbus_la_LIBADD = ${dbus_LIBS} INCLUDES += ${dbus_CFLAGS} endif if USE_LIBXML - interface_LTLIBRARIES += libxml.la - libxml_la_SOURCES = control/interfaces/xml_interface.h control/interfaces/xml_interface.c - libxml_la_LDFLAGS = -module - libxml_la_LIBADD = ${xml_LIBS} + interface_LTLIBRARIES += libcharon-xml.la + libcharon_xml_la_SOURCES = control/interfaces/xml_interface.h control/interfaces/xml_interface.c + libcharon_xml_la_LDFLAGS = -module + libcharon_xml_la_LIBADD = ${xml_LIBS} INCLUDES += ${xml_CFLAGS} endif diff --git a/src/charon/Makefile.in b/src/charon/Makefile.in index e3b397f4e..bbae1270a 100644 --- a/src/charon/Makefile.in +++ b/src/charon/Makefile.in @@ -34,20 +34,29 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ ipsec_PROGRAMS = charon$(EXEEXT) -@USE_P2P_TRUE@am__append_1 = encoding/payloads/endpoint_notify.c encoding/payloads/endpoint_notify.h \ + +# Use RAW socket if pluto gets built +@USE_PLUTO_TRUE@am__append_1 = network/socket-raw.c +@USE_PLUTO_FALSE@am__append_2 = network/socket.c +@USE_P2P_TRUE@am__append_3 = encoding/payloads/endpoint_notify.c encoding/payloads/endpoint_notify.h \ @USE_P2P_TRUE@ processing/jobs/initiate_mediation_job.c processing/jobs/initiate_mediation_job.h \ @USE_P2P_TRUE@ processing/jobs/mediation_job.c processing/jobs/mediation_job.h \ @USE_P2P_TRUE@ sa/connect_manager.c sa/connect_manager.h \ @USE_P2P_TRUE@ sa/mediation_manager.c sa/mediation_manager.h \ @USE_P2P_TRUE@ sa/tasks/ike_p2p.c sa/tasks/ike_p2p.h -@USE_LIBCURL_TRUE@am__append_2 = -lcurl -@BUILD_EAP_SIM_TRUE@am__append_3 = libeapsim.la -@USE_LIBSQLITE_TRUE@am__append_4 = libsqlite.la -@USE_LIBDBUS_TRUE@am__append_5 = libdbus.la -@USE_LIBDBUS_TRUE@am__append_6 = ${dbus_CFLAGS} -@USE_LIBXML_TRUE@am__append_7 = libxml.la -@USE_LIBXML_TRUE@am__append_8 = ${xml_CFLAGS} +@USE_LIBCURL_TRUE@am__append_4 = -lcurl +@USE_EAP_IDENTITY_TRUE@am__append_5 = libcharon-eapidentity.la +@USE_EAP_SIM_TRUE@am__append_6 = libcharon-eapsim.la +@USE_EAP_MD5_TRUE@am__append_7 = libcharon-eapmd5.la +@USE_EAP_AKA_TRUE@am__append_8 = libcharon-eapaka.la +@USE_STROKE_TRUE@am__append_9 = libcharon-local.la +@USE_LIBSQLITE_TRUE@am__append_10 = libcharon-sqlite.la +@USE_STROKE_TRUE@am__append_11 = libcharon-stroke.la +@USE_LIBDBUS_TRUE@am__append_12 = libcharon-dbus.la +@USE_LIBDBUS_TRUE@am__append_13 = ${dbus_CFLAGS} +@USE_LIBXML_TRUE@am__append_14 = libcharon-xml.la +@USE_LIBXML_TRUE@am__append_15 = ${xml_CFLAGS} subdir = src/charon DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 @@ -70,60 +79,102 @@ interfaceLTLIBRARIES_INSTALL = $(INSTALL) LTLIBRARIES = $(backend_LTLIBRARIES) $(eap_LTLIBRARIES) \ $(interface_LTLIBRARIES) am__DEPENDENCIES_1 = -@USE_LIBDBUS_TRUE@libdbus_la_DEPENDENCIES = $(am__DEPENDENCIES_1) -am__libdbus_la_SOURCES_DIST = control/interfaces/dbus_interface.h \ +@USE_LIBDBUS_TRUE@libcharon_dbus_la_DEPENDENCIES = \ +@USE_LIBDBUS_TRUE@ $(am__DEPENDENCIES_1) +am__libcharon_dbus_la_SOURCES_DIST = \ + control/interfaces/dbus_interface.h \ control/interfaces/dbus_interface.c -@USE_LIBDBUS_TRUE@am_libdbus_la_OBJECTS = dbus_interface.lo -libdbus_la_OBJECTS = $(am_libdbus_la_OBJECTS) -libdbus_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ +@USE_LIBDBUS_TRUE@am_libcharon_dbus_la_OBJECTS = dbus_interface.lo +libcharon_dbus_la_OBJECTS = $(am_libcharon_dbus_la_OBJECTS) +libcharon_dbus_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ + $(libcharon_dbus_la_LDFLAGS) $(LDFLAGS) -o $@ +@USE_LIBDBUS_TRUE@am_libcharon_dbus_la_rpath = -rpath $(interfacedir) +libcharon_eapaka_la_LIBADD = +am__libcharon_eapaka_la_SOURCES_DIST = \ + sa/authenticators/eap/eap_aka.h \ + sa/authenticators/eap/eap_aka.c +@USE_EAP_AKA_TRUE@am_libcharon_eapaka_la_OBJECTS = eap_aka.lo +libcharon_eapaka_la_OBJECTS = $(am_libcharon_eapaka_la_OBJECTS) +libcharon_eapaka_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ + $(libcharon_eapaka_la_LDFLAGS) $(LDFLAGS) -o $@ +@USE_EAP_AKA_TRUE@am_libcharon_eapaka_la_rpath = -rpath $(eapdir) +libcharon_eapidentity_la_LIBADD = +am__libcharon_eapidentity_la_SOURCES_DIST = \ + sa/authenticators/eap/eap_identity.h \ + sa/authenticators/eap/eap_identity.c +@USE_EAP_IDENTITY_TRUE@am_libcharon_eapidentity_la_OBJECTS = \ +@USE_EAP_IDENTITY_TRUE@ eap_identity.lo +libcharon_eapidentity_la_OBJECTS = \ + $(am_libcharon_eapidentity_la_OBJECTS) +libcharon_eapidentity_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ - $(libdbus_la_LDFLAGS) $(LDFLAGS) -o $@ -@USE_LIBDBUS_TRUE@am_libdbus_la_rpath = -rpath $(interfacedir) -libeapidentity_la_LIBADD = -am_libeapidentity_la_OBJECTS = eap_identity.lo -libeapidentity_la_OBJECTS = $(am_libeapidentity_la_OBJECTS) -libeapidentity_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(libcharon_eapidentity_la_LDFLAGS) $(LDFLAGS) -o $@ +@USE_EAP_IDENTITY_TRUE@am_libcharon_eapidentity_la_rpath = -rpath \ +@USE_EAP_IDENTITY_TRUE@ $(eapdir) +libcharon_eapmd5_la_LIBADD = +am__libcharon_eapmd5_la_SOURCES_DIST = \ + sa/authenticators/eap/eap_md5.h \ + sa/authenticators/eap/eap_md5.c +@USE_EAP_MD5_TRUE@am_libcharon_eapmd5_la_OBJECTS = eap_md5.lo +libcharon_eapmd5_la_OBJECTS = $(am_libcharon_eapmd5_la_OBJECTS) +libcharon_eapmd5_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ - $(libeapidentity_la_LDFLAGS) $(LDFLAGS) -o $@ -libeapsim_la_LIBADD = -am__libeapsim_la_SOURCES_DIST = sa/authenticators/eap/eap_sim.h \ + $(libcharon_eapmd5_la_LDFLAGS) $(LDFLAGS) -o $@ +@USE_EAP_MD5_TRUE@am_libcharon_eapmd5_la_rpath = -rpath $(eapdir) +libcharon_eapsim_la_LIBADD = +am__libcharon_eapsim_la_SOURCES_DIST = \ + sa/authenticators/eap/eap_sim.h \ sa/authenticators/eap/eap_sim.c -@BUILD_EAP_SIM_TRUE@am_libeapsim_la_OBJECTS = eap_sim.lo -libeapsim_la_OBJECTS = $(am_libeapsim_la_OBJECTS) -libeapsim_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ +@USE_EAP_SIM_TRUE@am_libcharon_eapsim_la_OBJECTS = eap_sim.lo +libcharon_eapsim_la_OBJECTS = $(am_libcharon_eapsim_la_OBJECTS) +libcharon_eapsim_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ - $(libeapsim_la_LDFLAGS) $(LDFLAGS) -o $@ -@BUILD_EAP_SIM_TRUE@am_libeapsim_la_rpath = -rpath $(eapdir) -liblocal_la_LIBADD = -am_liblocal_la_OBJECTS = local_backend.lo -liblocal_la_OBJECTS = $(am_liblocal_la_OBJECTS) -liblocal_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(libcharon_eapsim_la_LDFLAGS) $(LDFLAGS) -o $@ +@USE_EAP_SIM_TRUE@am_libcharon_eapsim_la_rpath = -rpath $(eapdir) +libcharon_local_la_LIBADD = +am__libcharon_local_la_SOURCES_DIST = config/backends/local_backend.h \ + config/backends/local_backend.c +@USE_STROKE_TRUE@am_libcharon_local_la_OBJECTS = local_backend.lo +libcharon_local_la_OBJECTS = $(am_libcharon_local_la_OBJECTS) +libcharon_local_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ - $(liblocal_la_LDFLAGS) $(LDFLAGS) -o $@ -libsqlite_la_DEPENDENCIES = -am__libsqlite_la_SOURCES_DIST = config/backends/sqlite_backend.h \ + $(libcharon_local_la_LDFLAGS) $(LDFLAGS) -o $@ +@USE_STROKE_TRUE@am_libcharon_local_la_rpath = -rpath $(backenddir) +libcharon_sqlite_la_DEPENDENCIES = +am__libcharon_sqlite_la_SOURCES_DIST = \ + config/backends/sqlite_backend.h \ config/backends/sqlite_backend.c -@USE_LIBSQLITE_TRUE@am_libsqlite_la_OBJECTS = sqlite_backend.lo -libsqlite_la_OBJECTS = $(am_libsqlite_la_OBJECTS) -libsqlite_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ +@USE_LIBSQLITE_TRUE@am_libcharon_sqlite_la_OBJECTS = \ +@USE_LIBSQLITE_TRUE@ sqlite_backend.lo +libcharon_sqlite_la_OBJECTS = $(am_libcharon_sqlite_la_OBJECTS) +libcharon_sqlite_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ - $(libsqlite_la_LDFLAGS) $(LDFLAGS) -o $@ -@USE_LIBSQLITE_TRUE@am_libsqlite_la_rpath = -rpath $(backenddir) -libstroke_la_LIBADD = -am_libstroke_la_OBJECTS = stroke_interface.lo -libstroke_la_OBJECTS = $(am_libstroke_la_OBJECTS) -libstroke_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(libcharon_sqlite_la_LDFLAGS) $(LDFLAGS) -o $@ +@USE_LIBSQLITE_TRUE@am_libcharon_sqlite_la_rpath = -rpath \ +@USE_LIBSQLITE_TRUE@ $(backenddir) +libcharon_stroke_la_LIBADD = +am__libcharon_stroke_la_SOURCES_DIST = \ + control/interfaces/stroke_interface.h \ + control/interfaces/stroke_interface.c +@USE_STROKE_TRUE@am_libcharon_stroke_la_OBJECTS = stroke_interface.lo +libcharon_stroke_la_OBJECTS = $(am_libcharon_stroke_la_OBJECTS) +libcharon_stroke_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ - $(libstroke_la_LDFLAGS) $(LDFLAGS) -o $@ -@USE_LIBXML_TRUE@libxml_la_DEPENDENCIES = $(am__DEPENDENCIES_1) -am__libxml_la_SOURCES_DIST = control/interfaces/xml_interface.h \ + $(libcharon_stroke_la_LDFLAGS) $(LDFLAGS) -o $@ +@USE_STROKE_TRUE@am_libcharon_stroke_la_rpath = -rpath $(interfacedir) +@USE_LIBXML_TRUE@libcharon_xml_la_DEPENDENCIES = \ +@USE_LIBXML_TRUE@ $(am__DEPENDENCIES_1) +am__libcharon_xml_la_SOURCES_DIST = \ + control/interfaces/xml_interface.h \ control/interfaces/xml_interface.c -@USE_LIBXML_TRUE@am_libxml_la_OBJECTS = xml_interface.lo -libxml_la_OBJECTS = $(am_libxml_la_OBJECTS) -libxml_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ +@USE_LIBXML_TRUE@am_libcharon_xml_la_OBJECTS = xml_interface.lo +libcharon_xml_la_OBJECTS = $(am_libcharon_xml_la_OBJECTS) +libcharon_xml_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ - $(libxml_la_LDFLAGS) $(LDFLAGS) -o $@ -@USE_LIBXML_TRUE@am_libxml_la_rpath = -rpath $(interfacedir) + $(libcharon_xml_la_LDFLAGS) $(LDFLAGS) -o $@ +@USE_LIBXML_TRUE@am_libcharon_xml_la_rpath = -rpath $(interfacedir) ipsecPROGRAMS_INSTALL = $(INSTALL_PROGRAM) PROGRAMS = $(ipsec_PROGRAMS) am__charon_SOURCES_DIST = bus/bus.c bus/bus.h \ @@ -181,7 +232,7 @@ am__charon_SOURCES_DIST = bus/bus.c bus/bus.h \ kernel/kernel_interface.c kernel/kernel_interface.h \ network/packet.c network/packet.h network/receiver.c \ network/receiver.h network/sender.c network/sender.h \ - network/socket.c network/socket.h processing/jobs/job.h \ + network/socket.h processing/jobs/job.h \ processing/jobs/acquire_job.c processing/jobs/acquire_job.h \ processing/jobs/callback_job.c processing/jobs/callback_job.h \ processing/jobs/delete_child_sa_job.c \ @@ -225,7 +276,9 @@ am__charon_SOURCES_DIST = bus/bus.c bus/bus.h \ sa/tasks/ike_natd.h sa/tasks/ike_mobike.c \ sa/tasks/ike_mobike.h sa/tasks/ike_rekey.c \ sa/tasks/ike_rekey.h sa/tasks/ike_reauth.c \ - sa/tasks/ike_reauth.h sa/tasks/task.c sa/tasks/task.h \ + sa/tasks/ike_reauth.h sa/tasks/ike_auth_lifetime.c \ + sa/tasks/ike_auth_lifetime.h sa/tasks/task.c sa/tasks/task.h \ + network/socket-raw.c network/socket.c \ encoding/payloads/endpoint_notify.c \ encoding/payloads/endpoint_notify.h \ processing/jobs/initiate_mediation_job.c \ @@ -234,7 +287,9 @@ am__charon_SOURCES_DIST = bus/bus.c bus/bus.h \ processing/jobs/mediation_job.h sa/connect_manager.c \ sa/connect_manager.h sa/mediation_manager.c \ sa/mediation_manager.h sa/tasks/ike_p2p.c sa/tasks/ike_p2p.h -@USE_P2P_TRUE@am__objects_1 = endpoint_notify.$(OBJEXT) \ +@USE_PLUTO_TRUE@am__objects_1 = socket-raw.$(OBJEXT) +@USE_PLUTO_FALSE@am__objects_2 = socket.$(OBJEXT) +@USE_P2P_TRUE@am__objects_3 = endpoint_notify.$(OBJEXT) \ @USE_P2P_TRUE@ initiate_mediation_job.$(OBJEXT) \ @USE_P2P_TRUE@ mediation_job.$(OBJEXT) \ @USE_P2P_TRUE@ connect_manager.$(OBJEXT) \ @@ -258,7 +313,7 @@ am_charon_OBJECTS = bus.$(OBJEXT) file_logger.$(OBJEXT) \ ts_payload.$(OBJEXT) unknown_payload.$(OBJEXT) \ vendor_id_payload.$(OBJEXT) kernel_interface.$(OBJEXT) \ packet.$(OBJEXT) receiver.$(OBJEXT) sender.$(OBJEXT) \ - socket.$(OBJEXT) acquire_job.$(OBJEXT) callback_job.$(OBJEXT) \ + acquire_job.$(OBJEXT) callback_job.$(OBJEXT) \ delete_child_sa_job.$(OBJEXT) delete_ike_sa_job.$(OBJEXT) \ process_message_job.$(OBJEXT) rekey_child_sa_job.$(OBJEXT) \ rekey_ike_sa_job.$(OBJEXT) retransmit_job.$(OBJEXT) \ @@ -273,7 +328,9 @@ am_charon_OBJECTS = bus.$(OBJEXT) file_logger.$(OBJEXT) \ ike_auth.$(OBJEXT) ike_cert.$(OBJEXT) ike_config.$(OBJEXT) \ ike_delete.$(OBJEXT) ike_dpd.$(OBJEXT) ike_init.$(OBJEXT) \ ike_natd.$(OBJEXT) ike_mobike.$(OBJEXT) ike_rekey.$(OBJEXT) \ - ike_reauth.$(OBJEXT) task.$(OBJEXT) $(am__objects_1) + ike_reauth.$(OBJEXT) ike_auth_lifetime.$(OBJEXT) \ + task.$(OBJEXT) $(am__objects_1) $(am__objects_2) \ + $(am__objects_3) charon_OBJECTS = $(am_charon_OBJECTS) charon_DEPENDENCIES = \ $(top_builddir)/src/libstrongswan/libstrongswan.la \ @@ -290,14 +347,21 @@ CCLD = $(CC) LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) \ $(LDFLAGS) -o $@ -SOURCES = $(libdbus_la_SOURCES) $(libeapidentity_la_SOURCES) \ - $(libeapsim_la_SOURCES) $(liblocal_la_SOURCES) \ - $(libsqlite_la_SOURCES) $(libstroke_la_SOURCES) \ - $(libxml_la_SOURCES) $(charon_SOURCES) -DIST_SOURCES = $(am__libdbus_la_SOURCES_DIST) \ - $(libeapidentity_la_SOURCES) $(am__libeapsim_la_SOURCES_DIST) \ - $(liblocal_la_SOURCES) $(am__libsqlite_la_SOURCES_DIST) \ - $(libstroke_la_SOURCES) $(am__libxml_la_SOURCES_DIST) \ +SOURCES = $(libcharon_dbus_la_SOURCES) $(libcharon_eapaka_la_SOURCES) \ + $(libcharon_eapidentity_la_SOURCES) \ + $(libcharon_eapmd5_la_SOURCES) $(libcharon_eapsim_la_SOURCES) \ + $(libcharon_local_la_SOURCES) $(libcharon_sqlite_la_SOURCES) \ + $(libcharon_stroke_la_SOURCES) $(libcharon_xml_la_SOURCES) \ + $(charon_SOURCES) +DIST_SOURCES = $(am__libcharon_dbus_la_SOURCES_DIST) \ + $(am__libcharon_eapaka_la_SOURCES_DIST) \ + $(am__libcharon_eapidentity_la_SOURCES_DIST) \ + $(am__libcharon_eapmd5_la_SOURCES_DIST) \ + $(am__libcharon_eapsim_la_SOURCES_DIST) \ + $(am__libcharon_local_la_SOURCES_DIST) \ + $(am__libcharon_sqlite_la_SOURCES_DIST) \ + $(am__libcharon_stroke_la_SOURCES_DIST) \ + $(am__libcharon_xml_la_SOURCES_DIST) \ $(am__charon_SOURCES_DIST) ETAGS = etags CTAGS = ctags @@ -486,7 +550,7 @@ charon_SOURCES = bus/bus.c bus/bus.h bus/listeners/file_logger.c \ kernel/kernel_interface.c kernel/kernel_interface.h \ network/packet.c network/packet.h network/receiver.c \ network/receiver.h network/sender.c network/sender.h \ - network/socket.c network/socket.h processing/jobs/job.h \ + network/socket.h processing/jobs/job.h \ processing/jobs/acquire_job.c processing/jobs/acquire_job.h \ processing/jobs/callback_job.c processing/jobs/callback_job.h \ processing/jobs/delete_child_sa_job.c \ @@ -530,45 +594,52 @@ charon_SOURCES = bus/bus.c bus/bus.h bus/listeners/file_logger.c \ sa/tasks/ike_natd.h sa/tasks/ike_mobike.c \ sa/tasks/ike_mobike.h sa/tasks/ike_rekey.c \ sa/tasks/ike_rekey.h sa/tasks/ike_reauth.c \ - sa/tasks/ike_reauth.h sa/tasks/task.c sa/tasks/task.h \ - $(am__append_1) + sa/tasks/ike_reauth.h sa/tasks/ike_auth_lifetime.c \ + sa/tasks/ike_auth_lifetime.h sa/tasks/task.c sa/tasks/task.h \ + $(am__append_1) $(am__append_2) $(am__append_3) INCLUDES = -I${linuxdir} -I$(top_srcdir)/src/libstrongswan \ -I$(top_srcdir)/src/charon -I$(top_srcdir)/src/stroke \ - $(am__append_6) $(am__append_8) + $(am__append_13) $(am__append_15) AM_CFLAGS = -rdynamic -DIPSEC_CONFDIR=\"${confdir}\" -DIPSEC_DIR=\"${ipsecdir}\" -DIPSEC_PIDDIR=\"${piddir}\" \ -DIPSEC_EAPDIR=\"${eapdir}\" -DIPSEC_BACKENDDIR=\"${backenddir}\" -DIPSEC_INTERFACEDIR=\"${interfacedir}\" charon_LDADD = $(top_builddir)/src/libstrongswan/libstrongswan.la \ - -lgmp -lpthread -lm -ldl $(am__append_2) - -# build EAP plugins, EAP-Identity is always built -################################################# -eap_LTLIBRARIES = libeapidentity.la $(am__append_3) -libeapidentity_la_SOURCES = sa/authenticators/eap/eap_identity.h sa/authenticators/eap/eap_identity.c -libeapidentity_la_LDFLAGS = -module -@BUILD_EAP_SIM_TRUE@libeapsim_la_SOURCES = sa/authenticators/eap/eap_sim.h sa/authenticators/eap/eap_sim.c -@BUILD_EAP_SIM_TRUE@libeapsim_la_LDFLAGS = -module - -# build backends, local backend is always built -############################################### -backend_LTLIBRARIES = liblocal.la $(am__append_4) -liblocal_la_SOURCES = config/backends/local_backend.h config/backends/local_backend.c -liblocal_la_LDFLAGS = -module -@USE_LIBSQLITE_TRUE@libsqlite_la_SOURCES = config/backends/sqlite_backend.h config/backends/sqlite_backend.c -@USE_LIBSQLITE_TRUE@libsqlite_la_LIBADD = -lsqlite3 -@USE_LIBSQLITE_TRUE@libsqlite_la_LDFLAGS = -module - -# build control interfaces, stroke interface is always built -############################################################ -interface_LTLIBRARIES = libstroke.la $(am__append_5) $(am__append_7) -libstroke_la_SOURCES = control/interfaces/stroke_interface.h control/interfaces/stroke_interface.c -libstroke_la_LDFLAGS = -module -@USE_LIBDBUS_TRUE@libdbus_la_SOURCES = control/interfaces/dbus_interface.h control/interfaces/dbus_interface.c -@USE_LIBDBUS_TRUE@libdbus_la_LDFLAGS = -module -@USE_LIBDBUS_TRUE@libdbus_la_LIBADD = ${dbus_LIBS} -@USE_LIBXML_TRUE@libxml_la_SOURCES = control/interfaces/xml_interface.h control/interfaces/xml_interface.c -@USE_LIBXML_TRUE@libxml_la_LDFLAGS = -module -@USE_LIBXML_TRUE@libxml_la_LIBADD = ${xml_LIBS} + -lgmp -lpthread -lm -ldl $(am__append_4) + +# build EAP plugins +################### +eap_LTLIBRARIES = $(am__append_5) $(am__append_6) $(am__append_7) \ + $(am__append_8) +@USE_EAP_IDENTITY_TRUE@libcharon_eapidentity_la_SOURCES = sa/authenticators/eap/eap_identity.h sa/authenticators/eap/eap_identity.c +@USE_EAP_IDENTITY_TRUE@libcharon_eapidentity_la_LDFLAGS = -module +@USE_EAP_SIM_TRUE@libcharon_eapsim_la_SOURCES = sa/authenticators/eap/eap_sim.h sa/authenticators/eap/eap_sim.c +@USE_EAP_SIM_TRUE@libcharon_eapsim_la_LDFLAGS = -module +@USE_EAP_MD5_TRUE@libcharon_eapmd5_la_SOURCES = sa/authenticators/eap/eap_md5.h sa/authenticators/eap/eap_md5.c +@USE_EAP_MD5_TRUE@libcharon_eapmd5_la_LDFLAGS = -module +@USE_EAP_AKA_TRUE@libcharon_eapaka_la_SOURCES = sa/authenticators/eap/eap_aka.h sa/authenticators/eap/eap_aka.c +@USE_EAP_AKA_TRUE@libcharon_eapaka_la_LDFLAGS = -module + +# build backends +################ +backend_LTLIBRARIES = $(am__append_9) $(am__append_10) +@USE_STROKE_TRUE@libcharon_local_la_SOURCES = config/backends/local_backend.h config/backends/local_backend.c +@USE_STROKE_TRUE@libcharon_local_la_LDFLAGS = -module +@USE_LIBSQLITE_TRUE@libcharon_sqlite_la_SOURCES = config/backends/sqlite_backend.h config/backends/sqlite_backend.c +@USE_LIBSQLITE_TRUE@libcharon_sqlite_la_LIBADD = -lsqlite3 +@USE_LIBSQLITE_TRUE@libcharon_sqlite_la_LDFLAGS = -module + +# build control interfaces +########################## +interface_LTLIBRARIES = $(am__append_11) $(am__append_12) \ + $(am__append_14) +@USE_STROKE_TRUE@libcharon_stroke_la_SOURCES = control/interfaces/stroke_interface.h control/interfaces/stroke_interface.c +@USE_STROKE_TRUE@libcharon_stroke_la_LDFLAGS = -module +@USE_LIBDBUS_TRUE@libcharon_dbus_la_SOURCES = control/interfaces/dbus_interface.h control/interfaces/dbus_interface.c +@USE_LIBDBUS_TRUE@libcharon_dbus_la_LDFLAGS = -module +@USE_LIBDBUS_TRUE@libcharon_dbus_la_LIBADD = ${dbus_LIBS} +@USE_LIBXML_TRUE@libcharon_xml_la_SOURCES = control/interfaces/xml_interface.h control/interfaces/xml_interface.c +@USE_LIBXML_TRUE@libcharon_xml_la_LDFLAGS = -module +@USE_LIBXML_TRUE@libcharon_xml_la_LIBADD = ${xml_LIBS} all: all-am .SUFFIXES: @@ -683,20 +754,24 @@ clean-interfaceLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libdbus.la: $(libdbus_la_OBJECTS) $(libdbus_la_DEPENDENCIES) - $(libdbus_la_LINK) $(am_libdbus_la_rpath) $(libdbus_la_OBJECTS) $(libdbus_la_LIBADD) $(LIBS) -libeapidentity.la: $(libeapidentity_la_OBJECTS) $(libeapidentity_la_DEPENDENCIES) - $(libeapidentity_la_LINK) -rpath $(eapdir) $(libeapidentity_la_OBJECTS) $(libeapidentity_la_LIBADD) $(LIBS) -libeapsim.la: $(libeapsim_la_OBJECTS) $(libeapsim_la_DEPENDENCIES) - $(libeapsim_la_LINK) $(am_libeapsim_la_rpath) $(libeapsim_la_OBJECTS) $(libeapsim_la_LIBADD) $(LIBS) -liblocal.la: $(liblocal_la_OBJECTS) $(liblocal_la_DEPENDENCIES) - $(liblocal_la_LINK) -rpath $(backenddir) $(liblocal_la_OBJECTS) $(liblocal_la_LIBADD) $(LIBS) -libsqlite.la: $(libsqlite_la_OBJECTS) $(libsqlite_la_DEPENDENCIES) - $(libsqlite_la_LINK) $(am_libsqlite_la_rpath) $(libsqlite_la_OBJECTS) $(libsqlite_la_LIBADD) $(LIBS) -libstroke.la: $(libstroke_la_OBJECTS) $(libstroke_la_DEPENDENCIES) - $(libstroke_la_LINK) -rpath $(interfacedir) $(libstroke_la_OBJECTS) $(libstroke_la_LIBADD) $(LIBS) -libxml.la: $(libxml_la_OBJECTS) $(libxml_la_DEPENDENCIES) - $(libxml_la_LINK) $(am_libxml_la_rpath) $(libxml_la_OBJECTS) $(libxml_la_LIBADD) $(LIBS) +libcharon-dbus.la: $(libcharon_dbus_la_OBJECTS) $(libcharon_dbus_la_DEPENDENCIES) + $(libcharon_dbus_la_LINK) $(am_libcharon_dbus_la_rpath) $(libcharon_dbus_la_OBJECTS) $(libcharon_dbus_la_LIBADD) $(LIBS) +libcharon-eapaka.la: $(libcharon_eapaka_la_OBJECTS) $(libcharon_eapaka_la_DEPENDENCIES) + $(libcharon_eapaka_la_LINK) $(am_libcharon_eapaka_la_rpath) $(libcharon_eapaka_la_OBJECTS) $(libcharon_eapaka_la_LIBADD) $(LIBS) +libcharon-eapidentity.la: $(libcharon_eapidentity_la_OBJECTS) $(libcharon_eapidentity_la_DEPENDENCIES) + $(libcharon_eapidentity_la_LINK) $(am_libcharon_eapidentity_la_rpath) $(libcharon_eapidentity_la_OBJECTS) $(libcharon_eapidentity_la_LIBADD) $(LIBS) +libcharon-eapmd5.la: $(libcharon_eapmd5_la_OBJECTS) $(libcharon_eapmd5_la_DEPENDENCIES) + $(libcharon_eapmd5_la_LINK) $(am_libcharon_eapmd5_la_rpath) $(libcharon_eapmd5_la_OBJECTS) $(libcharon_eapmd5_la_LIBADD) $(LIBS) +libcharon-eapsim.la: $(libcharon_eapsim_la_OBJECTS) $(libcharon_eapsim_la_DEPENDENCIES) + $(libcharon_eapsim_la_LINK) $(am_libcharon_eapsim_la_rpath) $(libcharon_eapsim_la_OBJECTS) $(libcharon_eapsim_la_LIBADD) $(LIBS) +libcharon-local.la: $(libcharon_local_la_OBJECTS) $(libcharon_local_la_DEPENDENCIES) + $(libcharon_local_la_LINK) $(am_libcharon_local_la_rpath) $(libcharon_local_la_OBJECTS) $(libcharon_local_la_LIBADD) $(LIBS) +libcharon-sqlite.la: $(libcharon_sqlite_la_OBJECTS) $(libcharon_sqlite_la_DEPENDENCIES) + $(libcharon_sqlite_la_LINK) $(am_libcharon_sqlite_la_rpath) $(libcharon_sqlite_la_OBJECTS) $(libcharon_sqlite_la_LIBADD) $(LIBS) +libcharon-stroke.la: $(libcharon_stroke_la_OBJECTS) $(libcharon_stroke_la_DEPENDENCIES) + $(libcharon_stroke_la_LINK) $(am_libcharon_stroke_la_rpath) $(libcharon_stroke_la_OBJECTS) $(libcharon_stroke_la_LIBADD) $(LIBS) +libcharon-xml.la: $(libcharon_xml_la_OBJECTS) $(libcharon_xml_la_DEPENDENCIES) + $(libcharon_xml_la_LINK) $(am_libcharon_xml_la_rpath) $(libcharon_xml_la_OBJECTS) $(libcharon_xml_la_LIBADD) $(LIBS) install-ipsecPROGRAMS: $(ipsec_PROGRAMS) @$(NORMAL_INSTALL) test -z "$(ipsecdir)" || $(MKDIR_P) "$(DESTDIR)$(ipsecdir)" @@ -756,8 +831,10 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/delete_child_sa_job.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/delete_ike_sa_job.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/delete_payload.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/eap_aka.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/eap_authenticator.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/eap_identity.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/eap_md5.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/eap_method.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/eap_payload.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/eap_sim.Plo@am__quote@ @@ -768,6 +845,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/generator.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/id_payload.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ike_auth.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ike_auth_lifetime.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ike_cert.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ike_cfg.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ike_config.Po@am__quote@ @@ -814,6 +892,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/send_dpd_job.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/send_keepalive_job.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sender.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/socket-raw.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/socket.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sqlite_backend.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/stroke_interface.Plo@am__quote@ @@ -857,6 +936,13 @@ dbus_interface.lo: control/interfaces/dbus_interface.c @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dbus_interface.lo `test -f 'control/interfaces/dbus_interface.c' || echo '$(srcdir)/'`control/interfaces/dbus_interface.c +eap_aka.lo: sa/authenticators/eap/eap_aka.c +@am__fastdepCC_TRUE@ $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT eap_aka.lo -MD -MP -MF $(DEPDIR)/eap_aka.Tpo -c -o eap_aka.lo `test -f 'sa/authenticators/eap/eap_aka.c' || echo '$(srcdir)/'`sa/authenticators/eap/eap_aka.c +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/eap_aka.Tpo $(DEPDIR)/eap_aka.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='sa/authenticators/eap/eap_aka.c' object='eap_aka.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o eap_aka.lo `test -f 'sa/authenticators/eap/eap_aka.c' || echo '$(srcdir)/'`sa/authenticators/eap/eap_aka.c + eap_identity.lo: sa/authenticators/eap/eap_identity.c @am__fastdepCC_TRUE@ $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT eap_identity.lo -MD -MP -MF $(DEPDIR)/eap_identity.Tpo -c -o eap_identity.lo `test -f 'sa/authenticators/eap/eap_identity.c' || echo '$(srcdir)/'`sa/authenticators/eap/eap_identity.c @am__fastdepCC_TRUE@ mv -f $(DEPDIR)/eap_identity.Tpo $(DEPDIR)/eap_identity.Plo @@ -864,6 +950,13 @@ eap_identity.lo: sa/authenticators/eap/eap_identity.c @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o eap_identity.lo `test -f 'sa/authenticators/eap/eap_identity.c' || echo '$(srcdir)/'`sa/authenticators/eap/eap_identity.c +eap_md5.lo: sa/authenticators/eap/eap_md5.c +@am__fastdepCC_TRUE@ $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT eap_md5.lo -MD -MP -MF $(DEPDIR)/eap_md5.Tpo -c -o eap_md5.lo `test -f 'sa/authenticators/eap/eap_md5.c' || echo '$(srcdir)/'`sa/authenticators/eap/eap_md5.c +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/eap_md5.Tpo $(DEPDIR)/eap_md5.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='sa/authenticators/eap/eap_md5.c' object='eap_md5.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o eap_md5.lo `test -f 'sa/authenticators/eap/eap_md5.c' || echo '$(srcdir)/'`sa/authenticators/eap/eap_md5.c + eap_sim.lo: sa/authenticators/eap/eap_sim.c @am__fastdepCC_TRUE@ $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT eap_sim.lo -MD -MP -MF $(DEPDIR)/eap_sim.Tpo -c -o eap_sim.lo `test -f 'sa/authenticators/eap/eap_sim.c' || echo '$(srcdir)/'`sa/authenticators/eap/eap_sim.c @am__fastdepCC_TRUE@ mv -f $(DEPDIR)/eap_sim.Tpo $(DEPDIR)/eap_sim.Plo @@ -1473,20 +1566,6 @@ sender.obj: network/sender.c @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o sender.obj `if test -f 'network/sender.c'; then $(CYGPATH_W) 'network/sender.c'; else $(CYGPATH_W) '$(srcdir)/network/sender.c'; fi` -socket.o: network/socket.c -@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT socket.o -MD -MP -MF $(DEPDIR)/socket.Tpo -c -o socket.o `test -f 'network/socket.c' || echo '$(srcdir)/'`network/socket.c -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/socket.Tpo $(DEPDIR)/socket.Po -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='network/socket.c' object='socket.o' libtool=no @AMDEPBACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o socket.o `test -f 'network/socket.c' || echo '$(srcdir)/'`network/socket.c - -socket.obj: network/socket.c -@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT socket.obj -MD -MP -MF $(DEPDIR)/socket.Tpo -c -o socket.obj `if test -f 'network/socket.c'; then $(CYGPATH_W) 'network/socket.c'; else $(CYGPATH_W) '$(srcdir)/network/socket.c'; fi` -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/socket.Tpo $(DEPDIR)/socket.Po -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='network/socket.c' object='socket.obj' libtool=no @AMDEPBACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o socket.obj `if test -f 'network/socket.c'; then $(CYGPATH_W) 'network/socket.c'; else $(CYGPATH_W) '$(srcdir)/network/socket.c'; fi` - acquire_job.o: processing/jobs/acquire_job.c @am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT acquire_job.o -MD -MP -MF $(DEPDIR)/acquire_job.Tpo -c -o acquire_job.o `test -f 'processing/jobs/acquire_job.c' || echo '$(srcdir)/'`processing/jobs/acquire_job.c @am__fastdepCC_TRUE@ mv -f $(DEPDIR)/acquire_job.Tpo $(DEPDIR)/acquire_job.Po @@ -1991,6 +2070,20 @@ ike_reauth.obj: sa/tasks/ike_reauth.c @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o ike_reauth.obj `if test -f 'sa/tasks/ike_reauth.c'; then $(CYGPATH_W) 'sa/tasks/ike_reauth.c'; else $(CYGPATH_W) '$(srcdir)/sa/tasks/ike_reauth.c'; fi` +ike_auth_lifetime.o: sa/tasks/ike_auth_lifetime.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT ike_auth_lifetime.o -MD -MP -MF $(DEPDIR)/ike_auth_lifetime.Tpo -c -o ike_auth_lifetime.o `test -f 'sa/tasks/ike_auth_lifetime.c' || echo '$(srcdir)/'`sa/tasks/ike_auth_lifetime.c +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/ike_auth_lifetime.Tpo $(DEPDIR)/ike_auth_lifetime.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='sa/tasks/ike_auth_lifetime.c' object='ike_auth_lifetime.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o ike_auth_lifetime.o `test -f 'sa/tasks/ike_auth_lifetime.c' || echo '$(srcdir)/'`sa/tasks/ike_auth_lifetime.c + +ike_auth_lifetime.obj: sa/tasks/ike_auth_lifetime.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT ike_auth_lifetime.obj -MD -MP -MF $(DEPDIR)/ike_auth_lifetime.Tpo -c -o ike_auth_lifetime.obj `if test -f 'sa/tasks/ike_auth_lifetime.c'; then $(CYGPATH_W) 'sa/tasks/ike_auth_lifetime.c'; else $(CYGPATH_W) '$(srcdir)/sa/tasks/ike_auth_lifetime.c'; fi` +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/ike_auth_lifetime.Tpo $(DEPDIR)/ike_auth_lifetime.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='sa/tasks/ike_auth_lifetime.c' object='ike_auth_lifetime.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o ike_auth_lifetime.obj `if test -f 'sa/tasks/ike_auth_lifetime.c'; then $(CYGPATH_W) 'sa/tasks/ike_auth_lifetime.c'; else $(CYGPATH_W) '$(srcdir)/sa/tasks/ike_auth_lifetime.c'; fi` + task.o: sa/tasks/task.c @am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT task.o -MD -MP -MF $(DEPDIR)/task.Tpo -c -o task.o `test -f 'sa/tasks/task.c' || echo '$(srcdir)/'`sa/tasks/task.c @am__fastdepCC_TRUE@ mv -f $(DEPDIR)/task.Tpo $(DEPDIR)/task.Po @@ -2005,6 +2098,34 @@ task.obj: sa/tasks/task.c @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o task.obj `if test -f 'sa/tasks/task.c'; then $(CYGPATH_W) 'sa/tasks/task.c'; else $(CYGPATH_W) '$(srcdir)/sa/tasks/task.c'; fi` +socket-raw.o: network/socket-raw.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT socket-raw.o -MD -MP -MF $(DEPDIR)/socket-raw.Tpo -c -o socket-raw.o `test -f 'network/socket-raw.c' || echo '$(srcdir)/'`network/socket-raw.c +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/socket-raw.Tpo $(DEPDIR)/socket-raw.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='network/socket-raw.c' object='socket-raw.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o socket-raw.o `test -f 'network/socket-raw.c' || echo '$(srcdir)/'`network/socket-raw.c + +socket-raw.obj: network/socket-raw.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT socket-raw.obj -MD -MP -MF $(DEPDIR)/socket-raw.Tpo -c -o socket-raw.obj `if test -f 'network/socket-raw.c'; then $(CYGPATH_W) 'network/socket-raw.c'; else $(CYGPATH_W) '$(srcdir)/network/socket-raw.c'; fi` +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/socket-raw.Tpo $(DEPDIR)/socket-raw.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='network/socket-raw.c' object='socket-raw.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o socket-raw.obj `if test -f 'network/socket-raw.c'; then $(CYGPATH_W) 'network/socket-raw.c'; else $(CYGPATH_W) '$(srcdir)/network/socket-raw.c'; fi` + +socket.o: network/socket.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT socket.o -MD -MP -MF $(DEPDIR)/socket.Tpo -c -o socket.o `test -f 'network/socket.c' || echo '$(srcdir)/'`network/socket.c +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/socket.Tpo $(DEPDIR)/socket.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='network/socket.c' object='socket.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o socket.o `test -f 'network/socket.c' || echo '$(srcdir)/'`network/socket.c + +socket.obj: network/socket.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT socket.obj -MD -MP -MF $(DEPDIR)/socket.Tpo -c -o socket.obj `if test -f 'network/socket.c'; then $(CYGPATH_W) 'network/socket.c'; else $(CYGPATH_W) '$(srcdir)/network/socket.c'; fi` +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/socket.Tpo $(DEPDIR)/socket.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='network/socket.c' object='socket.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o socket.obj `if test -f 'network/socket.c'; then $(CYGPATH_W) 'network/socket.c'; else $(CYGPATH_W) '$(srcdir)/network/socket.c'; fi` + endpoint_notify.o: encoding/payloads/endpoint_notify.c @am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT endpoint_notify.o -MD -MP -MF $(DEPDIR)/endpoint_notify.Tpo -c -o endpoint_notify.o `test -f 'encoding/payloads/endpoint_notify.c' || echo '$(srcdir)/'`encoding/payloads/endpoint_notify.c @am__fastdepCC_TRUE@ mv -f $(DEPDIR)/endpoint_notify.Tpo $(DEPDIR)/endpoint_notify.Po diff --git a/src/charon/bus/bus.c b/src/charon/bus/bus.c index 5fda36925..e53ac43ce 100644 --- a/src/charon/bus/bus.c +++ b/src/charon/bus/bus.c @@ -24,6 +24,8 @@ #include +#include + ENUM(signal_names, SIG_ANY, SIG_MAX, /** should not get printed */ "SIG_ANY", @@ -53,104 +55,74 @@ ENUM(signal_names, SIG_ANY, SIG_MAX, "SIG_MAX", ); -typedef struct active_listener_t active_listener_t; +typedef struct private_bus_t private_bus_t; /** - * information for a active listener + * Private data of a bus_t object. */ -struct active_listener_t { - - /** - * associated thread - */ - pthread_t id; - - /** - * condvar to wait for a signal - */ - pthread_cond_t cond; - - /** - * state of the thread - */ - enum { - /** not registered, do not wait for thread */ - UNREGISTERED, - /** registered, if a signal occurs, wait until it is LISTENING */ - REGISTERED, - /** listening, deliver signal */ - LISTENING, - } state; - - /** - * currently processed signals type - */ - signal_t signal; - +struct private_bus_t { /** - * verbosity level of the signal + * Public part of a bus_t object. */ - level_t level; + bus_t public; /** - * current processed signals thread number + * List of registered listeners as entry_t's */ - int thread; + linked_list_t *listeners; /** - * currently processed signals ike_sa + * mutex to synchronize active listeners */ - ike_sa_t *ike_sa; + pthread_mutex_t mutex; /** - * currently processed signals format string + * Thread local storage for a unique, simple thread ID */ - char *format; + pthread_key_t thread_id; /** - * currently processed signals format varargs + * Thread local storage the threads IKE_SA */ - va_list args; - + pthread_key_t thread_sa; }; -typedef struct private_bus_t private_bus_t; +typedef struct entry_t entry_t; /** - * Private data of a bus_t object. + * a listener entry, either active or passive */ -struct private_bus_t { - /** - * Public part of a bus_t object. - */ - bus_t public; - - /** - * List of registered listeners implementing the bus_t interface - */ - linked_list_t *listeners; - +struct entry_t { + /** - * List of active listeners with listener_state TRUE + * registered listener interface */ - linked_list_t *active_listeners; + bus_listener_t *listener; /** - * mutex to synchronize active listeners + * is this a active listen() call with a blocking thread */ - pthread_mutex_t mutex; + bool blocker; /** - * Thread local storage for a unique, simple thread ID + * condvar where active listeners wait */ - pthread_key_t thread_id; + pthread_cond_t cond; +}; + +/** + * create a listener entry + */ +static entry_t *entry_create(bus_listener_t *listener, bool blocker) +{ + entry_t *this = malloc_thing(entry_t); - /** - * Thread local storage the threads IKE_SA - */ - pthread_key_t thread_sa; + this->listener = listener; + this->blocker = blocker; + pthread_cond_init(&this->cond, NULL); -}; + return this; +} /** * Get a unique thread number for a calling thread. Since @@ -160,7 +132,7 @@ struct private_bus_t { static int get_thread_number(private_bus_t *this) { static long current_num = 0; - static long stored_num; + long stored_num; stored_num = (long)pthread_getspecific(this->thread_id); if (stored_num == 0) @@ -180,7 +152,7 @@ static int get_thread_number(private_bus_t *this) static void add_listener(private_bus_t *this, bus_listener_t *listener) { pthread_mutex_lock(&this->mutex); - this->listeners->insert_last(this->listeners, listener); + this->listeners->insert_last(this->listeners, entry_create(listener, FALSE)); pthread_mutex_unlock(&this->mutex); } @@ -190,15 +162,16 @@ static void add_listener(private_bus_t *this, bus_listener_t *listener) static void remove_listener(private_bus_t *this, bus_listener_t *listener) { iterator_t *iterator; - bus_listener_t *current; + entry_t *entry; pthread_mutex_lock(&this->mutex); iterator = this->listeners->create_iterator(this->listeners, TRUE); - while (iterator->iterate(iterator, (void**)¤t)) + while (iterator->iterate(iterator, (void**)&entry)) { - if (current == listener) + if (entry->listener == listener) { iterator->remove(iterator); + free(entry); break; } } @@ -206,109 +179,67 @@ static void remove_listener(private_bus_t *this, bus_listener_t *listener) pthread_mutex_unlock(&this->mutex); } +typedef struct cleanup_data_t cleanup_data_t; + +/** + * data to remove a listener using pthread_cleanup handler + */ +struct cleanup_data_t { + /** bus instance */ + private_bus_t *this; + /** listener entry */ + entry_t *entry; +}; + /** - * Get the listener object for the calling thread + * pthread_cleanup handler to remove a listener */ -static active_listener_t *get_active_listener(private_bus_t *this) +static void listener_cleanup(cleanup_data_t *data) { - active_listener_t *current, *found = NULL; iterator_t *iterator; - - /* if the thread was here once before, we have a active_listener record */ - iterator = this->active_listeners->create_iterator(this->active_listeners, TRUE); - while (iterator->iterate(iterator, (void**)¤t)) + entry_t *entry; + + iterator = data->this->listeners->create_iterator(data->this->listeners, TRUE); + while (iterator->iterate(iterator, (void**)&entry)) { - if (current->id == pthread_self()) + if (entry == data->entry) { - found = current; + iterator->remove(iterator); + free(entry); break; } } iterator->destroy(iterator); - - if (found == NULL) - { - /* create a new object for a never-seen thread */ - found = malloc_thing(active_listener_t); - found->id = pthread_self(); - pthread_cond_init(&found->cond, NULL); - this->active_listeners->insert_last(this->active_listeners, found); - } - - return found; -} - -/** - * disable a listener to cleanly clean up - */ -static void unregister(active_listener_t *listener) -{ - listener->state = UNREGISTERED; - pthread_cond_broadcast(&listener->cond); } /** * Implementation of bus_t.listen. */ -static signal_t listen_(private_bus_t *this, level_t *level, int *thread, - ike_sa_t **ike_sa, char** format, va_list* args) +static void listen_(private_bus_t *this, bus_listener_t *listener, job_t *job) { - active_listener_t *listener; - int oldstate; - - pthread_mutex_lock(&this->mutex); - listener = get_active_listener(this); - /* go "listening", say hello to a thread which have a signal for us */ - listener->state = LISTENING; - pthread_cond_broadcast(&listener->cond); - /* wait until it has us delivered a signal, and go back to "registered". - * we allow cancellation here, but must cleanly disable the listener. */ - pthread_cleanup_push((void*)pthread_mutex_unlock, &this->mutex); - pthread_cleanup_push((void*)unregister, listener); - pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, &oldstate); - pthread_cond_wait(&listener->cond, &this->mutex); - pthread_setcancelstate(oldstate, NULL); - pthread_cleanup_pop(0); - pthread_cleanup_pop(0); - - pthread_mutex_unlock(&this->mutex); - - /* return signal values */ - *level = listener->level; - *thread = listener->thread; - *ike_sa = listener->ike_sa; - *format = listener->format; - va_copy(*args, listener->args); - va_end(listener->args); + int old; + cleanup_data_t data; - return listener->signal; -} + data.this = this; + data.entry = entry_create(listener, TRUE); -/** - * Implementation of bus_t.set_listen_state. - */ -static void set_listen_state(private_bus_t *this, bool active) -{ - active_listener_t *listener; - pthread_mutex_lock(&this->mutex); - - listener = get_active_listener(this); - if (active) - { - listener->state = REGISTERED; - } - else + this->listeners->insert_last(this->listeners, data.entry); + charon->processor->queue_job(charon->processor, job); + pthread_cleanup_push((void*)pthread_mutex_unlock, &this->mutex); + pthread_cleanup_push((void*)listener_cleanup, &data); + pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, &old); + while (data.entry->blocker) { - listener->state = UNREGISTERED; - /* say hello to signal emitter; we are finished processing the signal */ - pthread_cond_broadcast(&listener->cond); + pthread_cond_wait(&data.entry->cond, &this->mutex); } - - pthread_mutex_unlock(&this->mutex); + pthread_setcancelstate(old, NULL); + pthread_cleanup_pop(FALSE); + /* unlock mutex */ + pthread_cleanup_pop(TRUE); + free(data.entry); } - /** * Implementation of bus_t.set_sa. */ @@ -324,72 +255,37 @@ static void vsignal(private_bus_t *this, signal_t signal, level_t level, char* format, va_list args) { iterator_t *iterator; - bus_listener_t *listener; - active_listener_t *active_listener; + entry_t *entry; ike_sa_t *ike_sa; long thread; + pthread_mutex_lock(&this->mutex); ike_sa = pthread_getspecific(this->thread_sa); thread = get_thread_number(this); - pthread_mutex_lock(&this->mutex); - - /* do the job for all passive bus_listeners */ iterator = this->listeners->create_iterator(this->listeners, TRUE); - while (iterator->iterate(iterator, (void**)&listener)) + while (iterator->iterate(iterator, (void**)&entry)) { va_list args_copy; va_copy(args_copy, args); - if (!listener->signal(listener, signal, level, thread, - ike_sa, format, args_copy)) + if (!entry->listener->signal(entry->listener, signal, level, thread, + ike_sa, format, args_copy)) { - /* unregister listener if requested */ iterator->remove(iterator); + if (entry->blocker) + { + entry->blocker = FALSE; + pthread_cond_signal(&entry->cond); + } + else + { + free(entry); + } } va_end(args_copy); } iterator->destroy(iterator); - /* wake up all active listeners */ - iterator = this->active_listeners->create_iterator(this->active_listeners, TRUE); - while (iterator->iterate(iterator, (void**)&active_listener)) - { - /* wait until all threads are registered. But if the thread raising - * the signal is the same as the one that listens, we skip it. - * Otherwise we would deadlock. */ - while (active_listener->id != pthread_self() && - active_listener->state == REGISTERED) - { - pthread_cond_wait(&active_listener->cond, &this->mutex); - } - /* if thread is listening now, give it the signal to process */ - if (active_listener->state == LISTENING) - { - active_listener->level = level; - active_listener->thread = thread; - active_listener->ike_sa = ike_sa; - active_listener->signal = signal; - active_listener->format = format; - va_copy(active_listener->args, args); - active_listener->state = REGISTERED; - pthread_cond_broadcast(&active_listener->cond); - } - } - - /* we must wait now until all are not in state REGISTERED, - * as they may still use our arguments */ - iterator->reset(iterator); - while (iterator->iterate(iterator, (void**)&active_listener)) - { - /* do not wait for ourself, it won't happen (see above) */ - while (active_listener->id != pthread_self() && - active_listener->state == REGISTERED) - { - pthread_cond_wait(&active_listener->cond, &this->mutex); - } - } - iterator->destroy(iterator); - pthread_mutex_unlock(&this->mutex); } @@ -411,8 +307,7 @@ static void signal_(private_bus_t *this, signal_t signal, level_t level, */ static void destroy(private_bus_t *this) { - this->active_listeners->destroy_function(this->active_listeners, free); - this->listeners->destroy(this->listeners); + this->listeners->destroy_function(this->listeners, free); free(this); } @@ -425,18 +320,17 @@ bus_t *bus_create() this->public.add_listener = (void(*)(bus_t*,bus_listener_t*))add_listener; this->public.remove_listener = (void(*)(bus_t*,bus_listener_t*))remove_listener; - this->public.listen = (signal_t(*)(bus_t*,level_t*,int*,ike_sa_t**,char**,va_list*))listen_; - this->public.set_listen_state = (void(*)(bus_t*,bool))set_listen_state; + this->public.listen = (void(*)(bus_t*, bus_listener_t *listener, job_t *job))listen_; this->public.set_sa = (void(*)(bus_t*,ike_sa_t*))set_sa; this->public.signal = (void(*)(bus_t*,signal_t,level_t,char*,...))signal_; this->public.vsignal = (void(*)(bus_t*,signal_t,level_t,char*,va_list))vsignal; this->public.destroy = (void(*)(bus_t*)) destroy; this->listeners = linked_list_create(); - this->active_listeners = linked_list_create(); pthread_mutex_init(&this->mutex, NULL); pthread_key_create(&this->thread_id, NULL); pthread_key_create(&this->thread_sa, NULL); - return &(this->public); + return &this->public; } + diff --git a/src/charon/bus/bus.h b/src/charon/bus/bus.h index 00f1ab7ac..f71018444 100644 --- a/src/charon/bus/bus.h +++ b/src/charon/bus/bus.h @@ -32,6 +32,7 @@ typedef struct bus_t bus_t; #include #include +#include /** @@ -251,9 +252,7 @@ struct bus_listener_t { * in receiving event signals registers at the bus. Any signals sent to * are delivered to all registered listeners. * To deliver signals to threads, the blocking listen() call may be used - * to wait for a signal. However, passive listeners should be preferred, - * as listening actively requires some synchronization overhead as data - * must be passed from the raising thread to the listening thread. + * to wait for a signal. * * @ingroup bus */ @@ -280,44 +279,19 @@ struct bus_t { void (*remove_listener) (bus_t *this, bus_listener_t *listener); /** - * @brief Listen actively on the bus. + * @brief Register a listener and block the calling thread. * - * As we are fully multithreaded, we must provide a mechanism - * for active threads to listen to the bus. With the listen() method, - * a thread waits until a signal occurs, and then processes it. - * To prevent the listen() calling thread to miss signals emitted while - * it processes a signal, registration is required. This is done through - * the set_listen_state() method, see below. - * - * The listen() function is (has) a thread cancellation point, so you might - * want to register cleanup handlers. + * This call registers a listener and blocks the calling thread until + * its listeners function returns FALSE. This allows to wait for certain + * events. The associated job is executed after the listener has been + * registered, this allows to listen on events we initiate with the job + * without missing any signals. * * @param this bus - * @param level verbosity level of the signal - * @param thread receives thread number emitted the signal - * @param ike_sa receives the IKE_SA involved in the signal, or NULL - * @param format receives the format string supplied with the signal - * @param va_list receives the variable argument list for format - * @return the emitted signal type + * @param listener listener to register + * @param job job to execute asynchronously when registered, or NULL */ - signal_t (*listen) (bus_t *this, level_t* level, int *thread, - ike_sa_t **ike_sa, char** format, va_list* args); - - /** - * @brief Set the listening state of the calling thread. - * - * To prevent message loss for active listeners using listen(), threads - * must register themself to the bus before starting to listen(). When - * a signal occurs, the emitter waits until all threads with listen_state - * TRUE are waiting in the listen() method to process the signal. - * It is important that a thread with listen_state TRUE calls listen() - * periodically, or sets it's listening state to FALSE; otherwise - * all signal emitting threads get blocked on the bus. - * - * @param this bus - * @param active TRUE to set to listening - */ - void (*set_listen_state) (bus_t *this, bool active); + void (*listen)(bus_t *this, bus_listener_t *listener, job_t *job); /** * @brief Set the IKE_SA the calling thread is using. @@ -355,6 +329,10 @@ struct bus_t { * * Same as bus_t.signal(), but uses va_list argument list. * + * @todo Improve performace of vsignal implementation. This method is + * called extensively and therefore shouldn't allocate heap memory or + * do other expensive tasks! + * * @param this bus * @param singal kind of the signal (up, down, rekeyed, ...) * @param level verbosity level of the signal diff --git a/src/charon/config/backends/sqlite_backend.c b/src/charon/config/backends/sqlite_backend.c index 33093a735..e1c96c870 100644 --- a/src/charon/config/backends/sqlite_backend.c +++ b/src/charon/config/backends/sqlite_backend.c @@ -186,15 +186,15 @@ static peer_cfg_t *process_peer_cfg_row(private_sqlite_backend_t *this, 2, ike_cfg, local_id, remote_id, NULL, NULL, linked_list_create(), sqlite3_column_int(stmt, 4), /* cert_policy */ sqlite3_column_int(stmt, 5), /* auth_method */ - sqlite3_column_int(stmt, 6), /* eap_type */ + sqlite3_column_int(stmt, 6), 0 /* eap_type, vendor */ sqlite3_column_int(stmt, 7), /* keyingtries */ - sqlite3_column_int(stmt, 8), /* lifetime */ - sqlite3_column_int(stmt, 9), /* rekeytime */ - sqlite3_column_int(stmt, 10), /* jitter */ - sqlite3_column_int(stmt, 13), /* reauth */ + sqlite3_column_int(stmt, 8), /* rekey_time */ + sqlite3_column_int(stmt, 9), /* reauth_time */ + sqlite3_column_int(stmt, 10), /* jitter_time */ + sqlite3_column_int(stmt, 11), /* over_time */ sqlite3_column_int(stmt, 14), /* mobike */ - sqlite3_column_int(stmt, 11), /* dpd_delay */ - sqlite3_column_int(stmt, 12), /* dpd_action */ + sqlite3_column_int(stmt, 12), /* dpd_delay */ + sqlite3_column_int(stmt, 13), /* dpd_action */ local_vip, remote_vip, FALSE, NULL, NULL); add_children(this, peer_cfg, sqlite3_column_int(stmt, 0)); return peer_cfg; @@ -225,8 +225,9 @@ static peer_cfg_t *get_peer_cfg(private_sqlite_backend_t *this, if (sqlite3_prepare_v2(this->db, "SELECT peer_configs.oid, name, local_id, remote_id, cert_policy, " - "auth_method, eap_type, keyingtries, lifetime, rekeytime, jitter, " - "dpd_delay, dpd_action, reauth, mobike, local_vip, remote_vip, " + "auth_method, eap_type, keyingtries, " + "rekey_time, reauth_time, jitter_time, over_time, " + "dpd_delay, dpd_action, mobike, local_vip, remote_vip, " "local, remote, certreq " "FROM peer_configs, ike_configs " "ON peer_configs.ike_cfg = ike_configs.oid " diff --git a/src/charon/config/credentials/local_credential_store.c b/src/charon/config/credentials/local_credential_store.c index b71e9e9e2..b838f032d 100644 --- a/src/charon/config/credentials/local_credential_store.c +++ b/src/charon/config/credentials/local_credential_store.c @@ -18,6 +18,8 @@ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. + * + * RCSID $Id: local_credential_store.c 3346 2007-11-16 20:23:29Z andreas $ */ #include @@ -1394,7 +1396,7 @@ static void load_secrets(private_local_credential_store_t *this, bool reload) { continue; } - if (!extract_token(&ids, ':', &line)) + if (!extract_last_token(&ids, ':', &line)) { DBG1(DBG_CFG, "line %d: missing ':' separator", line_nr); goto error; diff --git a/src/charon/config/peer_cfg.c b/src/charon/config/peer_cfg.c index d61ed9512..0b5d391c4 100644 --- a/src/charon/config/peer_cfg.c +++ b/src/charon/config/peer_cfg.c @@ -127,14 +127,14 @@ struct private_peer_cfg_t { eap_type_t eap_type; /** - * number of tries after giving up if peer does not respond + * EAP vendor ID if vendor specific type is used */ - u_int32_t keyingtries; + u_int32_t eap_vendor; /** - * user reauthentication instead of rekeying + * number of tries after giving up if peer does not respond */ - bool use_reauth; + u_int32_t keyingtries; /** * enable support for MOBIKE @@ -142,20 +142,24 @@ struct private_peer_cfg_t { bool use_mobike; /** - * Time before an SA gets invalid + * Time before starting rekeying + */ + u_int32_t rekey_time; + + /** + * Time before starting reauthentication */ - u_int32_t lifetime; + u_int32_t reauth_time; /** - * Time before an SA gets rekeyed + * Time, which specifies the range of a random value substracted from above. */ - u_int32_t rekeytime; + u_int32_t jitter_time; /** - * Time, which specifies the range of a random value - * substracted from lifetime. + * Delay before deleting a rekeying/reauthenticating SA */ - u_int32_t jitter; + u_int32_t over_time; /** * What to do with an SA when other peer seams to be dead? @@ -339,8 +343,9 @@ static auth_method_t get_auth_method(private_peer_cfg_t *this) /** * Implementation of connection_t.get_eap_type. */ -static eap_type_t get_eap_type(private_peer_cfg_t *this) +static eap_type_t get_eap_type(private_peer_cfg_t *this, u_int32_t *vendor) { + *vendor = this->eap_vendor; return this->eap_type; } @@ -353,29 +358,45 @@ static u_int32_t get_keyingtries(private_peer_cfg_t *this) } /** - * Implementation of peer_cfg_t.get_soft_lifetime + * Implementation of peer_cfg_t.get_rekey_time. */ -static u_int32_t get_lifetime(private_peer_cfg_t *this, bool rekey) +static u_int32_t get_rekey_time(private_peer_cfg_t *this) { - if (rekey) + if (this->rekey_time == 0) { - if (this->jitter == 0) - { - return this->rekeytime; - } - return this->rekeytime - (random() % this->jitter); + return 0; + } + if (this->jitter_time == 0) + { + return this->rekey_time; } - return this->lifetime; + return this->rekey_time - (random() % this->jitter_time); } - + +/** + * Implementation of peer_cfg_t.get_reauth_time. + */ +static u_int32_t get_reauth_time(private_peer_cfg_t *this) +{ + if (this->reauth_time == 0) + { + return 0; + } + if (this->jitter_time == 0) + { + return this->reauth_time; + } + return this->reauth_time - (random() % this->jitter_time); +} + /** - * Implementation of peer_cfg_t.use_reauth. + * Implementation of peer_cfg_t.get_over_time. */ -static bool use_reauth(private_peer_cfg_t *this) +static u_int32_t get_over_time(private_peer_cfg_t *this) { - return this->use_reauth; + return this->over_time; } - + /** * Implementation of peer_cfg_t.use_mobike. */ @@ -503,9 +524,10 @@ peer_cfg_t *peer_cfg_create(char *name, u_int ike_version, ike_cfg_t *ike_cfg, identification_t *my_ca, identification_t *other_ca, linked_list_t *groups, cert_policy_t cert_policy, auth_method_t auth_method, eap_type_t eap_type, - u_int32_t keyingtries, u_int32_t lifetime, - u_int32_t rekeytime, u_int32_t jitter, - bool reauth, bool mobike, + u_int32_t eap_vendor, + u_int32_t keyingtries, u_int32_t rekey_time, + u_int32_t reauth_time, u_int32_t jitter_time, + u_int32_t over_time, bool mobike, u_int32_t dpd_delay, dpd_action_t dpd_action, host_t *my_virtual_ip, host_t *other_virtual_ip, bool p2p_mediation, peer_cfg_t *p2p_mediated_by, @@ -527,10 +549,11 @@ peer_cfg_t *peer_cfg_create(char *name, u_int ike_version, ike_cfg_t *ike_cfg, this->public.get_groups = (linked_list_t* (*)(peer_cfg_t *))get_groups; this->public.get_cert_policy = (cert_policy_t (*) (peer_cfg_t *))get_cert_policy; this->public.get_auth_method = (auth_method_t (*) (peer_cfg_t *))get_auth_method; - this->public.get_eap_type = (eap_type_t (*) (peer_cfg_t *))get_eap_type; + this->public.get_eap_type = (eap_type_t (*) (peer_cfg_t *,u_int32_t*))get_eap_type; this->public.get_keyingtries = (u_int32_t (*) (peer_cfg_t *))get_keyingtries; - this->public.get_lifetime = (u_int32_t (*) (peer_cfg_t *, bool rekey))get_lifetime; - this->public.use_reauth = (bool (*) (peer_cfg_t *))use_reauth; + this->public.get_rekey_time = (u_int32_t(*)(peer_cfg_t*))get_rekey_time; + this->public.get_reauth_time = (u_int32_t(*)(peer_cfg_t*))get_reauth_time; + this->public.get_over_time = (u_int32_t(*)(peer_cfg_t*))get_over_time; this->public.use_mobike = (bool (*) (peer_cfg_t *))use_mobike; this->public.get_dpd_delay = (u_int32_t (*) (peer_cfg_t *))get_dpd_delay; this->public.get_dpd_action = (dpd_action_t (*) (peer_cfg_t *))get_dpd_action; @@ -558,11 +581,20 @@ peer_cfg_t *peer_cfg_create(char *name, u_int ike_version, ike_cfg_t *ike_cfg, this->cert_policy = cert_policy; this->auth_method = auth_method; this->eap_type = eap_type; + this->eap_vendor = eap_vendor; this->keyingtries = keyingtries; - this->lifetime = lifetime; - this->rekeytime = rekeytime; - this->jitter = jitter; - this->use_reauth = reauth; + this->rekey_time = rekey_time; + this->reauth_time = reauth_time; + if (rekey_time && jitter_time > rekey_time) + { + jitter_time = rekey_time; + } + if (reauth_time && jitter_time > reauth_time) + { + jitter_time = reauth_time; + } + this->jitter_time = jitter_time; + this->over_time = over_time; this->use_mobike = mobike; this->dpd_delay = dpd_delay; this->dpd_action = dpd_action; diff --git a/src/charon/config/peer_cfg.h b/src/charon/config/peer_cfg.h index 3d238e6aa..7f1dbcab6 100644 --- a/src/charon/config/peer_cfg.h +++ b/src/charon/config/peer_cfg.h @@ -229,11 +229,16 @@ struct peer_cfg_t { /** * @brief Get the EAP type to use for peer authentication. + * + * If vendor specific types are used, a vendor ID != 0 is returned to + * to vendor argument. Then the returned type is specific for that + * vendor ID. * * @param this calling object + * @param vendor receives vendor specifier, 0 for predefined EAP types * @return authentication method */ - eap_type_t (*get_eap_type) (peer_cfg_t *this); + eap_type_t (*get_eap_type) (peer_cfg_t *this, u_int32_t *vendor); /** * @brief Get the max number of retries after timeout. @@ -244,27 +249,28 @@ struct peer_cfg_t { u_int32_t (*get_keyingtries) (peer_cfg_t *this); /** - * @brief Get the lifetime of a IKE_SA. + * @brief Get a time to start rekeying (is randomized with jitter). * - * If "rekey" is set to TRUE, a lifetime is returned before the first - * rekeying should be started. If it is FALSE, the actual lifetime is - * returned when the IKE_SA must be deleted. - * The rekey time automatically contains a jitter to avoid simlutaneous - * rekeying. - * - * @param this child_config - * @param rekey TRUE to get rekey time - * @return lifetime in seconds + * @param this calling object + * @return time in s when to start rekeying, 0 disables rekeying */ - u_int32_t (*get_lifetime) (peer_cfg_t *this, bool rekey); + u_int32_t (*get_rekey_time)(peer_cfg_t *this); /** - * @brief Should a full reauthentication be done instead of rekeying? - * + * @brief Get a time to start reauthentication (is randomized with jitter). + * * @param this calling object - * @return TRUE to use full reauthentication + * @return time in s when to start reauthentication, 0 disables it + */ + u_int32_t (*get_reauth_time)(peer_cfg_t *this); + + /** + * @brief Get the timeout of a rekeying/reauthenticating SA. + * + * @param thsi calling object + * @return timeout in s */ - bool (*use_reauth) (peer_cfg_t *this); + u_int32_t (*get_over_time)(peer_cfg_t *this); /** * @brief Use MOBIKE (RFC4555) if peer supports it? @@ -392,10 +398,12 @@ struct peer_cfg_t { * @param cert_policy should we send a certificate payload? * @param auth_method auth method to use to authenticate us * @param eap_type EAP type to use for peer authentication + * @param eap_vendor EAP vendor identifier, if vendor specific type is used * @param keyingtries how many keying tries should be done before giving up - * @param lifetime lifetime before deleting an SA - * @param rekeytime lifetime before rekeying an SA - * @param jitter range of random to substract from rekeytime + * @param rekey_time timeout before starting rekeying + * @param reauth_time timeout before starting reauthentication + * @param jitter_time timerange to randomly substract from rekey/reauth time + * @param over_time maximum overtime before closing a rekeying/reauth SA * @param reauth sould be done reauthentication instead of rekeying? * @param mobike use MOBIKE (RFC4555) if peer supports it * @param dpd_delay after how many seconds of inactivity to check DPD @@ -414,9 +422,10 @@ peer_cfg_t *peer_cfg_create(char *name, u_int ikev_version, ike_cfg_t *ike_cfg, identification_t *my_ca, identification_t *other_ca, linked_list_t *groups, cert_policy_t cert_policy, auth_method_t auth_method, eap_type_t eap_type, - u_int32_t keyingtries, u_int32_t lifetime, - u_int32_t rekeytime, u_int32_t jitter, - bool reauth, bool mobike, + u_int32_t eap_vendor, + u_int32_t keyingtries, u_int32_t rekey_time, + u_int32_t reauth_time, u_int32_t jitter_time, + u_int32_t over_time, bool mobike, u_int32_t dpd_delay, dpd_action_t dpd_action, host_t *my_virtual_ip, host_t *other_virtual_ip, bool p2p_mediation, peer_cfg_t *p2p_mediated_by, diff --git a/src/charon/control/interface_manager.c b/src/charon/control/interface_manager.c index c71036567..c14903c7d 100644 --- a/src/charon/control/interface_manager.c +++ b/src/charon/control/interface_manager.c @@ -56,18 +56,24 @@ struct private_interface_manager_t { linked_list_t *handles; }; + /** * helper struct to map bus listener callbacks to interface callbacks */ struct interface_bus_listener_t { /** - * bus listener callback function (called) + * public bus listener interface */ - bus_listener_t listener; + bus_listener_t public; + + /** + * status of the operation, return to method callers + */ + status_t status; /** - * IKE_SA to use for message filtering + * IKE SA to filter log output */ ike_sa_t *ike_sa; @@ -82,11 +88,47 @@ struct interface_bus_listener_t { void *param; /** - * caller has cancelled its listening subscription + * child configuration, used for initiate + */ + child_cfg_t *child_cfg; + + /** + * peer configuration, used for initiate + */ + peer_cfg_t *peer_cfg; + + /** + * unique ID, used for various methods + */ + u_int32_t id; +}; + + +typedef struct interface_job_t interface_job_t; + +/** + * job for asynchronous listen operations + */ +struct interface_job_t { + /** + * job interface + */ + job_t public; + + /** + * associated listener */ - bool cancelled; + interface_bus_listener_t listener; }; +/** + * Implements the famous nop operation + */ +static void nop(job_t *job) +{ + /* NOP */ +} + /** * Implementation of interface_manager_t.create_ike_sa_iterator. */ @@ -106,17 +148,16 @@ static bool initiate_listener(interface_bus_listener_t *this, signal_t signal, { if (!this->callback(this->param, signal, level, ike_sa, format, args)) { - this->cancelled = TRUE; return FALSE; } switch (signal) { + case CHILD_UP_SUCCESS: + this->status = SUCCESS; + return FALSE; case IKE_UP_FAILED: case CHILD_UP_FAILED: - case CHILD_UP_SUCCESS: - { return FALSE; - } default: break; } @@ -125,112 +166,82 @@ static bool initiate_listener(interface_bus_listener_t *this, signal_t signal, } /** - * listener function for terminate_ike + * execute function for initiate */ -static bool terminate_ike_listener(interface_bus_listener_t *this, signal_t signal, - level_t level, int thread, ike_sa_t *ike_sa, - char* format, va_list args) +static status_t initiate_execute(interface_job_t *job) { - if (this->ike_sa == ike_sa) + ike_sa_t *ike_sa; + ike_cfg_t *ike_cfg; + interface_bus_listener_t *listener = &job->listener; + peer_cfg_t *peer_cfg = listener->peer_cfg; + + ike_cfg = peer_cfg->get_ike_cfg(peer_cfg); + ike_sa = charon->ike_sa_manager->checkout_by_peer(charon->ike_sa_manager, + ike_cfg->get_my_host(ike_cfg), ike_cfg->get_other_host(ike_cfg), + peer_cfg->get_my_id(peer_cfg), peer_cfg->get_other_id(peer_cfg)); + listener->ike_sa = ike_sa; + + if (ike_sa->get_peer_cfg(ike_sa) == NULL) { - if (!this->callback(this->param, signal, level, ike_sa, format, args)) - { - this->cancelled = TRUE; - return FALSE; - } - switch (signal) - { - case IKE_DOWN_FAILED: - case IKE_DOWN_SUCCESS: - { - return FALSE; - } - default: - break; - } + ike_sa->set_peer_cfg(ike_sa, peer_cfg); } - return TRUE; -} - -/** - * listener function for terminate_child - */ -static bool terminate_child_listener(interface_bus_listener_t *this, signal_t signal, - level_t level, int thread, ike_sa_t *ike_sa, - char* format, va_list args) -{ - if (this->ike_sa == ike_sa) + peer_cfg->destroy(peer_cfg); + + if (ike_sa->initiate(ike_sa, listener->child_cfg) != SUCCESS) { - if (!this->callback(this->param, signal, level, ike_sa, format, args)) - { - this->cancelled = TRUE; - return FALSE; - } - switch (signal) - { - case IKE_DOWN_FAILED: - case IKE_DOWN_SUCCESS: - case CHILD_DOWN_FAILED: - case CHILD_DOWN_SUCCESS: - { - return FALSE; - } - default: - break; - } + return charon->ike_sa_manager->checkin_and_destroy( + charon->ike_sa_manager, ike_sa); } - return TRUE; + return charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa); } /** - * listener function for route + * Implementation of interface_manager_t.initiate. */ -static bool route_listener(interface_bus_listener_t *this, signal_t signal, - level_t level, int thread, ike_sa_t *ike_sa, - char* format, va_list args) +static status_t initiate(private_interface_manager_t *this, + peer_cfg_t *peer_cfg, child_cfg_t *child_cfg, + interface_manager_cb_t callback, void *param) { - if (this->ike_sa == ike_sa) + interface_job_t job; + + job.listener.public.signal = (void*)initiate_listener; + job.listener.ike_sa = NULL; + job.listener.callback = callback; + job.listener.param = param; + job.listener.status = FAILED; + job.listener.child_cfg = child_cfg; + job.listener.peer_cfg = peer_cfg; + job.public.execute = (void*)initiate_execute; + job.public.destroy = nop; + + if (callback == NULL) { - if (!this->callback(this->param, signal, level, ike_sa, format, args)) - { - this->cancelled = TRUE; - return FALSE; - } - switch (signal) - { - case CHILD_ROUTE_SUCCESS: - case CHILD_ROUTE_FAILED: - { - return FALSE; - } - default: - break; - } + return initiate_execute(&job); } - return TRUE; + charon->bus->listen(charon->bus, (bus_listener_t*)&job.listener, (job_t*)&job); + return job.listener.status; } /** - * listener function for unroute + * listener function for terminate_ike */ -static bool unroute_listener(interface_bus_listener_t *this, signal_t signal, - level_t level, int thread, ike_sa_t *ike_sa, - char* format, va_list args) +static bool terminate_ike_listener(interface_bus_listener_t *this, signal_t signal, + level_t level, int thread, ike_sa_t *ike_sa, + char* format, va_list args) { if (this->ike_sa == ike_sa) { if (!this->callback(this->param, signal, level, ike_sa, format, args)) { - this->cancelled = TRUE; return FALSE; } switch (signal) { - case CHILD_UNROUTE_SUCCESS: - case CHILD_UNROUTE_FAILED: - { + case IKE_DOWN_SUCCESS: + this->status = SUCCESS; + return FALSE; + case IKE_DOWN_FAILED: return FALSE; - } default: break; } @@ -239,102 +250,29 @@ static bool unroute_listener(interface_bus_listener_t *this, signal_t signal, } /** - * remove a previously registered listener from the bus + * execute function for terminate_ike */ -static void remove_listener(interface_bus_listener_t *listener) -{ - charon->bus->remove_listener(charon->bus, &listener->listener); -} - -/** - * Implementation of interface_manager_t.initiate. - */ -static status_t initiate(private_interface_manager_t *this, - peer_cfg_t *peer_cfg, child_cfg_t *child_cfg, - interface_manager_cb_t callback, void *param) +static status_t terminate_ike_execute(interface_job_t *job) { ike_sa_t *ike_sa; - ike_cfg_t *ike_cfg; - status_t retval = FAILED; - interface_bus_listener_t listener; + interface_bus_listener_t *listener = &job->listener; - ike_cfg = peer_cfg->get_ike_cfg(peer_cfg); - ike_sa = charon->ike_sa_manager->checkout_by_peer(charon->ike_sa_manager, - ike_cfg->get_my_host(ike_cfg), ike_cfg->get_other_host(ike_cfg), - peer_cfg->get_my_id(peer_cfg), peer_cfg->get_other_id(peer_cfg)); - - if (ike_sa->get_peer_cfg(ike_sa) == NULL) - { - ike_sa->set_peer_cfg(ike_sa, peer_cfg); - } - peer_cfg->destroy(peer_cfg); - - listener.listener.signal = (void*)initiate_listener; - listener.callback = callback; - listener.ike_sa = ike_sa; - listener.param = param; - listener.cancelled = FALSE; - - /* we listen passively to catch the signals we are raising in - * ike_sa->delete(). */ - if (callback) - { - charon->bus->add_listener(charon->bus, &listener.listener); - } - charon->bus->set_listen_state(charon->bus, TRUE); - if (ike_sa->initiate(ike_sa, child_cfg) != SUCCESS) - { - charon->bus->set_listen_state(charon->bus, FALSE); - charon->ike_sa_manager->checkin_and_destroy(charon->ike_sa_manager, ike_sa); - return FAILED; - } - charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa); - - if (callback == NULL) + ike_sa = charon->ike_sa_manager->checkout_by_id(charon->ike_sa_manager, + listener->id, FALSE); + if (ike_sa == NULL) { - /* don't wait for a result if no callback is specified */ - charon->bus->set_listen_state(charon->bus, FALSE); - return NEED_MORE; - } + SIG(IKE_DOWN_FAILED, "unable to terminate, IKE_SA with " + "ID %d not found", listener->id); + return NOT_FOUND; + } + listener->ike_sa = ike_sa; - /* wait until we get a result */ - while (TRUE) + if (ike_sa->delete(ike_sa) == DESTROY_ME) { - level_t level; - signal_t signal; - int thread; - ike_sa_t *current; - char* format; - va_list args; - - /* stop listening if the passive listener returned FALSE */ - if (listener.cancelled) - { - retval = NEED_MORE; - break; - } - pthread_cleanup_push((void*)remove_listener, &listener); - signal = charon->bus->listen(charon->bus, &level, &thread, - ¤t, &format, &args); - pthread_cleanup_pop(0); - /* ike_sa is a valid pointer until we get one of the signals */ - if (ike_sa == current) - { - switch (signal) - { - case CHILD_UP_SUCCESS: - retval = SUCCESS; - case CHILD_UP_FAILED: - case IKE_UP_FAILED: - break; - default: - continue; - } - break; - } + return charon->ike_sa_manager->checkin_and_destroy( + charon->ike_sa_manager, ike_sa); } - charon->bus->set_listen_state(charon->bus, FALSE); - return retval; + return charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa); } /** @@ -343,107 +281,78 @@ static status_t initiate(private_interface_manager_t *this, static status_t terminate_ike(interface_manager_t *this, u_int32_t unique_id, interface_manager_cb_t callback, void *param) { - ike_sa_t *ike_sa; - status_t status = FAILED;; - interface_bus_listener_t listener; + interface_job_t job; - ike_sa = charon->ike_sa_manager->checkout_by_id(charon->ike_sa_manager, - unique_id, FALSE); - if (ike_sa == NULL) - { - return NOT_FOUND; - } - - /* we listen passively to catch the signals we are raising in - * ike_sa->delete(). */ - listener.listener.signal = (void*)terminate_ike_listener; - listener.callback = callback; - listener.ike_sa = ike_sa; - listener.param = param; - listener.cancelled = FALSE; - if (callback) - { - charon->bus->add_listener(charon->bus, &listener.listener); - } - charon->bus->set_listen_state(charon->bus, TRUE); - status = ike_sa->delete(ike_sa); - if (status == DESTROY_ME) + job.listener.public.signal = (void*)terminate_ike_listener; + job.listener.ike_sa = NULL; + job.listener.callback = callback; + job.listener.param = param; + job.listener.status = FAILED; + job.listener.id = unique_id; + job.public.execute = (void*)terminate_ike_execute; + job.public.destroy = nop; + + if (callback == NULL) { - charon->ike_sa_manager->checkin_and_destroy(charon->ike_sa_manager, ike_sa); + return terminate_ike_execute(&job); } - else + charon->bus->listen(charon->bus, (bus_listener_t*)&job.listener, (job_t*)&job); + return job.listener.status; +} +/** + * listener function for terminate_child + */ +static bool terminate_child_listener(interface_bus_listener_t *this, signal_t signal, + level_t level, int thread, ike_sa_t *ike_sa, + char* format, va_list args) +{ + if (this->ike_sa == ike_sa) { - charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa); - - /* wait until IKE_SA is cleanly deleted using a delete message */ - while (TRUE) + if (!this->callback(this->param, signal, level, ike_sa, format, args)) { - level_t level; - signal_t signal; - int thread; - ike_sa_t *current; - char* format; - va_list args; - - /* stop listening if the passive listener returned FALSE */ - if (listener.cancelled) - { - status = NEED_MORE; - break; - } - pthread_cleanup_push((void*)remove_listener, &listener); - signal = charon->bus->listen(charon->bus, &level, &thread, - ¤t, &format, &args); - pthread_cleanup_pop(0); - - /* even if we checked in the IKE_SA, the pointer is valid until - * we get an IKE_DOWN_... */ - if (ike_sa == current) - { - switch (signal) - { - case IKE_DOWN_FAILED: - case IKE_DOWN_SUCCESS: - { - status = SUCCESS; - break; - } - default: - continue; - } + return FALSE; + } + switch (signal) + { + case CHILD_DOWN_SUCCESS: + case IKE_DOWN_SUCCESS: + this->status = SUCCESS; + return FALSE; + case IKE_DOWN_FAILED: + case CHILD_DOWN_FAILED: + return FALSE; + default: break; - } } } - charon->bus->set_listen_state(charon->bus, FALSE); - - return status; + return TRUE; } /** - * Implementation of interface_manager_t.terminate_child. + * execute function for terminate_child */ -static status_t terminate_child(interface_manager_t *this, u_int32_t reqid, - interface_manager_cb_t callback, void *param) +static status_t terminate_child_execute(interface_job_t *job) { ike_sa_t *ike_sa; child_sa_t *child_sa; iterator_t *iterator; - status_t status = FAILED; - interface_bus_listener_t listener; + interface_bus_listener_t *listener = &job->listener; ike_sa = charon->ike_sa_manager->checkout_by_id(charon->ike_sa_manager, - reqid, TRUE); + listener->id, TRUE); if (ike_sa == NULL) { + SIG(CHILD_DOWN_FAILED, "unable to terminate, CHILD_SA with " + "ID %d not found", listener->id); return NOT_FOUND; } + listener->ike_sa = ike_sa; iterator = ike_sa->create_child_sa_iterator(ike_sa); while (iterator->iterate(iterator, (void**)&child_sa)) { if (child_sa->get_state(child_sa) != CHILD_ROUTED && - child_sa->get_reqid(child_sa) == reqid) + child_sa->get_reqid(child_sa) == listener->id) { break; } @@ -453,160 +362,203 @@ static status_t terminate_child(interface_manager_t *this, u_int32_t reqid, if (child_sa == NULL) { + SIG(CHILD_DOWN_FAILED, "unable to terminate, established CHILD_SA with " + "ID %d not found", listener->id); charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa); return NOT_FOUND; } - listener.listener.signal = (void*)terminate_child_listener; - listener.callback = callback; - listener.ike_sa = ike_sa; - listener.param = param; - listener.cancelled = FALSE; - - /* we listen passively to catch the signals we are raising */ - if (callback) + if (ike_sa->delete_child_sa(ike_sa, child_sa->get_protocol(child_sa), + child_sa->get_spi(child_sa, TRUE)) == DESTROY_ME) { - charon->bus->add_listener(charon->bus, &listener.listener); + return charon->ike_sa_manager->checkin_and_destroy( + charon->ike_sa_manager, ike_sa); } - charon->bus->set_listen_state(charon->bus, TRUE); - status = ike_sa->delete_child_sa(ike_sa, child_sa->get_protocol(child_sa), - child_sa->get_spi(child_sa, TRUE)); - if (status == DESTROY_ME) + return charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa); +} + +/** + * Implementation of interface_manager_t.terminate_child. + */ +static status_t terminate_child(interface_manager_t *this, u_int32_t reqid, + interface_manager_cb_t callback, void *param) +{ + interface_job_t job; + + job.listener.public.signal = (void*)terminate_child_listener; + job.listener.ike_sa = NULL; + job.listener.callback = callback; + job.listener.param = param; + job.listener.status = FAILED; + job.listener.id = reqid; + job.public.execute = (void*)terminate_child_execute; + job.public.destroy = nop; + + if (callback == NULL) { - charon->ike_sa_manager->checkin_and_destroy(charon->ike_sa_manager, ike_sa); + return terminate_child_execute(&job); } - else + charon->bus->listen(charon->bus, (bus_listener_t*)&job.listener, (job_t*)&job); + return job.listener.status; +} + +/** + * listener function for route + */ +static bool route_listener(interface_bus_listener_t *this, signal_t signal, + level_t level, int thread, ike_sa_t *ike_sa, + char* format, va_list args) +{ + if (this->ike_sa == ike_sa) { - charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa); - - /* wait until CHILD_SA is cleanly deleted using a delete message */ - while (TRUE) + if (!this->callback(this->param, signal, level, ike_sa, format, args)) { - level_t level; - signal_t signal; - int thread; - ike_sa_t *current; - char* format; - va_list args; - - /* stop listening if the passive listener returned FALSE */ - if (listener.cancelled) - { - status = NEED_MORE; - break; - } - pthread_cleanup_push((void*)remove_listener, &listener); - signal = charon->bus->listen(charon->bus, &level, &thread, - ¤t, &format, &args); - pthread_cleanup_pop(0); - /* even if we checked in the IKE_SA, the pointer is valid until - * we get an IKE_DOWN_... */ - if (ike_sa == current) - { - switch (signal) - { - case IKE_DOWN_FAILED: - case IKE_DOWN_SUCCESS: - case CHILD_DOWN_FAILED: - case CHILD_DOWN_SUCCESS: - { - status = SUCCESS; - break; - } - default: - continue; - } + return FALSE; + } + switch (signal) + { + case CHILD_ROUTE_SUCCESS: + this->status = SUCCESS; + return FALSE; + case CHILD_ROUTE_FAILED: + return FALSE; + default: break; - } } } - charon->bus->set_listen_state(charon->bus, FALSE); - - return status; + return TRUE; } /** - * Implementation of interface_manager_t.route. + * execute function for route */ -static status_t route(interface_manager_t *this, - peer_cfg_t *peer_cfg, child_cfg_t *child_cfg, - interface_manager_cb_t callback, void *param) +static status_t route_execute(interface_job_t *job) { ike_sa_t *ike_sa; ike_cfg_t *ike_cfg; - status_t status = SUCCESS; + interface_bus_listener_t *listener = &job->listener; + peer_cfg_t *peer_cfg = listener->peer_cfg; ike_cfg = peer_cfg->get_ike_cfg(peer_cfg); ike_sa = charon->ike_sa_manager->checkout_by_peer(charon->ike_sa_manager, ike_cfg->get_my_host(ike_cfg), ike_cfg->get_other_host(ike_cfg), peer_cfg->get_my_id(peer_cfg), peer_cfg->get_other_id(peer_cfg)); + listener->ike_sa = ike_sa; if (ike_sa->get_peer_cfg(ike_sa) == NULL) { ike_sa->set_peer_cfg(ike_sa, peer_cfg); } - - /* we listen passively only, as routing is done by one thread only */ - if (callback) + if (ike_sa->route(ike_sa, listener->child_cfg) == DESTROY_ME) { - interface_bus_listener_t listener; - - listener.listener.signal = (void*)route_listener; - listener.callback = callback; - listener.ike_sa = ike_sa; - listener.param = param; - listener.cancelled = FALSE; - charon->bus->add_listener(charon->bus, &listener.listener); + return charon->ike_sa_manager->checkin_and_destroy( + charon->ike_sa_manager, ike_sa); } + return charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa); +} + +/** + * Implementation of interface_manager_t.route. + */ +static status_t route(interface_manager_t *this, + peer_cfg_t *peer_cfg, child_cfg_t *child_cfg, + interface_manager_cb_t callback, void *param) +{ + interface_job_t job; - if (ike_sa->route(ike_sa, child_cfg) != SUCCESS) + job.listener.public.signal = (void*)route_listener; + job.listener.ike_sa = NULL; + job.listener.callback = callback; + job.listener.param = param; + job.listener.status = FAILED; + job.listener.peer_cfg = peer_cfg; + job.listener.child_cfg = child_cfg; + job.public.execute = (void*)route_execute; + job.public.destroy = nop; + + if (callback == NULL) { - status = FAILED; + return route_execute(&job); } - charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa); - return status; + charon->bus->listen(charon->bus, (bus_listener_t*)&job.listener, (job_t*)&job); + return job.listener.status; } /** - * Implementation of interface_manager_t.unroute. + * listener function for unroute */ -static status_t unroute(interface_manager_t *this, u_int32_t reqid, - interface_manager_cb_t callback, void *param) +static bool unroute_listener(interface_bus_listener_t *this, signal_t signal, + level_t level, int thread, ike_sa_t *ike_sa, + char* format, va_list args) +{ + if (this->ike_sa == ike_sa) + { + if (!this->callback(this->param, signal, level, ike_sa, format, args)) + { + return FALSE; + } + switch (signal) + { + case CHILD_UNROUTE_SUCCESS: + this->status = SUCCESS; + return FALSE; + case CHILD_UNROUTE_FAILED: + return FALSE; + default: + break; + } + } + return TRUE; +} +/** + * execute function for unroute + */ +static status_t unroute_execute(interface_job_t *job) { ike_sa_t *ike_sa; - status_t status; + interface_bus_listener_t *listener = &job->listener; ike_sa = charon->ike_sa_manager->checkout_by_id(charon->ike_sa_manager, - reqid, TRUE); + listener->id, TRUE); if (ike_sa == NULL) { + SIG(CHILD_DOWN_FAILED, "unable to unroute, CHILD_SA with " + "ID %d not found", listener->id); return NOT_FOUND; } - - /* we listen passively only, as routing is done by one thread only */ - if (callback) + listener->ike_sa = ike_sa; + if (ike_sa->unroute(ike_sa, listener->id) == DESTROY_ME) { - interface_bus_listener_t listener; - - listener.listener.signal = (void*)unroute_listener; - listener.callback = callback; - listener.ike_sa = ike_sa; - listener.param = param; - listener.cancelled = FALSE; - charon->bus->add_listener(charon->bus, &listener.listener); + return charon->ike_sa_manager->checkin_and_destroy( + charon->ike_sa_manager, ike_sa); } - status = ike_sa->unroute(ike_sa, reqid); - if (status == DESTROY_ME) - { - charon->ike_sa_manager->checkin_and_destroy(charon->ike_sa_manager, ike_sa); - status = SUCCESS; - } - else + return charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa); +} + +/** + * Implementation of interface_manager_t.unroute. + */ +static status_t unroute(interface_manager_t *this, u_int32_t reqid, + interface_manager_cb_t callback, void *param) +{ + interface_job_t job; + + job.listener.public.signal = (void*)unroute_listener; + job.listener.ike_sa = NULL; + job.listener.callback = callback; + job.listener.param = param; + job.listener.status = FAILED; + job.listener.id = reqid; + job.public.execute = (void*)unroute_execute; + job.public.destroy = nop; + + if (callback == NULL) { - charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa); + return unroute_execute(&job); } - return status; + charon->bus->listen(charon->bus, (bus_listener_t*)&job.listener, (job_t*)&job); + return job.listener.status; } /** diff --git a/src/charon/control/interfaces/stroke_interface.c b/src/charon/control/interfaces/stroke_interface.c index 66ed423ae..b51d53ebd 100755 --- a/src/charon/control/interfaces/stroke_interface.c +++ b/src/charon/control/interfaces/stroke_interface.c @@ -239,13 +239,13 @@ static void stroke_add_conn(stroke_msg_t *msg, FILE *out) bool other_ca_same =FALSE; host_t *my_host, *other_host, *my_subnet, *other_subnet; host_t *my_vip = NULL, *other_vip = NULL; - linked_list_t *my_groups = linked_list_create(); linked_list_t *other_groups = linked_list_create(); proposal_t *proposal; traffic_selector_t *my_ts, *other_ts; char *interface; bool use_existing = FALSE; iterator_t *iterator; + u_int32_t vendor; pop_string(msg, &msg->add_conn.name); DBG1(DBG_CFG, "received stroke: add connection '%s'", msg->add_conn.name); @@ -262,7 +262,7 @@ static void stroke_add_conn(stroke_msg_t *msg, FILE *out) DBG2(DBG_CFG, " p2p_mediated_by=%s", msg->add_conn.p2p.mediated_by); DBG2(DBG_CFG, " p2p_peerid=%s", msg->add_conn.p2p.peerid); - my_host = msg->add_conn.me.address? + my_host = msg->add_conn.me.address ? host_create_from_string(msg->add_conn.me.address, IKE_PORT) : NULL; if (my_host == NULL) { @@ -365,11 +365,11 @@ static void stroke_add_conn(stroke_msg_t *msg, FILE *out) } } else -#endif /* P2P */ { - // no peer ID supplied, assume right ID + /* no peer ID supplied, assume right ID */ peer_id = other_id->clone(other_id); } +#endif /* P2P */ my_subnet = host_create_from_string(msg->add_conn.me.subnet ? msg->add_conn.me.subnet : msg->add_conn.me.address, IKE_PORT); @@ -544,7 +544,8 @@ static void stroke_add_conn(stroke_msg_t *msg, FILE *out) && ietfAttr_list_equals(other_groups, peer_cfg->get_groups(peer_cfg)) && peer_cfg->get_ike_version(peer_cfg) == (msg->add_conn.ikev2 ? 2 : 1) && peer_cfg->get_auth_method(peer_cfg) == msg->add_conn.auth_method - && peer_cfg->get_eap_type(peer_cfg) == msg->add_conn.eap_type) + && peer_cfg->get_eap_type(peer_cfg, &vendor) == msg->add_conn.eap_type + && vendor == msg->add_conn.eap_vendor) { DBG1(DBG_CFG, "reusing existing configuration '%s'", peer_cfg->get_name(peer_cfg)); @@ -564,9 +565,8 @@ static void stroke_add_conn(stroke_msg_t *msg, FILE *out) other_host->destroy(other_host); other_id->destroy(other_id); other_ca->destroy(other_ca); - peer_id->destroy(peer_id); + DESTROY_IF(peer_id); DESTROY_IF(mediated_by_cfg); - ietfAttr_list_destroy(my_groups); ietfAttr_list_destroy(other_groups); } else @@ -613,15 +613,25 @@ static void stroke_add_conn(stroke_msg_t *msg, FILE *out) ike_cfg->add_proposal(ike_cfg, proposal); } + u_int32_t rekey = 0, reauth = 0, over, jitter; + + jitter = msg->add_conn.rekey.margin * msg->add_conn.rekey.fuzz / 100; + over = msg->add_conn.rekey.margin; + if (msg->add_conn.rekey.reauth) + { + reauth = msg->add_conn.rekey.ike_lifetime - over; + } + else + { + rekey = msg->add_conn.rekey.ike_lifetime - over; + } peer_cfg = peer_cfg_create(msg->add_conn.name, msg->add_conn.ikev2 ? 2 : 1, ike_cfg, my_id, other_id, my_ca, other_ca, other_groups, - msg->add_conn.me.sendcert, - msg->add_conn.auth_method, msg->add_conn.eap_type, - msg->add_conn.rekey.tries, msg->add_conn.rekey.ike_lifetime, - msg->add_conn.rekey.ike_lifetime - msg->add_conn.rekey.margin, - msg->add_conn.rekey.margin * msg->add_conn.rekey.fuzz / 100, - msg->add_conn.rekey.reauth, msg->add_conn.mobike, + msg->add_conn.me.sendcert, msg->add_conn.auth_method, + msg->add_conn.eap_type, msg->add_conn.eap_vendor, + msg->add_conn.rekey.tries, rekey, reauth, jitter, over, + msg->add_conn.mobike, msg->add_conn.dpd.delay, msg->add_conn.dpd.action, my_vip, other_vip, msg->add_conn.p2p.mediation, mediated_by_cfg, peer_id); } @@ -1104,9 +1114,8 @@ static void stroke_del_ca(stroke_msg_t *msg, FILE *out) */ static void log_ike_sa(FILE *out, ike_sa_t *ike_sa, bool all) { - peer_cfg_t *cfg = ike_sa->get_peer_cfg(ike_sa); ike_sa_id_t *id = ike_sa->get_id(ike_sa); - u_int32_t next, now = time(NULL); + u_int32_t rekey, reauth; fprintf(out, "%12s[%d]: %N, %H[%D]...%H[%D]\n", ike_sa->get_name(ike_sa), ike_sa->get_unique_id(ike_sa), @@ -1116,21 +1125,26 @@ static void log_ike_sa(FILE *out, ike_sa_t *ike_sa, bool all) if (all) { - fprintf(out, "%12s[%d]: IKE SPIs: %.16llx_i%s %.16llx_r%s, ", + fprintf(out, "%12s[%d]: IKE SPIs: %.16llx_i%s %.16llx_r%s", ike_sa->get_name(ike_sa), ike_sa->get_unique_id(ike_sa), id->get_initiator_spi(id), id->is_initiator(id) ? "*" : "", id->get_responder_spi(id), id->is_initiator(id) ? "" : "*"); - ike_sa->get_stats(ike_sa, &next); - if (next) + rekey = ike_sa->get_statistic(ike_sa, STAT_REKEY_TIME); + reauth = ike_sa->get_statistic(ike_sa, STAT_REAUTH_TIME); + if (rekey) { - fprintf(out, "%s in %V\n", cfg->use_reauth(cfg) ? - "reauthentication" : "rekeying", &now, &next); + fprintf(out, ", rekeying in %V", &rekey); } - else + if (reauth) { - fprintf(out, "rekeying disabled\n"); + fprintf(out, ", reauthentication in %V", &reauth); } + if (!rekey && !reauth) + { + fprintf(out, ", rekeying disabled"); + } + fprintf(out, "\n"); } } @@ -1188,7 +1202,7 @@ static void log_child_sa(FILE *out, child_sa_t *child_sa, bool all) if (rekey) { - fprintf(out, "in %V", &now, &rekey); + fprintf(out, "in %#V", &now, &rekey); } else { @@ -1692,7 +1706,6 @@ static job_requeue_t stroke_process(int *fdp) return JOB_REQUEUE_NONE; } - /** * Implementation of private_stroke_interface_t.stroke_receive. */ diff --git a/src/charon/control/interfaces/xml_interface.c b/src/charon/control/interfaces/xml_interface.c index 02da1064d..aa2a554a0 100644 --- a/src/charon/control/interfaces/xml_interface.c +++ b/src/charon/control/interfaces/xml_interface.c @@ -91,6 +91,9 @@ static void write_id(xmlTextWriterPtr writer, char *element, identification_t *i char *type = ""; while (TRUE) { + case ID_ANY: + type = "any"; + break; case ID_IPV4_ADDR: type = "ipv4"; break; @@ -114,9 +117,6 @@ static void write_id(xmlTextWriterPtr writer, char *element, identification_t *i xmlTextWriterWriteFormatString(writer, "%D", id); break; } - case ID_ANY: - xmlTextWriterWriteAttribute(writer, "type", "any"); - break; default: /* TODO: base64 keyid */ xmlTextWriterWriteAttribute(writer, "type", "keyid"); @@ -146,17 +146,15 @@ static void write_address(xmlTextWriterPtr writer, char *element, host_t *host) } /** - * write a childEnd + * write networks element */ -static void write_childend(xmlTextWriterPtr writer, child_sa_t *child, bool local) +static void write_networks(xmlTextWriterPtr writer, char *element, + linked_list_t *list) { iterator_t *iterator; - linked_list_t *list; traffic_selector_t *ts; - xmlTextWriterWriteFormatElement(writer, "spi", "%lx", - htonl(child->get_spi(child, local))); - xmlTextWriterStartElement(writer, "networks"); - list = child->get_traffic_selectors(child, local); + + xmlTextWriterStartElement(writer, element); iterator = list->create_iterator(list, TRUE); while (iterator->iterate(iterator, (void**)&ts)) { @@ -170,6 +168,19 @@ static void write_childend(xmlTextWriterPtr writer, child_sa_t *child, bool loca xmlTextWriterEndElement(writer); } +/** + * write a childEnd + */ +static void write_childend(xmlTextWriterPtr writer, child_sa_t *child, bool local) +{ + linked_list_t *list; + + xmlTextWriterWriteFormatElement(writer, "spi", "%lx", + htonl(child->get_spi(child, local))); + list = child->get_traffic_selectors(child, local); + write_networks(writer, "networks", list); +} + /** * write a child_sa_t */ @@ -283,6 +294,201 @@ static void request_query_ikesa(xmlTextReaderPtr reader, xmlTextWriterPtr writer xmlTextWriterEndElement(writer); } +/** + * process a configlist query request message + */ +static void request_query_config(xmlTextReaderPtr reader, xmlTextWriterPtr writer) +{ + iterator_t *iterator; + peer_cfg_t *peer_cfg; + + /* */ + xmlTextWriterStartElement(writer, "configlist"); + + iterator = charon->backends->create_iterator(charon->backends); + while (iterator->iterate(iterator, (void**)&peer_cfg)) + { + iterator_t *children; + child_cfg_t *child_cfg; + ike_cfg_t *ike_cfg; + linked_list_t *list; + + if (peer_cfg->get_ike_version(peer_cfg) != 2) + { /* only IKEv2 connections yet */ + continue; + } + + /* */ + xmlTextWriterStartElement(writer, "peerconfig"); + xmlTextWriterWriteElement(writer, "name", peer_cfg->get_name(peer_cfg)); + write_id(writer, "local", peer_cfg->get_my_id(peer_cfg)); + write_id(writer, "remote", peer_cfg->get_other_id(peer_cfg)); + + /* */ + ike_cfg = peer_cfg->get_ike_cfg(peer_cfg); + xmlTextWriterStartElement(writer, "ikeconfig"); + write_address(writer, "local", ike_cfg->get_my_host(ike_cfg)); + write_address(writer, "remote", ike_cfg->get_other_host(ike_cfg)); + xmlTextWriterEndElement(writer); + /* */ + + /* */ + xmlTextWriterStartElement(writer, "childconfiglist"); + children = peer_cfg->create_child_cfg_iterator(peer_cfg); + while (children->iterate(children, (void**)&child_cfg)) + { + /* */ + xmlTextWriterStartElement(writer, "childconfig"); + xmlTextWriterWriteElement(writer, "name", + child_cfg->get_name(child_cfg)); + list = child_cfg->get_traffic_selectors(child_cfg, TRUE, NULL, NULL); + write_networks(writer, "local", list); + list->destroy_offset(list, offsetof(traffic_selector_t, destroy)); + list = child_cfg->get_traffic_selectors(child_cfg, FALSE, NULL, NULL); + write_networks(writer, "remote", list); + list->destroy_offset(list, offsetof(traffic_selector_t, destroy)); + xmlTextWriterEndElement(writer); + /* */ + } + children->destroy(children); + /* */ + xmlTextWriterEndElement(writer); + /* */ + xmlTextWriterEndElement(writer); + } + iterator->destroy(iterator); + /* */ + xmlTextWriterEndElement(writer); +} + +/** + * callback which logs to a XML writer + */ +static bool xml_callback(xmlTextWriterPtr writer, signal_t signal, level_t level, + ike_sa_t* ike_sa, char* format, va_list args) +{ + if (level <= 1) + { + /* */ + xmlTextWriterStartElement(writer, "item"); + xmlTextWriterWriteFormatAttribute(writer, "level", "%d", level); + xmlTextWriterWriteFormatAttribute(writer, "source", "%N", signal_names, signal); + xmlTextWriterWriteFormatAttribute(writer, "thread", "%u", pthread_self()); + xmlTextWriterWriteVFormatString(writer, format, args); + xmlTextWriterEndElement(writer); + /* */ + } + return TRUE; +} + +/** + * process a *terminate control request message + */ +static void request_control_terminate(xmlTextReaderPtr reader, + xmlTextWriterPtr writer, bool ike) +{ + if (xmlTextReaderRead(reader) && + xmlTextReaderNodeType(reader) == XML_READER_TYPE_TEXT) + { + const char *str; + u_int32_t id; + status_t status; + + str = xmlTextReaderConstValue(reader); + if (str == NULL || !(id = atoi(str))) + { + DBG1(DBG_CFG, "error parsing XML id string"); + return; + } + DBG1(DBG_CFG, "terminating %s_SA %d", ike ? "IKE" : "CHILD", id); + + /* */ + xmlTextWriterStartElement(writer, "log"); + if (ike) + { + status = charon->interfaces->terminate_ike( + charon->interfaces, id, + (interface_manager_cb_t)xml_callback, writer); + } + else + { + status = charon->interfaces->terminate_child( + charon->interfaces, id, + (interface_manager_cb_t)xml_callback, writer); + } + /* */ + xmlTextWriterEndElement(writer); + xmlTextWriterWriteFormatElement(writer, "status", "%d", status); + } +} + +/** + * process a *initiate control request message + */ +static void request_control_initiate(xmlTextReaderPtr reader, + xmlTextWriterPtr writer, bool ike) +{ + if (xmlTextReaderRead(reader) && + xmlTextReaderNodeType(reader) == XML_READER_TYPE_TEXT) + { + const char *str; + status_t status = FAILED; + peer_cfg_t *peer; + child_cfg_t *child = NULL; + iterator_t *iterator; + + str = xmlTextReaderConstValue(reader); + if (str == NULL) + { + DBG1(DBG_CFG, "error parsing XML config name string"); + return; + } + DBG1(DBG_CFG, "initiating %s_SA %s", ike ? "IKE" : "CHILD", str); + + /* */ + xmlTextWriterStartElement(writer, "log"); + peer = charon->backends->get_peer_cfg_by_name(charon->backends, (char*)str); + if (peer) + { + iterator = peer->create_child_cfg_iterator(peer); + if (ike) + { + if (!iterator->iterate(iterator, (void**)&child)) + { + child = NULL; + } + child->get_ref(child); + } + else + { + while (iterator->iterate(iterator, (void**)&child)) + { + if (streq(child->get_name(child), str)) + { + child->get_ref(child); + break; + } + child = NULL; + } + } + iterator->destroy(iterator); + if (child) + { + status = charon->interfaces->initiate(charon->interfaces, + peer, child, (interface_manager_cb_t)xml_callback, + writer); + } + else + { + peer->destroy(peer); + } + } + /* */ + xmlTextWriterEndElement(writer); + xmlTextWriterWriteFormatElement(writer, "status", "%d", status); + } +} + /** * process a query request */ @@ -299,12 +505,54 @@ static void request_query(xmlTextReaderPtr reader, xmlTextWriterPtr writer) request_query_ikesa(reader, writer); break; } + if (streq(xmlTextReaderConstName(reader), "configlist")) + { + request_query_config(reader, writer); + break; + } } } /* */ xmlTextWriterEndElement(writer); } +/** + * process a control request + */ +static void request_control(xmlTextReaderPtr reader, xmlTextWriterPtr writer) +{ + /* */ + xmlTextWriterStartElement(writer, "control"); + while (xmlTextReaderRead(reader)) + { + if (xmlTextReaderNodeType(reader) == XML_READER_TYPE_ELEMENT) + { + if (streq(xmlTextReaderConstName(reader), "ikesaterminate")) + { + request_control_terminate(reader, writer, TRUE); + break; + } + if (streq(xmlTextReaderConstName(reader), "childsaterminate")) + { + request_control_terminate(reader, writer, FALSE); + break; + } + if (streq(xmlTextReaderConstName(reader), "ikesainitiate")) + { + request_control_initiate(reader, writer, TRUE); + break; + } + if (streq(xmlTextReaderConstName(reader), "childsainitiate")) + { + request_control_initiate(reader, writer, FALSE); + break; + } + } + } + /* */ + xmlTextWriterEndElement(writer); +} + /** * process a request message */ @@ -337,6 +585,11 @@ static void request(xmlTextReaderPtr reader, char *id, int fd) request_query(reader, writer); break; } + if (streq(xmlTextReaderConstName(reader), "control")) + { + request_control(reader, writer); + break; + } } } /* and close document */ diff --git a/src/charon/daemon.c b/src/charon/daemon.c index 9e151c305..ee9710424 100644 --- a/src/charon/daemon.c +++ b/src/charon/daemon.c @@ -338,7 +338,7 @@ static bool initialize(private_daemon_t *this, bool syslog, level_t levels[]) this->public.interfaces = interface_manager_create(); this->public.backends = backend_manager_create(); this->public.kernel_interface = kernel_interface_create(); - this->public.socket = socket_create(IKEV2_UDP_PORT, IKEV2_NATT_PORT); + this->public.socket = socket_create(); this->public.sender = sender_create(); this->public.receiver = receiver_create(); diff --git a/src/charon/encoding/payloads/configuration_attribute.c b/src/charon/encoding/payloads/configuration_attribute.c index 0aa82169f..afd08c6be 100644 --- a/src/charon/encoding/payloads/configuration_attribute.c +++ b/src/charon/encoding/payloads/configuration_attribute.c @@ -165,7 +165,7 @@ static status_t verify(private_configuration_attribute_t *this) default: DBG1(DBG_ENC, "unknown attribute type %N", configuration_attribute_type_names, this->attribute_type); - return FAILED; + break; } if (failed) diff --git a/src/charon/encoding/payloads/eap_payload.c b/src/charon/encoding/payloads/eap_payload.c index 79ab32fe5..345114af0 100644 --- a/src/charon/encoding/payloads/eap_payload.c +++ b/src/charon/encoding/payloads/eap_payload.c @@ -235,11 +235,23 @@ static u_int8_t get_identifier(private_eap_payload_t *this) /** * Implementation of eap_payload_t.get_type. */ -static eap_type_t get_type(private_eap_payload_t *this) +static eap_type_t get_type(private_eap_payload_t *this, u_int32_t *vendor) { + eap_type_t type; + + *vendor = 0; if (this->data.len > 4) { - return *(this->data.ptr + 4); + type = *(this->data.ptr + 4); + if (type != EAP_EXPANDED) + { + return type; + } + if (this->data.len >= 12) + { + *vendor = ntohl(*(u_int32_t*)(this->data.ptr + 4)) & 0x00FFFFFF; + return ntohl(*(u_int32_t*)(this->data.ptr + 8)); + } } return 0; } @@ -275,7 +287,7 @@ eap_payload_t *eap_payload_create() this->public.set_data = (void (*) (eap_payload_t *,chunk_t))set_data; this->public.get_code = (eap_code_t (*) (eap_payload_t*))get_code; this->public.get_identifier = (u_int8_t (*) (eap_payload_t*))get_identifier; - this->public.get_type = (eap_type_t (*) (eap_payload_t*))get_type; + this->public.get_type = (eap_type_t (*) (eap_payload_t*,u_int32_t*))get_type; /* private variables */ this->critical = FALSE; @@ -329,3 +341,4 @@ eap_payload_t *eap_payload_create_nak() this->set_data(this, data); return this; } + diff --git a/src/charon/encoding/payloads/eap_payload.h b/src/charon/encoding/payloads/eap_payload.h index 13c0ade80..3addbb838 100644 --- a/src/charon/encoding/payloads/eap_payload.h +++ b/src/charon/encoding/payloads/eap_payload.h @@ -95,9 +95,10 @@ struct eap_payload_t { * @brief Get the EAP method type. * * @param this calling eap_payload_t object - * @return EAP method type + * @param vendor pointer receiving vendor identifier + * @return EAP method type, vendor specific if vendor != 0 */ - eap_type_t (*get_type) (eap_payload_t *this); + eap_type_t (*get_type) (eap_payload_t *this, u_int32_t *vendor); /** * @brief Destroys an eap_payload_t object. diff --git a/src/charon/encoding/payloads/endpoint_notify.c b/src/charon/encoding/payloads/endpoint_notify.c index 30f3ecd5f..98bfb2ea0 100644 --- a/src/charon/encoding/payloads/endpoint_notify.c +++ b/src/charon/encoding/payloads/endpoint_notify.c @@ -76,6 +76,13 @@ struct private_endpoint_notify_t { +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ */ +ENUM(p2p_endpoint_type_names, HOST, RELAYED, + "HOST", + "SERVER_REFLEXIVE", + "PEER_REFLEXIVE", + "RELAYED" +); + /** * Helper functions to parse integer values */ @@ -152,14 +159,10 @@ static status_t parse_notification_data(private_endpoint_notify_t *this, chunk_t switch(this->family) { - case NO_FAMILY: - this->endpoint = NULL; - break; - case IPv6: addr_family = AF_INET6; addr.len = 16; - // fall-through + /* fall-through */ case IPv4: if (parse_uint16(&cur, top, &port) != SUCCESS) { @@ -177,8 +180,11 @@ static status_t parse_notification_data(private_endpoint_notify_t *this, chunk_t this->endpoint = host_create_from_chunk(addr_family, addr, port); break; + case NO_FAMILY: + default: + this->endpoint = NULL; + break; } - return SUCCESS; } @@ -213,7 +219,7 @@ static chunk_t build_notification_data(private_endpoint_notify_t *this) } port_chunk = chunk_from_thing(port); - // data = prio | family | type | port | addr + /* data = prio | family | type | port | addr */ data = chunk_cat("ccccc", prio_chunk, family_chunk, type_chunk, port_chunk, addr_chunk); DBG3(DBG_IKE, "p2p_endpoint_data %B", &data); @@ -251,7 +257,7 @@ static u_int32_t get_priority(private_endpoint_notify_t *this) */ static void set_priority(private_endpoint_notify_t *this, u_int32_t priority) { - return this->priority = priority; + this->priority = priority; } /** @@ -368,13 +374,15 @@ endpoint_notify_t *endpoint_notify_create_from_host(p2p_endpoint_type_t type, ho this->priority = pow(2, 16) * P2P_PRIO_PEER; break; case RELAYED: + default: this->priority = pow(2, 16) * P2P_PRIO_RELAY; break; } this->priority += 65535; - if (!host) { + if (!host) + { return &this->public; } @@ -387,7 +395,8 @@ endpoint_notify_t *endpoint_notify_create_from_host(p2p_endpoint_type_t type, ho this->family = IPv6; break; default: - // unsupported family type, we do not set the hsot (family is set to NO_FAMILY) + /* unsupported family type, we do not set the hsot + * (family is set to NO_FAMILY) */ return &this->public; } diff --git a/src/charon/encoding/payloads/endpoint_notify.h b/src/charon/encoding/payloads/endpoint_notify.h index 272301d5b..4a3a68f95 100644 --- a/src/charon/encoding/payloads/endpoint_notify.h +++ b/src/charon/encoding/payloads/endpoint_notify.h @@ -35,6 +35,11 @@ typedef struct endpoint_notify_t endpoint_notify_t; #include +/** + * @brief P2P endpoint families. + * + * @ingroup payloads + */ enum p2p_endpoint_family_t { NO_FAMILY = 0, @@ -47,6 +52,11 @@ enum p2p_endpoint_family_t { }; +/** + * @brief P2P endpoint types. + * + * @ingroup payloads + */ enum p2p_endpoint_type_t { NO_TYPE = 0, @@ -63,6 +73,13 @@ enum p2p_endpoint_type_t { }; +/** + * enum name for p2p_endpoint_type_t. + * + * @ingroup payloads + */ +extern enum_name_t *p2p_endpoint_type_names; + /** * @brief Class representing a P2P_ENDPOINT notify. In fact it's not * the notify per se, but the notification data of that notify that is diff --git a/src/charon/encoding/payloads/ike_header.c b/src/charon/encoding/payloads/ike_header.c index 7253e4f51..3a171b095 100644 --- a/src/charon/encoding/payloads/ike_header.c +++ b/src/charon/encoding/payloads/ike_header.c @@ -192,7 +192,8 @@ static status_t verify(private_ike_header_t *this) if (this->initiator_spi == 0 #ifdef P2P - // we allow zero spi for INFORMATIONAL exchanges, to allow P2P connectivity checks + /* we allow zero spi for INFORMATIONAL exchanges, + * to allow P2P connectivity checks */ && this->exchange_type != INFORMATIONAL #endif /* P2P */ ) diff --git a/src/charon/encoding/payloads/notify_payload.c b/src/charon/encoding/payloads/notify_payload.c index 74a6c3197..d32257af6 100644 --- a/src/charon/encoding/payloads/notify_payload.c +++ b/src/charon/encoding/payloads/notify_payload.c @@ -57,13 +57,9 @@ ENUM_NEXT(notify_type_names, SINGLE_PAIR_REQUIRED, UNEXPECTED_NAT_DETECTED, AUTH "INVALID_SELECTORS", "UNACCEPTABLE_ADDRESSES", "UNEXPECTED_NAT_DETECTED"); -#ifdef P2P ENUM_NEXT(notify_type_names, P2P_CONNECT_FAILED, P2P_CONNECT_FAILED, UNEXPECTED_NAT_DETECTED, "P2P_CONNECT_FAILED"); ENUM_NEXT(notify_type_names, INITIAL_CONTACT, AUTH_LIFETIME, P2P_CONNECT_FAILED, -#else -ENUM_NEXT(notify_type_names, INITIAL_CONTACT, AUTH_LIFETIME, UNEXPECTED_NAT_DETECTED, -#endif /* P2P */ "INITIAL_CONTACT", "SET_WINDOW_SIZE", "ADDITIONAL_TS_POSSIBLE", @@ -86,7 +82,6 @@ ENUM_NEXT(notify_type_names, INITIAL_CONTACT, AUTH_LIFETIME, UNEXPECTED_NAT_DETE "AUTH_LIFETIME"); ENUM_NEXT(notify_type_names, EAP_ONLY_AUTHENTICATION, EAP_ONLY_AUTHENTICATION, AUTH_LIFETIME, "EAP_ONLY_AUTHENTICATION"); -#ifdef P2P ENUM_NEXT(notify_type_names, USE_BEET_MODE, USE_BEET_MODE, EAP_ONLY_AUTHENTICATION, "USE_BEET_MODE"); ENUM_NEXT(notify_type_names, P2P_MEDIATION, P2P_RESPONSE, USE_BEET_MODE, @@ -97,9 +92,6 @@ ENUM_NEXT(notify_type_names, P2P_MEDIATION, P2P_RESPONSE, USE_BEET_MODE, "P2P_SESSIONKEY", "P2P_RESPONSE"); ENUM_END(notify_type_names, P2P_RESPONSE); -#else -ENUM_END(notify_type_names, EAP_ONLY_AUTHENTICATION); -#endif /* P2P */ ENUM_BEGIN(notify_type_short_names, UNSUPPORTED_CRITICAL_PAYLOAD, UNSUPPORTED_CRITICAL_PAYLOAD, @@ -128,13 +120,9 @@ ENUM_NEXT(notify_type_short_names, SINGLE_PAIR_REQUIRED, UNEXPECTED_NAT_DETECTED "INVAL_SEL", "UNACCEPT_ADDR", "UNEXPECT_NAT"); -#ifdef P2P ENUM_NEXT(notify_type_short_names, P2P_CONNECT_FAILED, P2P_CONNECT_FAILED, UNEXPECTED_NAT_DETECTED, "P2P_CONN_FAIL"); ENUM_NEXT(notify_type_short_names, INITIAL_CONTACT, AUTH_LIFETIME, P2P_CONNECT_FAILED, -#else -ENUM_NEXT(notify_type_short_names, INITIAL_CONTACT, AUTH_LIFETIME, UNEXPECTED_NAT_DETECTED, -#endif /* P2P */ "INIT_CONTACT", "SET_WINSIZE", "ADD_TS_POSS", @@ -157,7 +145,6 @@ ENUM_NEXT(notify_type_short_names, INITIAL_CONTACT, AUTH_LIFETIME, UNEXPECTED_NA "AUTH_LFT"); ENUM_NEXT(notify_type_short_names, EAP_ONLY_AUTHENTICATION, EAP_ONLY_AUTHENTICATION, AUTH_LIFETIME, "EAP_ONLY"); -#ifdef P2P ENUM_NEXT(notify_type_short_names, USE_BEET_MODE, USE_BEET_MODE, EAP_ONLY_AUTHENTICATION, "BEET_MODE"); ENUM_NEXT(notify_type_short_names, P2P_MEDIATION, P2P_RESPONSE, USE_BEET_MODE, @@ -168,9 +155,6 @@ ENUM_NEXT(notify_type_short_names, P2P_MEDIATION, P2P_RESPONSE, USE_BEET_MODE, "P2P_SKEY", "P2P_R"); ENUM_END(notify_type_short_names, P2P_RESPONSE); -#else -ENUM_END(notify_type_short_names, EAP_ONLY_AUTHENTICATION); -#endif /* P2P */ typedef struct private_notify_payload_t private_notify_payload_t; @@ -342,7 +326,15 @@ static status_t verify(private_notify_payload_t *this) } break; } - // FIXME: check size of P2P-NAT-T payloads + case AUTH_LIFETIME: + { + if (this->notification_data.len != 4) + { + bad_length = TRUE; + } + break; + } + /* FIXME: check size of P2P-NAT-T payloads */ default: /* TODO: verify */ break; diff --git a/src/charon/encoding/payloads/notify_payload.h b/src/charon/encoding/payloads/notify_payload.h index 4a9ad992b..03f61d473 100644 --- a/src/charon/encoding/payloads/notify_payload.h +++ b/src/charon/encoding/payloads/notify_payload.h @@ -68,10 +68,9 @@ enum notify_type_t { INVALID_SELECTORS = 39, UNACCEPTABLE_ADDRESSES = 40, UNEXPECTED_NAT_DETECTED = 41, -#ifdef P2P /* P2P-NAT-T, private use */ P2P_CONNECT_FAILED = 8192, -#endif /* P2P */ + /* notify status messages */ INITIAL_CONTACT = 16384, SET_WINDOW_SIZE = 16385, @@ -99,7 +98,6 @@ enum notify_type_t { EAP_ONLY_AUTHENTICATION = 40960, /* BEET mode, not even a draft yet. private use */ USE_BEET_MODE = 40961, -#ifdef P2P /* P2P-NAT-T, private use */ P2P_MEDIATION = 40962, P2P_ENDPOINT = 40963, @@ -107,7 +105,6 @@ enum notify_type_t { P2P_SESSIONID = 40965, P2P_SESSIONKEY = 40966, P2P_RESPONSE = 40967 -#endif /* P2P */ }; /** diff --git a/src/charon/network/socket-raw.c b/src/charon/network/socket-raw.c new file mode 100644 index 000000000..3b76ae570 --- /dev/null +++ b/src/charon/network/socket-raw.c @@ -0,0 +1,771 @@ +/** + * @file socket.c + * + * @brief Implementation of socket_t. + * + */ + +/* + * Copyright (C) 2006 Tobias Brunner, Daniel Roethlisberger + * Copyright (C) 2005-2006 Martin Willi + * Copyright (C) 2005 Jan Hutter + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "socket.h" + +#include + +/* constants for packet handling */ +#define IP_LEN sizeof(struct iphdr) +#define IP6_LEN sizeof(struct ip6_hdr) +#define UDP_LEN sizeof(struct udphdr) +#define MARKER_LEN sizeof(u_int32_t) + +/* offsets for packet handling */ +#define IP_PROTO_OFFSET 9 +#define IP6_PROTO_OFFSET 6 +#define IKE_VERSION_OFFSET 17 +#define IKE_LENGTH_OFFSET 24 + +/* from linux/in.h */ +#ifndef IP_IPSEC_POLICY +#define IP_IPSEC_POLICY 16 +#endif /*IP_IPSEC_POLICY*/ + +/* from linux/udp.h */ +#ifndef UDP_ENCAP +#define UDP_ENCAP 100 +#endif /*UDP_ENCAP*/ + +#ifndef UDP_ENCAP_ESPINUDP +#define UDP_ENCAP_ESPINUDP 2 +#endif /*UDP_ENCAP_ESPINUDP*/ + +/* needed for older kernel headers */ +#ifndef IPV6_2292PKTINFO +#define IPV6_2292PKTINFO 2 +#endif /*IPV6_2292PKTINFO*/ + +/* missing on uclibc */ +#ifndef IPV6_IPSEC_POLICY +#define IPV6_IPSEC_POLICY 34 +#endif /*IPV6_IPSEC_POLICY*/ + +typedef struct private_socket_t private_socket_t; + +/** + * Private data of an socket_t object + */ +struct private_socket_t{ + /** + * public functions + */ + socket_t public; + + /** + * regular port + */ + int port; + + /** + * port used for nat-t + */ + int natt_port; + + /** + * raw receiver socket for IPv4 + */ + int recv4; + + /** + * raw receiver socket for IPv6 + */ + int recv6; + + /** + * send socket on regular port for IPv4 + */ + int send4; + + /** + * send socket on regular port for IPv6 + */ + int send6; + + /** + * send socket on nat-t port for IPv4 + */ + int send4_natt; + + /** + * send socket on nat-t port for IPv6 + */ + int send6_natt; +}; + +/** + * implementation of socket_t.receive + */ +static status_t receiver(private_socket_t *this, packet_t **packet) +{ + char buffer[MAX_PACKET]; + chunk_t data; + packet_t *pkt; + struct udphdr *udp; + host_t *source = NULL, *dest = NULL; + int bytes_read = 0; + int data_offset, oldstate; + fd_set rfds; + + FD_ZERO(&rfds); + + if (this->recv4) + { + FD_SET(this->recv4, &rfds); + } + if (this->recv6) + { + FD_SET(this->recv6, &rfds); + } + + DBG2(DBG_NET, "waiting for data on raw sockets"); + + pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, &oldstate); + if (select(max(this->recv4, this->recv6) + 1, &rfds, NULL, NULL, NULL) <= 0) + { + pthread_setcancelstate(oldstate, NULL); + return FAILED; + } + pthread_setcancelstate(oldstate, NULL); + + if (this->recv4 && FD_ISSET(this->recv4, &rfds)) + { + /* IPv4 raw sockets return the IP header. We read src/dest + * information directly from the raw header */ + struct iphdr *ip; + struct sockaddr_in src, dst; + + bytes_read = recv(this->recv4, buffer, MAX_PACKET, 0); + if (bytes_read < 0) + { + DBG1(DBG_NET, "error reading from IPv4 socket: %s", strerror(errno)); + return FAILED; + } + DBG3(DBG_NET, "received IPv4 packet %b", buffer, bytes_read); + + /* read source/dest from raw IP/UDP header */ + if (bytes_read < IP_LEN + UDP_LEN + MARKER_LEN) + { + DBG1(DBG_NET, "received IPv4 packet too short (%d bytes)", + bytes_read); + return FAILED; + } + ip = (struct iphdr*) buffer; + udp = (struct udphdr*) (buffer + IP_LEN); + src.sin_family = AF_INET; + src.sin_addr.s_addr = ip->saddr; + src.sin_port = udp->source; + dst.sin_family = AF_INET; + dst.sin_addr.s_addr = ip->daddr; + dst.sin_port = udp->dest; + source = host_create_from_sockaddr((sockaddr_t*)&src); + dest = host_create_from_sockaddr((sockaddr_t*)&dst); + + pkt = packet_create(); + pkt->set_source(pkt, source); + pkt->set_destination(pkt, dest); + DBG2(DBG_NET, "received packet: from %#H to %#H", source, dest); + data_offset = IP_LEN + UDP_LEN; + /* remove non esp marker */ + if (dest->get_port(dest) == IKEV2_NATT_PORT) + { + data_offset += MARKER_LEN; + } + /* fill in packet */ + data.len = bytes_read - data_offset; + data.ptr = malloc(data.len); + memcpy(data.ptr, buffer + data_offset, data.len); + pkt->set_data(pkt, data); + } + else if (this->recv6 && FD_ISSET(this->recv6, &rfds)) + { + /* IPv6 raw sockets return no IP header. We must query + * src/dest via socket options/ancillary data */ + struct msghdr msg; + struct cmsghdr *cmsgptr; + struct sockaddr_in6 src, dst; + struct iovec iov; + char ancillary[64]; + + msg.msg_name = &src; + msg.msg_namelen = sizeof(src); + iov.iov_base = buffer; + iov.iov_len = sizeof(buffer); + msg.msg_iov = &iov; + msg.msg_iovlen = 1; + msg.msg_control = ancillary; + msg.msg_controllen = sizeof(ancillary); + msg.msg_flags = 0; + + bytes_read = recvmsg(this->recv6, &msg, 0); + if (bytes_read < 0) + { + DBG1(DBG_NET, "error reading from IPv6 socket: %s", strerror(errno)); + return FAILED; + } + DBG3(DBG_NET, "received IPv6 packet %b", buffer, bytes_read); + + if (bytes_read < IP_LEN + UDP_LEN + MARKER_LEN) + { + DBG3(DBG_NET, "received IPv6 packet too short (%d bytes)", + bytes_read); + return FAILED; + } + + /* read ancillary data to get destination address */ + for (cmsgptr = CMSG_FIRSTHDR(&msg); cmsgptr != NULL; + cmsgptr = CMSG_NXTHDR(&msg, cmsgptr)) + { + if (cmsgptr->cmsg_len == 0) + { + DBG1(DBG_NET, "error reading IPv6 ancillary data"); + return FAILED; + } + if (cmsgptr->cmsg_level == SOL_IPV6 && + cmsgptr->cmsg_type == IPV6_2292PKTINFO) + { + struct in6_pktinfo *pktinfo; + pktinfo = (struct in6_pktinfo*)CMSG_DATA(cmsgptr); + + memset(&dst, 0, sizeof(dst)); + memcpy(&dst.sin6_addr, &pktinfo->ipi6_addr, sizeof(dst.sin6_addr)); + dst.sin6_family = AF_INET6; + udp = (struct udphdr*) (buffer); + dst.sin6_port = udp->dest; + src.sin6_port = udp->source; + dest = host_create_from_sockaddr((sockaddr_t*)&dst); + } + } + /* ancillary data missing? */ + if (dest == NULL) + { + DBG1(DBG_NET, "error reading IPv6 packet header"); + return FAILED; + } + + source = host_create_from_sockaddr((sockaddr_t*)&src); + + pkt = packet_create(); + pkt->set_source(pkt, source); + pkt->set_destination(pkt, dest); + DBG2(DBG_NET, "received packet: from %#H to %#H", source, dest); + data_offset = UDP_LEN; + /* remove non esp marker */ + if (dest->get_port(dest) == IKEV2_NATT_PORT) + { + data_offset += MARKER_LEN; + } + /* fill in packet */ + data.len = bytes_read - data_offset; + data.ptr = malloc(data.len); + memcpy(data.ptr, buffer + data_offset, data.len); + pkt->set_data(pkt, data); + } + else + { + /* oops, shouldn't happen */ + return FAILED; + } + + /* return packet */ + *packet = pkt; + return SUCCESS; +} + +/** + * implementation of socket_t.send + */ +status_t sender(private_socket_t *this, packet_t *packet) +{ + int sport, skt, family; + ssize_t bytes_sent; + chunk_t data, marked; + host_t *src, *dst; + struct msghdr msg; + struct cmsghdr *cmsg; + struct iovec iov; + + src = packet->get_source(packet); + dst = packet->get_destination(packet); + data = packet->get_data(packet); + + DBG2(DBG_NET, "sending packet: from %#H to %#H", src, dst); + + /* send data */ + sport = src->get_port(src); + family = dst->get_family(dst); + if (sport == IKEV2_UDP_PORT) + { + if (family == AF_INET) + { + skt = this->send4; + } + else + { + skt = this->send6; + } + } + else if (sport == IKEV2_NATT_PORT) + { + if (family == AF_INET) + { + skt = this->send4_natt; + } + else + { + skt = this->send6_natt; + } + /* NAT keepalives without marker */ + if (data.len != 1 || data.ptr[0] != 0xFF) + { + /* add non esp marker to packet */ + if (data.len > MAX_PACKET - MARKER_LEN) + { + DBG1(DBG_NET, "unable to send packet: it's too big (%d bytes)", + data.len); + return FAILED; + } + marked = chunk_alloc(data.len + MARKER_LEN); + memset(marked.ptr, 0, MARKER_LEN); + memcpy(marked.ptr + MARKER_LEN, data.ptr, data.len); + /* let the packet do the clean up for us */ + packet->set_data(packet, marked); + data = marked; + } + } + else + { + DBG1(DBG_NET, "unable to locate a send socket for port %d", sport); + return FAILED; + } + + memset(&msg, 0, sizeof(struct msghdr)); + msg.msg_name = dst->get_sockaddr(dst);; + msg.msg_namelen = *dst->get_sockaddr_len(dst); + iov.iov_base = data.ptr; + iov.iov_len = data.len; + msg.msg_iov = &iov; + msg.msg_iovlen = 1; + msg.msg_flags = 0; + + if (!dst->is_anyaddr(dst)) + { + if (family == AF_INET) + { + char buf[CMSG_SPACE(sizeof(struct in_pktinfo))]; + struct in_pktinfo *pktinfo; + struct sockaddr_in *sin; + + msg.msg_control = buf; + msg.msg_controllen = sizeof(buf); + cmsg = CMSG_FIRSTHDR(&msg); + cmsg->cmsg_level = SOL_IP; + cmsg->cmsg_type = IP_PKTINFO; + cmsg->cmsg_len = CMSG_LEN(sizeof(struct in_pktinfo)); + pktinfo = (struct in_pktinfo*)CMSG_DATA(cmsg); + memset(pktinfo, 0, sizeof(struct in_pktinfo)); + sin = (struct sockaddr_in*)src->get_sockaddr(src); + memcpy(&pktinfo->ipi_spec_dst, &sin->sin_addr, sizeof(struct in_addr)); + } + else + { + char buf[CMSG_SPACE(sizeof(struct in6_pktinfo))]; + struct in6_pktinfo *pktinfo; + struct sockaddr_in6 *sin; + + msg.msg_control = buf; + msg.msg_controllen = sizeof(buf); + cmsg = CMSG_FIRSTHDR(&msg); + cmsg->cmsg_level = SOL_IPV6; + cmsg->cmsg_type = IPV6_2292PKTINFO; + cmsg->cmsg_len = CMSG_LEN(sizeof(struct in6_pktinfo)); + pktinfo = (struct in6_pktinfo*)CMSG_DATA(cmsg); + memset(pktinfo, 0, sizeof(struct in6_pktinfo)); + sin = (struct sockaddr_in6*)src->get_sockaddr(src); + memcpy(&pktinfo->ipi6_addr, &sin->sin6_addr, sizeof(struct in6_addr)); + } + } + + bytes_sent = sendmsg(skt, &msg, 0); + + if (bytes_sent != data.len) + { + DBG1(DBG_NET, "error writing to socket: %s", strerror(errno)); + return FAILED; + } + return SUCCESS; +} + +/** + * open a socket to send packets + */ +static int open_send_socket(private_socket_t *this, int family, u_int16_t port) +{ + int on = TRUE; + int type = UDP_ENCAP_ESPINUDP; + struct sockaddr_storage addr; + u_int sol, ipsec_policy; + struct sadb_x_policy policy; + int skt; + + memset(&addr, 0, sizeof(addr)); + /* precalculate constants depending on address family */ + switch (family) + { + case AF_INET: + { + struct sockaddr_in *sin = (struct sockaddr_in *)&addr; + sin->sin_family = AF_INET; + sin->sin_addr.s_addr = INADDR_ANY; + sin->sin_port = htons(port); + sol = SOL_IP; + ipsec_policy = IP_IPSEC_POLICY; + break; + } + case AF_INET6: + { + struct sockaddr_in6 *sin6 = (struct sockaddr_in6 *)&addr; + sin6->sin6_family = AF_INET6; + memcpy(&sin6->sin6_addr, &in6addr_any, sizeof(in6addr_any)); + sin6->sin6_port = htons(port); + sol = SOL_IPV6; + ipsec_policy = IPV6_IPSEC_POLICY; + break; + } + default: + return 0; + } + + skt = socket(family, SOCK_DGRAM, IPPROTO_UDP); + if (skt < 0) + { + DBG1(DBG_NET, "could not open send socket: %s", strerror(errno)); + return 0; + } + + if (setsockopt(skt, SOL_SOCKET, SO_REUSEADDR, (void*)&on, sizeof(on)) < 0) + { + DBG1(DBG_NET, "unable to set SO_REUSEADDR on send socket: %s", + strerror(errno)); + close(skt); + return 0; + } + + /* bypass outgoung IKE traffic on send socket */ + memset(&policy, 0, sizeof(policy)); + policy.sadb_x_policy_len = sizeof(policy) / sizeof(u_int64_t); + policy.sadb_x_policy_exttype = SADB_X_EXT_POLICY; + policy.sadb_x_policy_type = IPSEC_POLICY_BYPASS; + policy.sadb_x_policy_dir = IPSEC_DIR_OUTBOUND; + + if (setsockopt(skt, sol, ipsec_policy, &policy, sizeof(policy)) < 0) + { + DBG1(DBG_NET, "unable to set IPSEC_POLICY on send socket: %s", + strerror(errno)); + close(skt); + return 0; + } + + /* We don't receive packets on the send socket, but we need a INBOUND policy. + * Otherwise, UDP decapsulation does not work!!! */ + policy.sadb_x_policy_dir = IPSEC_DIR_INBOUND; + if (setsockopt(skt, sol, ipsec_policy, &policy, sizeof(policy)) < 0) + { + DBG1(DBG_NET, "unable to set IPSEC_POLICY on send socket: %s", + strerror(errno)); + close(skt); + return 0; + } + + /* bind the send socket */ + if (bind(skt, (struct sockaddr *)&addr, sizeof(addr)) < 0) + { + DBG1(DBG_NET, "unable to bind send socket: %s", + strerror(errno)); + close(skt); + return 0; + } + + if (family == AF_INET) + { + /* enable UDP decapsulation globally, only for one socket needed */ + if (setsockopt(skt, SOL_UDP, UDP_ENCAP, &type, sizeof(type)) < 0) + { + DBG1(DBG_NET, "unable to set UDP_ENCAP: %s; NAT-T may fail", + strerror(errno)); + } + } + + return skt; +} + +/** + * open a socket to receive packets + */ +static int open_recv_socket(private_socket_t *this, int family) +{ + int skt; + int on = TRUE; + u_int proto_offset, ip_len, sol, ipsec_policy, udp_header, ike_header; + struct sadb_x_policy policy; + + /* precalculate constants depending on address family */ + switch (family) + { + case AF_INET: + proto_offset = IP_PROTO_OFFSET; + ip_len = IP_LEN; + sol = SOL_IP; + ipsec_policy = IP_IPSEC_POLICY; + break; + case AF_INET6: + proto_offset = IP6_PROTO_OFFSET; + ip_len = 0; /* IPv6 raw sockets contain no IP header */ + sol = SOL_IPV6; + ipsec_policy = IPV6_IPSEC_POLICY; + break; + default: + return 0; + } + udp_header = ip_len; + ike_header = ip_len + UDP_LEN; + + /* This filter code filters out all non-IKEv2 traffic on + * a SOCK_RAW IP_PROTP_UDP socket. Handling of other + * IKE versions is done in pluto. + */ + struct sock_filter ikev2_filter_code[] = + { + /* Destination Port must be either port or natt_port */ + BPF_STMT(BPF_LD+BPF_H+BPF_ABS, udp_header + 2), + BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, IKEV2_UDP_PORT, 1, 0), + BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, IKEV2_NATT_PORT, 5, 12), + /* port */ + /* IKE version must be 2.0 */ + BPF_STMT(BPF_LD+BPF_B+BPF_ABS, ike_header + IKE_VERSION_OFFSET), + BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x20, 0, 10), + /* packet length is length in IKEv2 header + ip header + udp header */ + BPF_STMT(BPF_LD+BPF_W+BPF_ABS, ike_header + IKE_LENGTH_OFFSET), + BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, ip_len + UDP_LEN), + BPF_STMT(BPF_RET+BPF_A, 0), + /* natt_port */ + /* nat-t: check for marker */ + BPF_STMT(BPF_LD+BPF_W+BPF_ABS, ike_header), + BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0, 0, 5), + /* nat-t: IKE version must be 2.0 */ + BPF_STMT(BPF_LD+BPF_B+BPF_ABS, ike_header + MARKER_LEN + IKE_VERSION_OFFSET), + BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x20, 0, 3), + /* nat-t: packet length is length in IKEv2 header + ip header + udp header + non esp marker */ + BPF_STMT(BPF_LD+BPF_W+BPF_ABS, ike_header + MARKER_LEN + IKE_LENGTH_OFFSET), + BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, ip_len + UDP_LEN + MARKER_LEN), + BPF_STMT(BPF_RET+BPF_A, 0), + /* packet doesn't match, ignore */ + BPF_STMT(BPF_RET+BPF_K, 0), + }; + + /* Filter struct to use with setsockopt */ + struct sock_fprog ikev2_filter = { + sizeof(ikev2_filter_code) / sizeof(struct sock_filter), + ikev2_filter_code + }; + + /* set up a raw socket */ + skt = socket(family, SOCK_RAW, IPPROTO_UDP); + if (skt < 0) + { + DBG1(DBG_NET, "unable to create raw socket: %s", strerror(errno)); + return 0; + } + + if (setsockopt(skt, SOL_SOCKET, SO_ATTACH_FILTER, + &ikev2_filter, sizeof(ikev2_filter)) < 0) + { + DBG1(DBG_NET, "unable to attach IKEv2 filter to raw socket: %s", + strerror(errno)); + close(skt); + return 0; + } + + if (family == AF_INET6 && + /* we use IPV6_2292PKTINFO, as IPV6_PKTINFO is defined as + * 2 or 50 depending on kernel header version */ + setsockopt(skt, sol, IPV6_2292PKTINFO, &on, sizeof(on)) < 0) + { + DBG1(DBG_NET, "unable to set IPV6_PKTINFO on raw socket: %s", + strerror(errno)); + close(skt); + return 0; + } + + /* bypass incomining IKE traffic on this socket */ + memset(&policy, 0, sizeof(policy)); + policy.sadb_x_policy_len = sizeof(policy) / sizeof(u_int64_t); + policy.sadb_x_policy_exttype = SADB_X_EXT_POLICY; + policy.sadb_x_policy_type = IPSEC_POLICY_BYPASS; + policy.sadb_x_policy_dir = IPSEC_DIR_INBOUND; + + if (setsockopt(skt, sol, ipsec_policy, &policy, sizeof(policy)) < 0) + { + DBG1(DBG_NET, "unable to set IPSEC_POLICY on raw socket: %s", + strerror(errno)); + close(skt); + return 0; + } + + return skt; +} + +/** + * implementation of socket_t.destroy + */ +static void destroy(private_socket_t *this) +{ + if (this->recv4) + { + close(this->recv4); + } + if (this->recv6) + { + close(this->recv6); + } + if (this->send4) + { + close(this->send4); + } + if (this->send6) + { + close(this->send6); + } + if (this->send4_natt) + { + close(this->send4_natt); + } + if (this->send6_natt) + { + close(this->send6_natt); + } + free(this); +} + +/* + * See header for description + */ +socket_t *socket_create() +{ + int key; + private_socket_t *this = malloc_thing(private_socket_t); + + /* public functions */ + this->public.send = (status_t(*)(socket_t*, packet_t*))sender; + this->public.receive = (status_t(*)(socket_t*, packet_t**))receiver; + this->public.destroy = (void(*)(socket_t*)) destroy; + + this->recv4 = 0; + this->recv6 = 0; + this->send4 = 0; + this->send6 = 0; + this->send4_natt = 0; + this->send6_natt = 0; + + /* we open a AF_KEY socket to autoload the af_key module. Otherwise + * setsockopt(IPSEC_POLICY) won't work. */ + key = socket(AF_KEY, SOCK_RAW, PF_KEY_V2); + if (key == 0) + { + charon->kill(charon, "could not open AF_KEY socket"); + } + close(key); + + this->recv4 = open_recv_socket(this, AF_INET); + if (this->recv4 == 0) + { + DBG1(DBG_NET, "could not open IPv4 receive socket, IPv4 disabled"); + } + else + { + this->send4 = open_send_socket(this, AF_INET, IKEV2_UDP_PORT); + if (this->send4 == 0) + { + DBG1(DBG_NET, "could not open IPv4 send socket, IPv4 disabled"); + close(this->recv4); + } + else + { + this->send4_natt = open_send_socket(this, AF_INET, IKEV2_NATT_PORT); + if (this->send4_natt == 0) + { + DBG1(DBG_NET, "could not open IPv4 NAT-T send socket"); + } + } + } + + this->recv6 = open_recv_socket(this, AF_INET6); + if (this->recv6 == 0) + { + DBG1(DBG_NET, "could not open IPv6 receive socket, IPv6 disabled"); + } + else + { + this->send6 = open_send_socket(this, AF_INET6, IKEV2_UDP_PORT); + if (this->send6 == 0) + { + DBG1(DBG_NET, "could not open IPv6 send socket, IPv6 disabled"); + close(this->recv6); + } + else + { + this->send6_natt = open_send_socket(this, AF_INET6, IKEV2_NATT_PORT); + if (this->send6_natt == 0) + { + DBG1(DBG_NET, "could not open IPv6 NAT-T send socket"); + } + } + } + + if (!(this->send4 || this->send6) || !(this->recv4 || this->recv6)) + { + DBG1(DBG_NET, "could not create any sockets"); + destroy(this); + charon->kill(charon, "socket initialization failed"); + } + + return (socket_t*)this; +} diff --git a/src/charon/network/socket.c b/src/charon/network/socket.c index dd231ebed..a4c407579 100644 --- a/src/charon/network/socket.c +++ b/src/charon/network/socket.c @@ -7,7 +7,7 @@ /* * Copyright (C) 2006 Tobias Brunner, Daniel Roethlisberger - * Copyright (C) 2005-2006 Martin Willi + * Copyright (C) 2005-2007 Martin Willi * Copyright (C) 2005 Jan Hutter * Hochschule fuer Technik Rapperswil * @@ -43,18 +43,9 @@ #include -/* constants for packet handling */ -#define IP_LEN sizeof(struct iphdr) -#define IP6_LEN sizeof(struct ip6_hdr) -#define UDP_LEN sizeof(struct udphdr) +/* length of non-esp marker */ #define MARKER_LEN sizeof(u_int32_t) -/* offsets for packet handling */ -#define IP_PROTO_OFFSET 9 -#define IP6_PROTO_OFFSET 6 -#define IKE_VERSION_OFFSET 17 -#define IKE_LENGTH_OFFSET 24 - /* from linux/in.h */ #ifndef IP_IPSEC_POLICY #define IP_IPSEC_POLICY 16 @@ -84,51 +75,31 @@ typedef struct private_socket_t private_socket_t; /** * Private data of an socket_t object */ -struct private_socket_t{ +struct private_socket_t { /** * public functions */ socket_t public; - - /** - * regular port - */ - int port; - - /** - * port used for nat-t - */ - int natt_port; /** - * raw receiver socket for IPv4 + * IPv4 socket (500) */ - int recv4; + int ipv4; /** - * raw receiver socket for IPv6 - */ - int recv6; - - /** - * send socket on regular port for IPv4 + * IPv4 socket for NATT (4500) */ - int send4; - - /** - * send socket on regular port for IPv6 - */ - int send6; - + int ipv4_natt; + /** - * send socket on nat-t port for IPv4 + * IPv6 socket (500) */ - int send4_natt; - + int ipv6; + /** - * send socket on nat-t port for IPv6 + * IPv6 socket for NATT (4500) */ - int send6_natt; + int ipv6_natt; }; /** @@ -139,91 +110,72 @@ static status_t receiver(private_socket_t *this, packet_t **packet) char buffer[MAX_PACKET]; chunk_t data; packet_t *pkt; - struct udphdr *udp; host_t *source = NULL, *dest = NULL; int bytes_read = 0; int data_offset, oldstate; fd_set rfds; + int max_fd = 0, selected = 0; + u_int16_t port; FD_ZERO(&rfds); - if (this->recv4) + if (this->ipv4) { - FD_SET(this->recv4, &rfds); + FD_SET(this->ipv4, &rfds); } - if (this->recv6) + if (this->ipv4_natt) { - FD_SET(this->recv6, &rfds); + FD_SET(this->ipv4_natt, &rfds); } + if (this->ipv6) + { + FD_SET(this->ipv6, &rfds); + } + if (this->ipv6_natt) + { + FD_SET(this->ipv6_natt, &rfds); + } + max_fd = max(max(this->ipv4, this->ipv4_natt), max(this->ipv6, this->ipv6_natt)); - DBG2(DBG_NET, "waiting for data on raw sockets"); - + DBG2(DBG_NET, "waiting for data on sockets"); pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, &oldstate); - if (select(max(this->recv4, this->recv6) + 1, &rfds, NULL, NULL, NULL) <= 0) + if (select(max_fd + 1, &rfds, NULL, NULL, NULL) <= 0) { pthread_setcancelstate(oldstate, NULL); return FAILED; } pthread_setcancelstate(oldstate, NULL); - if (this->recv4 && FD_ISSET(this->recv4, &rfds)) + if (FD_ISSET(this->ipv4, &rfds)) { - /* IPv4 raw sockets return the IP header. We read src/dest - * information directly from the raw header */ - struct iphdr *ip; - struct sockaddr_in src, dst; - - bytes_read = recv(this->recv4, buffer, MAX_PACKET, 0); - if (bytes_read < 0) - { - DBG1(DBG_NET, "error reading from IPv4 socket: %s", strerror(errno)); - return FAILED; - } - DBG3(DBG_NET, "received IPv4 packet %b", buffer, bytes_read); - - /* read source/dest from raw IP/UDP header */ - if (bytes_read < IP_LEN + UDP_LEN + MARKER_LEN) - { - DBG1(DBG_NET, "received IPv4 packet too short (%d bytes)", - bytes_read); - return FAILED; - } - ip = (struct iphdr*) buffer; - udp = (struct udphdr*) (buffer + IP_LEN); - src.sin_family = AF_INET; - src.sin_addr.s_addr = ip->saddr; - src.sin_port = udp->source; - dst.sin_family = AF_INET; - dst.sin_addr.s_addr = ip->daddr; - dst.sin_port = udp->dest; - source = host_create_from_sockaddr((sockaddr_t*)&src); - dest = host_create_from_sockaddr((sockaddr_t*)&dst); - - pkt = packet_create(); - pkt->set_source(pkt, source); - pkt->set_destination(pkt, dest); - DBG2(DBG_NET, "received packet: from %#H to %#H", source, dest); - data_offset = IP_LEN + UDP_LEN; - /* remove non esp marker */ - if (dest->get_port(dest) == this->natt_port) - { - data_offset += MARKER_LEN; - } - /* fill in packet */ - data.len = bytes_read - data_offset; - data.ptr = malloc(data.len); - memcpy(data.ptr, buffer + data_offset, data.len); - pkt->set_data(pkt, data); + port = IKEV2_UDP_PORT; + selected = this->ipv4; } - else if (this->recv6 && FD_ISSET(this->recv6, &rfds)) + if (FD_ISSET(this->ipv4_natt, &rfds)) + { + port = IKEV2_NATT_PORT; + selected = this->ipv4_natt; + } + if (FD_ISSET(this->ipv6, &rfds)) + { + port = IKEV2_UDP_PORT; + selected = this->ipv6; + } + if (FD_ISSET(this->ipv6_natt, &rfds)) + { + port = IKEV2_NATT_PORT; + selected = this->ipv6_natt; + } + if (selected) { - /* IPv6 raw sockets return no IP header. We must query - * src/dest via socket options/ancillary data */ struct msghdr msg; struct cmsghdr *cmsgptr; - struct sockaddr_in6 src, dst; struct iovec iov; char ancillary[64]; + union { + struct sockaddr_in in4; + struct sockaddr_in6 in6; + } src; msg.msg_name = &src; msg.msg_namelen = sizeof(src); @@ -234,18 +186,17 @@ static status_t receiver(private_socket_t *this, packet_t **packet) msg.msg_control = ancillary; msg.msg_controllen = sizeof(ancillary); msg.msg_flags = 0; - - bytes_read = recvmsg(this->recv6, &msg, 0); + bytes_read = recvmsg(selected, &msg, 0); if (bytes_read < 0) { - DBG1(DBG_NET, "error reading from IPv6 socket: %s", strerror(errno)); + DBG1(DBG_NET, "error reading socket: %s", strerror(errno)); return FAILED; } - DBG3(DBG_NET, "received IPv6 packet %b", buffer, bytes_read); + DBG3(DBG_NET, "received packet %b", buffer, bytes_read); - if (bytes_read < IP_LEN + UDP_LEN + MARKER_LEN) + if (bytes_read < MARKER_LEN) { - DBG3(DBG_NET, "received IPv6 packet too short (%d bytes)", + DBG3(DBG_NET, "received packet too short (%d bytes)", bytes_read); return FAILED; } @@ -256,40 +207,55 @@ static status_t receiver(private_socket_t *this, packet_t **packet) { if (cmsgptr->cmsg_len == 0) { - DBG1(DBG_NET, "error reading IPv6 ancillary data"); + DBG1(DBG_NET, "error reading ancillary data"); return FAILED; - } + } + if (cmsgptr->cmsg_level == SOL_IPV6 && cmsgptr->cmsg_type == IPV6_2292PKTINFO) { struct in6_pktinfo *pktinfo; pktinfo = (struct in6_pktinfo*)CMSG_DATA(cmsgptr); + struct sockaddr_in6 dst; memset(&dst, 0, sizeof(dst)); memcpy(&dst.sin6_addr, &pktinfo->ipi6_addr, sizeof(dst.sin6_addr)); dst.sin6_family = AF_INET6; - udp = (struct udphdr*) (buffer); - dst.sin6_port = udp->dest; - src.sin6_port = udp->source; + dst.sin6_port = htons(port); dest = host_create_from_sockaddr((sockaddr_t*)&dst); } + if (cmsgptr->cmsg_level == SOL_IP && + cmsgptr->cmsg_type == IP_PKTINFO) + { + struct in_pktinfo *pktinfo; + pktinfo = (struct in_pktinfo*)CMSG_DATA(cmsgptr); + struct sockaddr_in dst; + + memset(&dst, 0, sizeof(dst)); + memcpy(&dst.sin_addr, &pktinfo->ipi_addr, sizeof(dst.sin_addr)); + dst.sin_family = AF_INET; + dst.sin_port = htons(port); + dest = host_create_from_sockaddr((sockaddr_t*)&dst); + } + if (dest) + { + break; + } } - /* ancillary data missing? */ if (dest == NULL) { - DBG1(DBG_NET, "error reading IPv6 packet header"); + DBG1(DBG_NET, "error reading IP header"); return FAILED; } - source = host_create_from_sockaddr((sockaddr_t*)&src); pkt = packet_create(); pkt->set_source(pkt, source); pkt->set_destination(pkt, dest); DBG2(DBG_NET, "received packet: from %#H to %#H", source, dest); - data_offset = UDP_LEN; + data_offset = 0; /* remove non esp marker */ - if (dest->get_port(dest) == this->natt_port) + if (dest->get_port(dest) == IKEV2_NATT_PORT) { data_offset += MARKER_LEN; } @@ -304,7 +270,6 @@ static status_t receiver(private_socket_t *this, packet_t **packet) /* oops, shouldn't happen */ return FAILED; } - /* return packet */ *packet = pkt; return SUCCESS; @@ -332,26 +297,26 @@ status_t sender(private_socket_t *this, packet_t *packet) /* send data */ sport = src->get_port(src); family = dst->get_family(dst); - if (sport == this->port) + if (sport == IKEV2_UDP_PORT) { if (family == AF_INET) { - skt = this->send4; + skt = this->ipv4; } else { - skt = this->send6; + skt = this->ipv6; } } - else if (sport == this->natt_port) + else if (sport == IKEV2_NATT_PORT) { if (family == AF_INET) { - skt = this->send4_natt; + skt = this->ipv4_natt; } else { - skt = this->send6_natt; + skt = this->ipv6_natt; } /* NAT keepalives without marker */ if (data.len != 1 || data.ptr[0] != 0xFF) @@ -437,12 +402,12 @@ status_t sender(private_socket_t *this, packet_t *packet) /** * open a socket to send packets */ -static int open_send_socket(private_socket_t *this, int family, u_int16_t port) +static int open_socket(private_socket_t *this, int family, u_int16_t port) { int on = TRUE; int type = UDP_ENCAP_ESPINUDP; struct sockaddr_storage addr; - u_int sol, ipsec_policy; + u_int sol, ipsec_policy, pktinfo; struct sadb_x_policy policy; int skt; @@ -458,6 +423,7 @@ static int open_send_socket(private_socket_t *this, int family, u_int16_t port) sin->sin_port = htons(port); sol = SOL_IP; ipsec_policy = IP_IPSEC_POLICY; + pktinfo = IP_PKTINFO; break; } case AF_INET6: @@ -468,6 +434,7 @@ static int open_send_socket(private_socket_t *this, int family, u_int16_t port) sin6->sin6_port = htons(port); sol = SOL_IPV6; ipsec_policy = IPV6_IPSEC_POLICY; + pktinfo = IPV6_2292PKTINFO; break; } default: @@ -477,39 +444,34 @@ static int open_send_socket(private_socket_t *this, int family, u_int16_t port) skt = socket(family, SOCK_DGRAM, IPPROTO_UDP); if (skt < 0) { - DBG1(DBG_NET, "could not open send socket: %s", strerror(errno)); + DBG1(DBG_NET, "could not open socket: %s", strerror(errno)); return 0; } - if (setsockopt(skt, SOL_SOCKET, SO_REUSEADDR, (void*)&on, sizeof(on)) < 0) { - DBG1(DBG_NET, "unable to set SO_REUSEADDR on send socket: %s", - strerror(errno)); + DBG1(DBG_NET, "unable to set SO_REUSEADDR on socket: %s", strerror(errno)); close(skt); return 0; } - /* bypass outgoung IKE traffic on send socket */ + /* bypass IKE traffic on socket */ memset(&policy, 0, sizeof(policy)); policy.sadb_x_policy_len = sizeof(policy) / sizeof(u_int64_t); policy.sadb_x_policy_exttype = SADB_X_EXT_POLICY; policy.sadb_x_policy_type = IPSEC_POLICY_BYPASS; - policy.sadb_x_policy_dir = IPSEC_DIR_OUTBOUND; + policy.sadb_x_policy_dir = IPSEC_DIR_OUTBOUND; if (setsockopt(skt, sol, ipsec_policy, &policy, sizeof(policy)) < 0) { - DBG1(DBG_NET, "unable to set IPSEC_POLICY on send socket: %s", + DBG1(DBG_NET, "unable to set IPSEC_POLICY on socket: %s", strerror(errno)); close(skt); return 0; } - - /* We don't receive packets on the send socket, but we need a INBOUND policy. - * Otherwise, UDP decapsulation does not work!!! */ policy.sadb_x_policy_dir = IPSEC_DIR_INBOUND; if (setsockopt(skt, sol, ipsec_policy, &policy, sizeof(policy)) < 0) { - DBG1(DBG_NET, "unable to set IPSEC_POLICY on send socket: %s", + DBG1(DBG_NET, "unable to set IPSEC_POLICY on socket: %s", strerror(errno)); close(skt); return 0; @@ -518,138 +480,25 @@ static int open_send_socket(private_socket_t *this, int family, u_int16_t port) /* bind the send socket */ if (bind(skt, (struct sockaddr *)&addr, sizeof(addr)) < 0) { - DBG1(DBG_NET, "unable to bind send socket: %s", - strerror(errno)); + DBG1(DBG_NET, "unable to bind socket: %s", strerror(errno)); close(skt); return 0; } - if (family == AF_INET) + /* get additional packet info on receive */ + if (setsockopt(skt, sol, pktinfo, &on, sizeof(on)) < 0) { - /* enable UDP decapsulation globally, only for one socket needed */ - if (setsockopt(skt, SOL_UDP, UDP_ENCAP, &type, sizeof(type)) < 0) - { - DBG1(DBG_NET, "unable to set UDP_ENCAP: %s; NAT-T may fail", - strerror(errno)); - } - } - - return skt; -} - -/** - * open a socket to receive packets - */ -static int open_recv_socket(private_socket_t *this, int family) -{ - int skt; - int on = TRUE; - u_int proto_offset, ip_len, sol, ipsec_policy, udp_header, ike_header; - struct sadb_x_policy policy; - - /* precalculate constants depending on address family */ - switch (family) - { - case AF_INET: - proto_offset = IP_PROTO_OFFSET; - ip_len = IP_LEN; - sol = SOL_IP; - ipsec_policy = IP_IPSEC_POLICY; - break; - case AF_INET6: - proto_offset = IP6_PROTO_OFFSET; - ip_len = 0; /* IPv6 raw sockets contain no IP header */ - sol = SOL_IPV6; - ipsec_policy = IPV6_IPSEC_POLICY; - break; - default: - return 0; - } - udp_header = ip_len; - ike_header = ip_len + UDP_LEN; - - /* This filter code filters out all non-IKEv2 traffic on - * a SOCK_RAW IP_PROTP_UDP socket. Handling of other - * IKE versions is done in pluto. - */ - struct sock_filter ikev2_filter_code[] = - { - /* Destination Port must be either port or natt_port */ - BPF_STMT(BPF_LD+BPF_H+BPF_ABS, udp_header + 2), - BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, this->port, 1, 0), - BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, this->natt_port, 5, 12), - /* port */ - /* IKE version must be 2.0 */ - BPF_STMT(BPF_LD+BPF_B+BPF_ABS, ike_header + IKE_VERSION_OFFSET), - BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x20, 0, 10), - /* packet length is length in IKEv2 header + ip header + udp header */ - BPF_STMT(BPF_LD+BPF_W+BPF_ABS, ike_header + IKE_LENGTH_OFFSET), - BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, ip_len + UDP_LEN), - BPF_STMT(BPF_RET+BPF_A, 0), - /* natt_port */ - /* nat-t: check for marker */ - BPF_STMT(BPF_LD+BPF_W+BPF_ABS, ike_header), - BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0, 0, 5), - /* nat-t: IKE version must be 2.0 */ - BPF_STMT(BPF_LD+BPF_B+BPF_ABS, ike_header + MARKER_LEN + IKE_VERSION_OFFSET), - BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x20, 0, 3), - /* nat-t: packet length is length in IKEv2 header + ip header + udp header + non esp marker */ - BPF_STMT(BPF_LD+BPF_W+BPF_ABS, ike_header + MARKER_LEN + IKE_LENGTH_OFFSET), - BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, ip_len + UDP_LEN + MARKER_LEN), - BPF_STMT(BPF_RET+BPF_A, 0), - /* packet doesn't match, ignore */ - BPF_STMT(BPF_RET+BPF_K, 0), - }; - - /* Filter struct to use with setsockopt */ - struct sock_fprog ikev2_filter = { - sizeof(ikev2_filter_code) / sizeof(struct sock_filter), - ikev2_filter_code - }; - - /* set up a raw socket */ - skt = socket(family, SOCK_RAW, IPPROTO_UDP); - if (skt < 0) - { - DBG1(DBG_NET, "unable to create raw socket: %s", strerror(errno)); - return 0; - } - - if (setsockopt(skt, SOL_SOCKET, SO_ATTACH_FILTER, - &ikev2_filter, sizeof(ikev2_filter)) < 0) - { - DBG1(DBG_NET, "unable to attach IKEv2 filter to raw socket: %s", - strerror(errno)); + DBG1(DBG_NET, "unable to set IP_PKTINFO on socket: %s", strerror(errno)); close(skt); return 0; } - if (family == AF_INET6 && - /* we use IPV6_2292PKTINFO, as IPV6_PKTINFO is defined as - * 2 or 50 depending on kernel header version */ - setsockopt(skt, sol, IPV6_2292PKTINFO, &on, sizeof(on)) < 0) + /* enable UDP decapsulation globally, only for one socket needed */ + if (family == AF_INET && port == IKEV2_NATT_PORT && + setsockopt(skt, SOL_UDP, UDP_ENCAP, &type, sizeof(type)) < 0) { - DBG1(DBG_NET, "unable to set IPV6_PKTINFO on raw socket: %s", - strerror(errno)); - close(skt); - return 0; - } - - /* bypass incomining IKE traffic on this socket */ - memset(&policy, 0, sizeof(policy)); - policy.sadb_x_policy_len = sizeof(policy) / sizeof(u_int64_t); - policy.sadb_x_policy_exttype = SADB_X_EXT_POLICY; - policy.sadb_x_policy_type = IPSEC_POLICY_BYPASS; - policy.sadb_x_policy_dir = IPSEC_DIR_INBOUND; - - if (setsockopt(skt, sol, ipsec_policy, &policy, sizeof(policy)) < 0) - { - DBG1(DBG_NET, "unable to set IPSEC_POLICY on raw socket: %s", - strerror(errno)); - close(skt); - return 0; + DBG1(DBG_NET, "unable to set UDP_ENCAP: %s", strerror(errno)); } - return skt; } @@ -658,29 +507,21 @@ static int open_recv_socket(private_socket_t *this, int family) */ static void destroy(private_socket_t *this) { - if (this->recv4) - { - close(this->recv4); - } - if (this->recv6) - { - close(this->recv6); - } - if (this->send4) + if (this->ipv4) { - close(this->send4); + close(this->ipv4); } - if (this->send6) + if (this->ipv4_natt) { - close(this->send6); + close(this->ipv4_natt); } - if (this->send4_natt) + if (this->ipv6) { - close(this->send4_natt); + close(this->ipv6); } - if (this->send6_natt) + if (this->ipv6_natt) { - close(this->send6_natt); + close(this->ipv6_natt); } free(this); } @@ -688,7 +529,7 @@ static void destroy(private_socket_t *this) /* * See header for description */ -socket_t *socket_create(u_int16_t port, u_int16_t natt_port) +socket_t *socket_create() { int key; private_socket_t *this = malloc_thing(private_socket_t); @@ -698,14 +539,10 @@ socket_t *socket_create(u_int16_t port, u_int16_t natt_port) this->public.receive = (status_t(*)(socket_t*, packet_t**))receiver; this->public.destroy = (void(*)(socket_t*)) destroy; - this->port = port; - this->natt_port = natt_port; - this->recv4 = 0; - this->recv6 = 0; - this->send4 = 0; - this->send6 = 0; - this->send4_natt = 0; - this->send6_natt = 0; + this->ipv4 = 0; + this->ipv6 = 0; + this->ipv4_natt = 0; + this->ipv6_natt = 0; /* we open a AF_KEY socket to autoload the af_key module. Otherwise * setsockopt(IPSEC_POLICY) won't work. */ @@ -715,59 +552,41 @@ socket_t *socket_create(u_int16_t port, u_int16_t natt_port) charon->kill(charon, "could not open AF_KEY socket"); } close(key); - - this->recv4 = open_recv_socket(this, AF_INET); - if (this->recv4 == 0) + + this->ipv4 = open_socket(this, AF_INET, IKEV2_UDP_PORT); + if (this->ipv4 == 0) { - DBG1(DBG_NET, "could not open IPv4 receive socket, IPv4 disabled"); + DBG1(DBG_NET, "could not open IPv4 socket, IPv4 disabled"); } else { - this->send4 = open_send_socket(this, AF_INET, this->port); - if (this->send4 == 0) + this->ipv4_natt = open_socket(this, AF_INET, IKEV2_NATT_PORT); + if (this->ipv4_natt == 0) { - DBG1(DBG_NET, "could not open IPv4 send socket, IPv4 disabled"); - close(this->recv4); - } - else - { - this->send4_natt = open_send_socket(this, AF_INET, this->natt_port); - if (this->send4_natt == 0) - { - DBG1(DBG_NET, "could not open IPv4 NAT-T send socket"); - } + DBG1(DBG_NET, "could not open IPv4 NAT-T socket"); } } - - this->recv6 = open_recv_socket(this, AF_INET6); - if (this->recv6 == 0) + + this->ipv6 = open_socket(this, AF_INET6, IKEV2_UDP_PORT); + if (this->ipv6 == 0) { - DBG1(DBG_NET, "could not open IPv6 receive socket, IPv6 disabled"); + DBG1(DBG_NET, "could not open IPv6 socket, IPv6 disabled"); } else { - this->send6 = open_send_socket(this, AF_INET6, this->port); - if (this->send6 == 0) + this->ipv6_natt = open_socket(this, AF_INET6, IKEV2_NATT_PORT); + if (this->ipv6_natt == 0) { - DBG1(DBG_NET, "could not open IPv6 send socket, IPv6 disabled"); - close(this->recv6); - } - else - { - this->send6_natt = open_send_socket(this, AF_INET6, this->natt_port); - if (this->send6_natt == 0) - { - DBG1(DBG_NET, "could not open IPv6 NAT-T send socket"); - } + DBG1(DBG_NET, "could not open IPv6 NAT-T socket"); } } - if (!(this->send4 || this->send6) || !(this->recv4 || this->recv6)) + if (!this->ipv4 && !this->ipv6) { DBG1(DBG_NET, "could not create any sockets"); destroy(this); charon->kill(charon, "socket initialization failed"); - } - + } return (socket_t*)this; } + diff --git a/src/charon/network/socket.h b/src/charon/network/socket.h index ef60fa7b6..4d8251325 100644 --- a/src/charon/network/socket.h +++ b/src/charon/network/socket.h @@ -100,13 +100,11 @@ struct socket_t { /** * @brief Create a socket_t, wich binds multiple sockets. * - * @param port port to bind socket to - * @param natt_port port to float to in NAT-T * @return socket_t object * * @ingroup network */ -socket_t *socket_create(u_int16_t port, u_int16_t natt_port); +socket_t *socket_create(); #endif /*SOCKET_H_*/ diff --git a/src/charon/processing/jobs/callback_job.c b/src/charon/processing/jobs/callback_job.c index 6f534e0f7..53297916e 100644 --- a/src/charon/processing/jobs/callback_job.c +++ b/src/charon/processing/jobs/callback_job.c @@ -121,12 +121,7 @@ static void cancel(private_callback_job_t *this) { pthread_t thread; - /* wait until thread has started */ pthread_mutex_lock(&this->mutex); - while (this->thread == 0) - { - pthread_cond_wait(&this->condvar, &this->mutex); - } thread = this->thread; /* terminate its children */ @@ -134,8 +129,11 @@ static void cancel(private_callback_job_t *this) pthread_mutex_unlock(&this->mutex); /* terminate thread */ - pthread_cancel(thread); - pthread_join(thread, NULL); + if (thread) + { + pthread_cancel(thread); + pthread_join(thread, NULL); + } } /** @@ -159,6 +157,7 @@ static void execute(private_callback_job_t *this) continue; case JOB_REQUEUE_FAIR: { + this->thread = 0; charon->processor->queue_job(charon->processor, &this->public.job_interface); break; @@ -166,6 +165,7 @@ static void execute(private_callback_job_t *this) case JOB_REQUEUE_NONE: default: { + this->thread = 0; cleanup = TRUE; break; } diff --git a/src/charon/processing/jobs/initiate_mediation_job.c b/src/charon/processing/jobs/initiate_mediation_job.c index d78f8a202..b8d516e22 100644 --- a/src/charon/processing/jobs/initiate_mediation_job.c +++ b/src/charon/processing/jobs/initiate_mediation_job.c @@ -73,7 +73,7 @@ static bool initiate_callback(private_initiate_mediation_job_t *this, signal_t s { if (signal == CHILD_UP_SUCCESS) { - // mediation connection is up + /* mediation connection is up */ this->mediation_sa_id = ike_sa->get_id(ike_sa); this->mediation_sa_id = this->mediation_sa_id->clone(this->mediation_sa_id); return FALSE; @@ -85,7 +85,7 @@ static bool initiate_callback(private_initiate_mediation_job_t *this, signal_t s * Implementation of job_t.execute. */ static void initiate(private_initiate_mediation_job_t *this) -{//FIXME: check the logging +{ /* FIXME: check the logging */ ike_sa_t *mediated_sa, *mediation_sa; peer_cfg_t *mediated_cfg, *mediation_cfg; @@ -94,7 +94,8 @@ static void initiate(private_initiate_mediation_job_t *this) if (mediated_sa) { mediated_cfg = mediated_sa->get_peer_cfg(mediated_sa); - mediated_cfg->get_ref(mediated_cfg); // get_peer_cfg returns an internal object + /* get_peer_cfg returns an internal object */ + mediated_cfg->get_ref(mediated_cfg); charon->ike_sa_manager->checkin(charon->ike_sa_manager, mediated_sa); @@ -107,18 +108,19 @@ static void initiate(private_initiate_mediation_job_t *this) { mediated_cfg->destroy(mediated_cfg); mediation_cfg->destroy(mediation_cfg); - charon->bus->set_sa(charon->bus, mediated_sa); // this pointer should still be valid + /* this pointer should still be valid */ + charon->bus->set_sa(charon->bus, mediated_sa); DBG1(DBG_IKE, "mediation with the same peer is already in progress, queued"); destroy(this); return; } - - mediation_cfg->get_ref(mediation_cfg); // we need an additional reference because initiate consumes one + /* we need an additional reference because initiate consumes one */ + mediation_cfg->get_ref(mediation_cfg); - // this function call blocks until the connection is up or failed - // we do not check the status, but NEED_MORE would be returned on success - // because the registered callback returns FALSE then - // this->mediation_sa_id is set in the callback + /* this function call blocks until the connection is up or failed + * we do not check the status, but NEED_MORE would be returned on success + * because the registered callback returns FALSE then + * this->mediation_sa_id is set in the callback */ charon->interfaces->initiate(charon->interfaces, mediation_cfg, NULL, (interface_manager_cb_t)initiate_callback, this); if (!this->mediation_sa_id) @@ -127,7 +129,7 @@ static void initiate(private_initiate_mediation_job_t *this) mediation_cfg->get_name(mediation_cfg)); mediation_cfg->destroy(mediation_cfg); mediated_cfg->destroy(mediated_cfg); - charon->bus->set_sa(charon->bus, mediated_sa); // this pointer should still be valid + charon->bus->set_sa(charon->bus, mediated_sa); SIG(IKE_UP_FAILED, "mediation failed"); destroy(this); return; @@ -146,7 +148,7 @@ static void initiate(private_initiate_mediation_job_t *this) mediated_cfg->destroy(mediated_cfg); charon->ike_sa_manager->checkin_and_destroy(charon->ike_sa_manager, mediation_sa); - charon->bus->set_sa(charon->bus, mediated_sa); // this pointer should still be valid + charon->bus->set_sa(charon->bus, mediated_sa); SIG(IKE_UP_FAILED, "mediation failed"); destroy(this); return; @@ -164,7 +166,7 @@ static void initiate(private_initiate_mediation_job_t *this) * Implementation of job_t.execute. */ static void reinitiate(private_initiate_mediation_job_t *this) -{//FIXME: check the logging +{ /* FIXME: check the logging */ ike_sa_t *mediated_sa, *mediation_sa; peer_cfg_t *mediated_cfg; @@ -173,7 +175,7 @@ static void reinitiate(private_initiate_mediation_job_t *this) if (mediated_sa) { mediated_cfg = mediated_sa->get_peer_cfg(mediated_sa); - mediated_cfg->get_ref(mediated_cfg); // get_peer_cfg returns an internal object + mediated_cfg->get_ref(mediated_cfg); charon->ike_sa_manager->checkin(charon->ike_sa_manager, mediated_sa); mediation_sa = charon->ike_sa_manager->checkout(charon->ike_sa_manager, @@ -187,7 +189,7 @@ static void reinitiate(private_initiate_mediation_job_t *this) mediated_cfg->destroy(mediated_cfg); charon->ike_sa_manager->checkin_and_destroy(charon->ike_sa_manager, mediation_sa); - charon->bus->set_sa(charon->bus, mediated_sa); // this pointer should still be valid + charon->bus->set_sa(charon->bus, mediated_sa); SIG(IKE_UP_FAILED, "mediation failed"); destroy(this); return; diff --git a/src/charon/processing/jobs/mediation_job.c b/src/charon/processing/jobs/mediation_job.c index 6f5f74372..3b9d363d7 100644 --- a/src/charon/processing/jobs/mediation_job.c +++ b/src/charon/processing/jobs/mediation_job.c @@ -104,7 +104,7 @@ static void execute(private_mediation_job_t *this) { if (this->callback) { - // send callback to a peer + /* send callback to a peer */ if (target_sa->callback(target_sa, this->source) != SUCCESS) { DBG1(DBG_JOB, "callback for '%D' to '%D' failed", @@ -116,14 +116,14 @@ static void execute(private_mediation_job_t *this) } else { - // normal mediation between two peers + /* normal mediation between two peers */ if (target_sa->relay(target_sa, this->source, this->session_id, this->session_key, this->endpoints, this->response) != SUCCESS) { DBG1(DBG_JOB, "mediation between '%D' and '%D' failed", this->source, this->target); charon->ike_sa_manager->checkin(charon->ike_sa_manager, target_sa); - // FIXME: notify the initiator + /* FIXME: notify the initiator */ destroy(this); return; } diff --git a/src/charon/processing/jobs/process_message_job.c b/src/charon/processing/jobs/process_message_job.c index ec2e7735d..91e7a80bf 100644 --- a/src/charon/processing/jobs/process_message_job.c +++ b/src/charon/processing/jobs/process_message_job.c @@ -60,12 +60,13 @@ static void execute(private_process_message_job_t *this) ike_sa_t *ike_sa; #ifdef P2P - // if this is an unencrypted INFORMATIONAL exchange it is likely a - // connectivity check + /* if this is an unencrypted INFORMATIONAL exchange it is likely a + * connectivity check. */ if (this->message->get_exchange_type(this->message) == INFORMATIONAL && this->message->get_first_payload_type(this->message) != ENCRYPTED) { - // theoretically this could also be an error message see RFC 4306, section 1.5. + /* theoretically this could also be an error message + * see RFC 4306, section 1.5. */ DBG1(DBG_NET, "received unencrypted informational: from %#H to %#H", this->message->get_source(this->message), this->message->get_destination(this->message)); diff --git a/src/charon/processing/scheduler.c b/src/charon/processing/scheduler.c index 2706585b0..ededb479a 100644 --- a/src/charon/processing/scheduler.c +++ b/src/charon/processing/scheduler.c @@ -87,6 +87,8 @@ struct private_scheduler_t { * Condvar to wait for next job. */ pthread_cond_t condvar; + + bool cancelled; }; /** @@ -148,9 +150,7 @@ static job_requeue_t schedule(private_scheduler_t * this) pthread_cond_wait(&this->condvar, &this->mutex); } pthread_setcancelstate(oldstate, NULL); - pthread_cleanup_pop(0); - - pthread_mutex_unlock(&this->mutex); + pthread_cleanup_pop(TRUE); return JOB_REQUEUE_DIRECT; } @@ -234,6 +234,7 @@ static void schedule_job(private_scheduler_t *this, job_t *job, u_int32_t time) */ static void destroy(private_scheduler_t *this) { + this->cancelled = TRUE; this->job->cancel(this->job); this->list->destroy_function(this->list, (void*)event_destroy); free(this); @@ -251,6 +252,7 @@ scheduler_t * scheduler_create() this->public.destroy = (void(*)(scheduler_t*)) destroy; this->list = linked_list_create(); + this->cancelled = FALSE; pthread_mutex_init(&this->mutex, NULL); pthread_cond_init(&this->condvar, NULL); diff --git a/src/charon/sa/authenticators/eap/eap_aka.c b/src/charon/sa/authenticators/eap/eap_aka.c new file mode 100644 index 000000000..8fb1f85cd --- /dev/null +++ b/src/charon/sa/authenticators/eap/eap_aka.c @@ -0,0 +1,1440 @@ +/** + * @file eap_aka.c + * + * @brief Implementation of eap_aka_t. + * + */ + +/* + * Copyright (C) 2006 Martin Willi + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + + +/* The EAP-AKA method uses it's own simple parser for processing EAP-AKA + * payloads, as the IKEv2 parser is not suitable for that job. There are + * two simple methods for parsing payloads, read_header() and read_attribute(). + * Every EAP-AKA payload consists of a header and a list of attributes. Those + * functions mentioned read the data and return the type of the found + * attribute/EAP-AKA-type. For generating a EAP-AKA message, we have a + * build_aka_payload(), which builds the whole message from a variable + * argument list containing its attributes. + * The processing of messages is split up in various functions: + * - peer_process() - General processing multiplexer for the peer + * - peer_process_challenge() - Specific AKA-Challenge processor + * - peer_process_notification() - Processing of AKA-Notification + * - server_process() - General processing multiplexer for the server + * - peer_process_challenge() - Processing of a received Challenge response + * - peer_process_synchronize() - Process a sequence number synchronization + * - server_initiate() - Initiation method for the server, calls + * - server_initiate_challenge() - Initiation of AKA-Challenge + */ + +#include +#include +#include +#include + +#include "eap_aka.h" + +#include +#include +#include +#include +#include + +/* Use test vectors specified in S.S0055 +#define TEST_VECTORS */ + +#define RAND_LENGTH 16 +#define RES_LENGTH 16 +#define SQN_LENGTH 6 +#define K_LENGTH 16 +#define MAC_LENGTH 8 +#define CK_LENGTH 16 +#define IK_LENGTH 16 +#define AK_LENGTH 6 +#define AMF_LENGTH 2 +#define FMK_LENGTH 4 +#define AUTN_LENGTH (SQN_LENGTH + AMF_LENGTH + MAC_LENGTH) +#define AUTS_LENGTH (SQN_LENGTH + MAC_LENGTH) +#define PAYLOAD_LENGTH 64 +#define MK_LENGTH 20 +#define MSK_LENGTH 64 +#define EMSK_LENGTH 64 +#define KAUTH_LENGTH 16 +#define KENCR_LENGTH 16 +#define AT_MAC_LENGTH 16 + +#define F1 0x42 +#define F1STAR 0x43 +#define F2 0x44 +#define F3 0x45 +#define F4 0x46 +#define F5 0x47 +#define F5STAR 0x48 + +ENUM_BEGIN(aka_subtype_names, AKA_CHALLENGE, AKA_IDENTITY, + "AKA_CHALLENGE", + "AKA_AUTHENTICATION_REJECT", + "AKA_3", + "AKA_SYNCHRONIZATION_FAILURE", + "AKA_IDENTITY"); +ENUM_NEXT(aka_subtype_names, AKA_NOTIFICATION, AKA_CLIENT_ERROR, AKA_IDENTITY, + "AKA_NOTIFICATION", + "AKA_REAUTHENTICATION", + "AKA_CLIENT_ERROR"); +ENUM_END(aka_subtype_names, AKA_CLIENT_ERROR); + + +ENUM_BEGIN(aka_attribute_names, AT_END, AT_CLIENT_ERROR_CODE, + "AT_END", + "AT_0", + "AT_RAND", + "AT_AUTN", + "AT_RES", + "AT_AUTS", + "AT_5", + "AT_PADDING", + "AT_NONCE_MT", + "AT_8", + "AT_9", + "AT_PERMANENT_ID_REQ", + "AT_MAC", + "AT_NOTIFICATION", + "AT_ANY_ID_REQ", + "AT_IDENTITY", + "AT_VERSION_LIST", + "AT_SELECTED_VERSION", + "AT_FULLAUTH_ID_REQ", + "AT_18", + "AT_COUNTER", + "AT_COUNTER_TOO_SMALL", + "AT_NONCE_S", + "AT_CLIENT_ERROR_CODE"); +ENUM_NEXT(aka_attribute_names, AT_IV, AT_RESULT_IND, AT_CLIENT_ERROR_CODE, + "AT_IV", + "AT_ENCR_DATA", + "AT_131", + "AT_NEXT_PSEUDONYM", + "AT_NEXT_REAUTH_ID", + "AT_CHECKCODE", + "AT_RESULT_IND"); +ENUM_END(aka_attribute_names, AT_RESULT_IND); + + +typedef struct private_eap_aka_t private_eap_aka_t; + +/** + * Private data of an eap_aka_t object. + */ +struct private_eap_aka_t { + + /** + * Public authenticator_t interface. + */ + eap_aka_t public; + + /** + * ID of the server + */ + identification_t *server; + + /** + * ID of the peer + */ + identification_t *peer; + + /** + * Key for EAP MAC + */ + chunk_t k_auth; + + /** + * Key for EAP encryption + */ + chunk_t k_encr; + + /** + * MSK + */ + chunk_t msk; + + /** + * Extendend MSK + */ + chunk_t emsk; + + /** + * Expected result from client XRES + */ + chunk_t xres; + + /** + * Shared secret K from ipsec.conf (padded) + */ + chunk_t k; + + /** + * random value RAND generated by server + */ + chunk_t rand; +}; + +/** Family key, as proposed in S.S0055 */ +static u_int8_t fmk_buf[] = {0x41, 0x48, 0x41, 0x47}; +static chunk_t fmk = chunk_from_buf(fmk_buf); + +/** Authentication management field */ +static u_int8_t amf_buf[] = {0x00, 0x01}; +static chunk_t amf = chunk_from_buf(amf_buf); + +/** AT_CLIENT_ERROR_CODE AKA attribute */ +static u_int8_t client_error_code_buf[] = {0, 0}; +static chunk_t client_error_code = chunk_from_buf(client_error_code_buf); + +/** previously used sqn by peer, next one must be greater */ +static u_int8_t peer_sqn_buf[6]; +static chunk_t peer_sqn = chunk_from_buf(peer_sqn_buf); + +/** set SQN to the current time */ +static void update_sqn(u_int8_t *sqn, time_t offset) +{ + timeval_t time; + gettimeofday(&time, NULL); + /* set sqb_sqn to an integer containing seconds followed by most + * significant useconds */ + time.tv_sec = htonl(time.tv_sec + offset); + /* usec's are never larger than 0x000f423f, so we shift the 12 first bits */ + time.tv_usec <<= 12; + time.tv_usec = htonl(time.tv_usec); + memcpy(sqn, &time.tv_sec, 4); + memcpy(sqn + 4, &time.tv_usec, 2); +} + +/** initialize peers SQN to the current system time at startup */ +static void __attribute__ ((constructor))init_sqn(void) +{ + update_sqn(peer_sqn_buf, 0); +} + +/** + * Binary represnation of the polynom T^160 + T^5 + T^3 + T^2 + 1 + */ +static u_int8_t g[] = { + 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x2d +}; + +/** + * Predefined random bits from the RAND Corporation book + */ +static u_int8_t a[] = { + 0x9d, 0xe9, 0xc9, 0xc8, 0xef, 0xd5, 0x78, 0x11, + 0x48, 0x23, 0x14, 0x01, 0x90, 0x1f, 0x2d, 0x49, + 0x3f, 0x4c, 0x63, 0x65 +}; + +/** + * Predefined random bits from the RAND Corporation book + */ +static u_int8_t b[] = { + 0x75, 0xef, 0xd1, 0x5c, 0x4b, 0x8f, 0x8f, 0x51, + 0x4e, 0xf3, 0xbc, 0xc3, 0x79, 0x4a, 0x76, 0x5e, + 0x7e, 0xec, 0x45, 0xe0 +}; + +/** + * Multiplicate two mpz_t with bits interpreted as polynoms. + */ +static void mpz_mul_poly(mpz_t r, mpz_t a, mpz_t b) +{ + mpz_t bm, rm; + int current = 0, shifted = 0, shift; + + mpz_init_set(bm, b); + mpz_init_set_ui(rm, 0); + /* scan through a, for each found bit: */ + while ((current = mpz_scan1(a, current)) != ULONG_MAX) + { + /* XOR shifted b into r */ + shift = current - shifted; + mpz_mul_2exp(bm, bm, shift); + shifted += shift; + mpz_xor(rm, rm, bm); + current++; + } + + mpz_swap(r, rm); + mpz_clear(rm); + mpz_clear(bm); +} + +/** + * Calculate the sum of a + b interpreted as polynoms. + */ +static void mpz_add_poly(mpz_t res, mpz_t a, mpz_t b) +{ + /* addition of polynominals is just the XOR */ + mpz_xor(res, a, b); +} + +/** + * Calculate the remainder of a/b interpreted as polynoms. + */ +static void mpz_mod_poly(mpz_t r, mpz_t a, mpz_t b) +{ + /* Example: + * a = 10001010 + * b = 00000101 + */ + int a_bit, b_bit, diff; + mpz_t bm, am; + + mpz_init_set(am, a); + mpz_init(bm); + + a_bit = mpz_sizeinbase(a, 2); + b_bit = mpz_sizeinbase(b, 2); + + /* don't do anything if b > a */ + if (a_bit >= b_bit) + { + /* shift b left to align up most signaficant "1" to a: + * a = 10001010 + * b = 10100000 + */ + mpz_mul_2exp(bm, b, a_bit - b_bit); + do + { + /* XOR b into a, this kills the most significant "1": + * a = 00101010 + */ + mpz_xor(am, am, bm); + /* find the next most significant "1" in a, and align up b: + * a = 00101010 + * b = 00101000 + */ + diff = a_bit - mpz_sizeinbase(am, 2); + mpz_div_2exp(bm, bm, diff); + a_bit -= diff; + } + while (b_bit <= mpz_sizeinbase(bm, 2)); + /* While b is not shifted to its original value */ + } + /* after another iteration: + * a = 00000010 + * which is the polynomial modulo + */ + + mpz_swap(r, am); + mpz_clear(am); + mpz_clear(bm); +} + +/** + * Step 4 of the various fx() functions: + * Polynomial whiten calculations + */ +static void step4(u_int8_t x[]) +{ + mpz_t xm, am, bm, gm; + + mpz_init(xm); + mpz_init(am); + mpz_init(bm); + mpz_init(gm); + + mpz_import(xm, HASH_SIZE_SHA1, 1, 1, 1, 0, x); + mpz_import(am, sizeof(a), 1, 1, 1, 0, a); + mpz_import(bm, sizeof(b), 1, 1, 1, 0, b); + mpz_import(gm, sizeof(g), 1, 1, 1, 0, g); + + mpz_mul_poly(xm, am, xm); + mpz_add_poly(xm, bm, xm); + mpz_mod_poly(xm, xm, gm); + + mpz_export(x, NULL, 1, HASH_SIZE_SHA1, 1, 0, xm); + + mpz_clear(xm); + mpz_clear(am); + mpz_clear(bm); + mpz_clear(gm); +} + +/** + * Step 3 of the various fx() functions: + * XOR the key into the SHA1 IV + */ +static void step3(chunk_t k, chunk_t payload, u_int8_t h[]) +{ + u_int8_t iv[] = { + 0x67,0x45,0x23,0x01,0xEF,0xCD,0xAB,0x89,0x98,0xBA, + 0xDC,0xFE,0x10,0x32,0x54,0x76,0xC3,0xD2,0xE1,0xF0, + }; + + /* XOR key into IV */ + memxor(iv, k.ptr, k.len); + + /* hash it with the G() function defined in FIPS 186-2 from fips_prf.h */ + g_sha1(iv, payload, h); +} + +/** + * Calculation function for f2(), f3(), f4() + */ +static void fx(u_int8_t f, chunk_t k, chunk_t rand, u_int8_t out[]) +{ + chunk_t payload = chunk_alloca(PAYLOAD_LENGTH); + u_int8_t h[HASH_SIZE_SHA1]; + u_int8_t i; + + for (i = 0; i < 2; i++) + { + memset(payload.ptr, 0x5c, payload.len); + payload.ptr[11] ^= f; + memxor(payload.ptr + 12, fmk.ptr, fmk.len); + memxor(payload.ptr + 24, rand.ptr, rand.len); + + payload.ptr[3] ^= i; + payload.ptr[19] ^= i; + payload.ptr[35] ^= i; + payload.ptr[51] ^= i; + + step3(k, payload, h); + step4(h); + memcpy(out + i * 8, h, 8); + } +} + +/** + * Calculation function of f1() and f1star() + */ +static void f1x(u_int8_t f, chunk_t k, chunk_t rand, chunk_t sqn, + chunk_t amf, u_int8_t mac[]) +{ + /* generate MAC = f1(FMK, SQN, RAND, AMF) + * K is loaded into hashers IV; FMK, RAND, SQN, AMF are XORed in a 512-bit + * payload which gets hashed + */ + chunk_t payload = chunk_alloca(PAYLOAD_LENGTH); + u_int8_t h[HASH_SIZE_SHA1]; + + memset(payload.ptr, 0x5c, PAYLOAD_LENGTH); + payload.ptr[11] ^= f; + memxor(payload.ptr + 12, fmk.ptr, fmk.len); + memxor(payload.ptr + 16, rand.ptr, rand.len); + memxor(payload.ptr + 34, sqn.ptr, sqn.len); + memxor(payload.ptr + 42, amf.ptr, amf.len); + + step3(k, payload, h); + step4(h); + memcpy(mac, h, MAC_LENGTH); +} + +/** + * Calculation function of f5() and f5star() + */ +static void f5x(u_int8_t f, chunk_t k, chunk_t rand, u_int8_t ak[]) +{ + chunk_t payload = chunk_alloca(PAYLOAD_LENGTH); + u_int8_t h[HASH_SIZE_SHA1]; + + memset(payload.ptr, 0x5c, payload.len); + payload.ptr[11] ^= f; + memxor(payload.ptr + 12, fmk.ptr, fmk.len); + memxor(payload.ptr + 16, rand.ptr, rand.len); + + step3(k, payload, h); + step4(h); + memcpy(ak, h, AK_LENGTH); +} + +/** + * Calculate the MAC from a RAND, SQN, AMF value using K + */ +static void f1(chunk_t k, chunk_t rand, chunk_t sqn, chunk_t amf, u_int8_t mac[]) +{ + f1x(F1, k, rand, sqn, amf, mac); + DBG3(DBG_IKE, "MAC %b", mac, MAC_LENGTH); +} + +/** + * Calculate the MACS from a RAND, SQN, AMF value using K + */ +static void f1star(chunk_t k, chunk_t rand, chunk_t sqn, chunk_t amf, u_int8_t macs[]) +{ + f1x(F1STAR, k, rand, sqn, amf, macs); + DBG3(DBG_IKE, "MACS %b", macs, MAC_LENGTH); +} + +/** + * Calculate RES from RAND using K + */ +static void f2(chunk_t k, chunk_t rand, u_int8_t res[]) +{ + fx(F2, k, rand, res); + DBG3(DBG_IKE, "RES %b", res, RES_LENGTH); +} + +/** + * Calculate CK from RAND using K + */ +static void f3(chunk_t k, chunk_t rand, u_int8_t ck[]) +{ + fx(F3, k, rand, ck); + DBG3(DBG_IKE, "CK %b", ck, CK_LENGTH); +} + +/** + * Calculate IK from RAND using K + */ +static void f4(chunk_t k, chunk_t rand, u_int8_t ik[]) +{ + fx(F4, k, rand, ik); + DBG3(DBG_IKE, "IK %b", ik, IK_LENGTH); +} + +/** + * Calculate AK from a RAND using K + */ +static void f5(chunk_t k, chunk_t rand, u_int8_t ak[]) +{ + f5x(F5, k, rand, ak); + DBG3(DBG_IKE, "AK %b", ak, AK_LENGTH); +} + +/** + * Calculate AKS from a RAND using K + */ +static void f5star(chunk_t k, chunk_t rand, u_int8_t aks[]) +{ + f5x(F5STAR, k, rand, aks); + DBG3(DBG_IKE, "AKS %b", aks, AK_LENGTH); +} + +/** + * derive the keys needed for EAP_AKA + */ +static void derive_keys(private_eap_aka_t *this, identification_t *id) +{ + hasher_t *hasher; + prf_t *prf; + chunk_t ck, ik, mk, identity, tmp; + + ck = chunk_alloca(CK_LENGTH); + ik = chunk_alloca(IK_LENGTH); + mk = chunk_alloca(MK_LENGTH); + identity = id->get_encoding(id); + + /* MK = SHA1( Identity | IK | CK ) */ + f3(this->k, this->rand, ck.ptr); + f4(this->k, this->rand, ik.ptr); + DBG3(DBG_IKE, "Identity %B", &identity); + tmp = chunk_cata("ccc", identity, ik, ck); + DBG3(DBG_IKE, "Identity|IK|CK %B", &tmp); + hasher = hasher_create(HASH_SHA1); + hasher->get_hash(hasher, tmp, mk.ptr); + hasher->destroy(hasher); + + /* K_encr | K_auth | MSK | EMSK = prf(0) | prf(0) + * FIPS PRF has 320 bit block size, we need 160 byte for keys + * => run prf four times */ + prf = prf_create(PRF_FIPS_SHA1_160); + prf->set_key(prf, mk); + tmp = chunk_alloca(prf->get_block_size(prf) * 4); + prf->get_bytes(prf, chunk_empty, tmp.ptr); + prf->get_bytes(prf, chunk_empty, tmp.ptr + tmp.len / 4 * 1); + prf->get_bytes(prf, chunk_empty, tmp.ptr + tmp.len / 4 * 2); + prf->get_bytes(prf, chunk_empty, tmp.ptr + tmp.len / 4 * 3); + prf->destroy(prf); + chunk_free(&this->k_encr); + chunk_free(&this->k_auth); + chunk_free(&this->msk); + chunk_free(&this->emsk); + chunk_split(tmp, "aaaa", 16, &this->k_encr, 16, &this->k_auth, + 64, &this->msk, 64, &this->emsk); + DBG3(DBG_IKE, "MK %B", &mk); + DBG3(DBG_IKE, "PRF res %B", &tmp); + DBG3(DBG_IKE, "K_encr %B", &this->k_encr); + DBG3(DBG_IKE, "K_auth %B", &this->k_auth); + DBG3(DBG_IKE, "MSK %B", &this->msk); + DBG3(DBG_IKE, "EMSK %B", &this->emsk); +} + +/* + * Get a shared key from ipsec.secrets. + * We use the standard keys as used in preshared key authentication. As + * these keys have an undefined length, we: + * - strip them if they are longer + * - fill them up with '\0' if they are shorter + */ +static status_t load_key(identification_t *me, identification_t *other, chunk_t *k) +{ + chunk_t shared_key; + + if (charon->credentials->get_eap_key(charon->credentials, me, + other, &shared_key) != SUCCESS) + { + return NOT_FOUND; + } + chunk_free(k); + *k = chunk_alloc(K_LENGTH); + memset(k->ptr, '\0', k->len); + memcpy(k->ptr, shared_key.ptr, min(shared_key.len, k->len)); + chunk_free(&shared_key); + return SUCCESS; +} + +/** + * skip EAP_AKA header in message and returns its AKA subtype + */ +static aka_subtype_t read_header(chunk_t *message) +{ + aka_subtype_t type; + + if (message->len < 8) + { + *message = chunk_empty; + return 0; + } + type = *(message->ptr + 5); + *message = chunk_skip(*message, 8); + return type; +} + +/** + * read the next attribute from the chunk data + */ +static aka_attribute_t read_attribute(chunk_t *data, chunk_t *attr_data) +{ + aka_attribute_t attribute; + size_t length; + + DBG3(DBG_IKE, "reading attribute from %B", data); + + if (data->len < 2) + { + return AT_END; + } + /* read attribute and length */ + attribute = *data->ptr++; + length = *data->ptr++ * 4 - 2; + data->len -= 2; + DBG3(DBG_IKE, "found attribute %N with length %d", + aka_attribute_names, attribute, length); + if (length > data->len) + { + return AT_END; + } + /* apply attribute value to attr_data */ + attr_data->len = length; + attr_data->ptr = data->ptr; + /* update data to point to next attribute */ + *data = chunk_skip(*data, length); + return attribute; +} + +/** + * Build an AKA payload from different attributes. + * The variable argument takes an aka_attribute_t + * followed by its data in a chunk. + */ +static eap_payload_t *build_aka_payload(private_eap_aka_t *this, eap_code_t code, + u_int8_t identifier, aka_subtype_t type, ...) +{ + chunk_t message = chunk_alloca(512); /* is enought for all current messages */ + chunk_t pos = message; + eap_payload_t *payload; + va_list args; + aka_attribute_t attr; + u_int8_t *mac_pos = NULL; + + /* write EAP header, skip length bytes */ + *pos.ptr++ = code; + *pos.ptr++ = identifier; + pos.ptr += 2; + pos.len -= 4; + /* write AKA header with type and subtype, null reserved bytes */ + *pos.ptr++ = EAP_AKA; + *pos.ptr++ = type; + *pos.ptr++ = 0; + *pos.ptr++ = 0; + pos.len -= 4; + + va_start(args, type); + while ((attr = va_arg(args, aka_attribute_t)) != AT_END) + { + chunk_t data = va_arg(args, chunk_t); + + DBG3(DBG_IKE, "building %N %B", aka_attribute_names, attr, &data); + + /* write attribute header */ + *pos.ptr++ = attr; + pos.len--; + + switch (attr) + { + case AT_RES: + { + /* attribute length in 4byte words */ + *pos.ptr = data.len/4 + 1; + pos = chunk_skip(pos, 1); + /* RES length in bits */ + *(u_int16_t*)pos.ptr = htons(data.len * 8); + pos = chunk_skip(pos, sizeof(u_int16_t)); + memcpy(pos.ptr, data.ptr, data.len); + pos = chunk_skip(pos, data.len); + break; + } + case AT_AUTN: + case AT_RAND: + { + *pos.ptr++ = data.len/4 + 1; pos.len--; + *pos.ptr++ = 0; pos.len--; + *pos.ptr++ = 0; pos.len--; + memcpy(pos.ptr, data.ptr, data.len); + pos = chunk_skip(pos, data.len); + break; + } + case AT_MAC: + { + *pos.ptr++ = 5; pos.len--; + *pos.ptr++ = 0; pos.len--; + *pos.ptr++ = 0; pos.len--; + mac_pos = pos.ptr; + /* MAC is calculated over message including zeroed AT_MAC attribute */ + memset(mac_pos, 0, AT_MAC_LENGTH); + pos.ptr += AT_MAC_LENGTH; + pos.len -= AT_MAC_LENGTH; + break; + } + default: + { + /* length is data length in 4-bytes + 1 for header */ + *pos.ptr = data.len/4 + 1; + pos = chunk_skip(pos, 1); + memcpy(pos.ptr, data.ptr, data.len); + pos = chunk_skip(pos, data.len); + } + } + } + va_end(args); + + /* calculate message length, write into header */ + message.len = pos.ptr - message.ptr; + *(u_int16_t*)(message.ptr + 2) = htons(message.len); + + /* create MAC if AT_MAC attribte was included */ + if (mac_pos) + { + signer_t *signer = signer_create(AUTH_HMAC_SHA1_128); + signer->set_key(signer, this->k_auth); + DBG3(DBG_IKE, "AT_MAC signature of %B", &message); + DBG3(DBG_IKE, "using key %B", &this->k_auth); + signer->get_signature(signer, message, mac_pos); + DBG3(DBG_IKE, "is %b", mac_pos, AT_MAC_LENGTH); + signer->destroy(signer); + } + + /* payload constructor takes data with some bytes skipped */ + payload = eap_payload_create_data(message); + + DBG3(DBG_IKE, "created EAP message %B", &message); + return payload; +} + +/** + * Initiate a AKA-Challenge using SQN + */ +static status_t server_initiate_challenge(private_eap_aka_t *this, chunk_t sqn, eap_payload_t **out) +{ + randomizer_t *randomizer; + status_t status; + chunk_t mac, ak, autn; + + mac = chunk_alloca(MAC_LENGTH); + ak = chunk_alloca(AK_LENGTH); + chunk_free(&this->rand); + chunk_free(&this->xres); + + /* generate RAND: + * we use our standard randomizer, not f0() proposed in S.S0055 + */ + randomizer = randomizer_create(); + status = randomizer->allocate_pseudo_random_bytes(randomizer, RAND_LENGTH, &this->rand); + randomizer->destroy(randomizer); + if (status != SUCCESS) + { + DBG1(DBG_IKE, "generating RAND for EAP-AKA authentication failed"); + return FAILED; + } + +# ifdef TEST_VECTORS + /* Test vector for RAND */ + u_int8_t test_rand[] = { + 0x4b,0x05,0x2b,0x20,0xe2,0xa0,0x6c,0x8f, + 0xf7,0x00,0xda,0x51,0x2b,0x4e,0x11,0x1e, + }; + memcpy(this->rand.ptr, test_rand, this->rand.len); +# endif /* TEST_VECTORS */ + + /* Get the shared key K: */ + if (load_key(this->server, this->peer, &this->k) != SUCCESS) + { + DBG1(DBG_IKE, "no shared key found for IDs '%D' - '%D' to authenticate " + "with EAP-AKA", this->server, this->peer); + return FAILED; + } + +# ifdef TEST_VECTORS + /* Test vector for K */ + u_int8_t test_k[] = { + 0xad,0x1b,0x5a,0x15,0x9b,0xe8,0x6b,0x2c, + 0xa6,0x6c,0x7a,0xe4,0x0b,0xba,0x9b,0x9d, + }; + memcpy(this->k.ptr, test_k, this->k.len); +# endif /* TEST_VECTORS */ + + /* generate MAC */ + f1(this->k, this->rand, sqn, amf, mac.ptr); + + /* generate AK */ + f5(this->k, this->rand, ak.ptr); + + /* precalculate XRES as expected from client */ + this->xres = chunk_alloc(RES_LENGTH); + f2(this->k, this->rand, this->xres.ptr); + + /* calculate AUTN = (SQN xor AK) || AMF || MAC */ + autn = chunk_cata("ccc", sqn, amf, mac); + memxor(autn.ptr, ak.ptr, ak.len); + DBG3(DBG_IKE, "AUTN %B", &autn); + + + /* derive K_encr, K_auth, MSK, EMSK */ + derive_keys(this, this->peer); + + /* build payload */ + *out = build_aka_payload(this, EAP_REQUEST, 0, AKA_CHALLENGE, + AT_RAND, this->rand, AT_AUTN, autn, AT_MAC, + chunk_empty, AT_END); + return NEED_MORE; +} + +/** + * Implementation of eap_method_t.initiate for an EAP_AKA server + */ +static status_t server_initiate(private_eap_aka_t *this, eap_payload_t **out) +{ + chunk_t sqn = chunk_alloca(SQN_LENGTH); + + /* we use an offset of 3 minutes to tolerate clock inaccuracy + * without the need to synchronize sequence numbers */ + update_sqn(sqn.ptr, 180); + +# ifdef TEST_VECTORS + /* Test vector for SQN */ + u_int8_t test_sqn[] = {0x00,0x00,0x00,0x00,0x00,0x01}; + memcpy(sqn.ptr, test_sqn, sqn.len); +# endif /* TEST_VECTORS */ + + return server_initiate_challenge(this, sqn, out); +} + +static status_t server_process_synchronize(private_eap_aka_t *this, + eap_payload_t *in, eap_payload_t **out) +{ + chunk_t attr, auts = chunk_empty, pos, message, macs, xmacs, sqn, aks, amf; + u_int i; + + message = in->get_data(in); + pos = message; + read_header(&pos); + + /* iterate over attributes */ + while (TRUE) + { + aka_attribute_t attribute = read_attribute(&pos, &attr); + switch (attribute) + { + case AT_END: + break; + case AT_AUTS: + auts = attr; + continue; + default: + if (attribute >= 0 && attribute <= 127) + { + DBG1(DBG_IKE, "found non skippable attribute %N", + aka_attribute_names, attribute); + return FAILED; + } + DBG1(DBG_IKE, "ignoring skippable attribute %N", + aka_attribute_names, attribute); + continue; + } + break; + } + + if (auts.len != AUTS_LENGTH) + { + DBG1(DBG_IKE, "synchronization request didn't contain useable AUTS"); + return FAILED; + } + + chunk_split(auts, "mm", SQN_LENGTH, &sqn, MAC_LENGTH, &macs); + aks = chunk_alloca(AK_LENGTH); + f5star(this->k, this->rand, aks.ptr); + /* decrypt serial number by XORing AKS */ + memxor(sqn.ptr, aks.ptr, aks.len); + + /* verify MACS */ + xmacs = chunk_alloca(MAC_LENGTH); + amf = chunk_alloca(AMF_LENGTH); + /* an AMF of zero is used for MACS calculation */ + memset(amf.ptr, 0, amf.len); + f1star(this->k, this->rand, sqn, amf, xmacs.ptr); + if (!chunk_equals(macs, xmacs)) + { + DBG1(DBG_IKE, "received MACS does not match XMACS"); + DBG3(DBG_IKE, "MACS %B XMACS %B", &macs, &xmacs); + return FAILED; + } + + /* retry the challenge with the received SQN + 1*/ + for (i = SQN_LENGTH - 1; i >= 0; i--) + { + if (++sqn.ptr[i] != 0) + { + break; + } + } + return server_initiate_challenge(this, sqn, out); +} + +/** + * process an AKA_Challenge response + */ +static status_t server_process_challenge(private_eap_aka_t *this, eap_payload_t *in) +{ + chunk_t attr, res = chunk_empty, at_mac = chunk_empty, pos, message; + + message = in->get_data(in); + pos = message; + read_header(&pos); + + /* iterate over attributes */ + while (TRUE) + { + aka_attribute_t attribute = read_attribute(&pos, &attr); + switch (attribute) + { + case AT_END: + break; + case AT_RES: + res = attr; + if (attr.len == 2 + RES_LENGTH && + *(u_int16_t*)attr.ptr == htons(RES_LENGTH * 8)) + { + res = chunk_skip(attr, 2); + } + continue; + + case AT_MAC: + attr = chunk_skip(attr, 2); + at_mac = chunk_clonea(attr); + /* zero MAC in message for MAC verification */ + memset(attr.ptr, 0, attr.len); + continue; + default: + if (attribute >= 0 && attribute <= 127) + { + DBG1(DBG_IKE, "found non skippable attribute %N", + aka_attribute_names, attribute); + return FAILED; + } + DBG1(DBG_IKE, "ignoring skippable attribute %N", + aka_attribute_names, attribute); + continue; + } + break; + } + + /* verify EAP message MAC AT_MAC */ + { + bool valid; + signer_t *signer = signer_create(AUTH_HMAC_SHA1_128); + signer->set_key(signer, this->k_auth); + DBG3(DBG_IKE, "verifying AT_MAC signature of %B", &message); + DBG3(DBG_IKE, "using key %B", &this->k_auth); + valid = signer->verify_signature(signer, message, at_mac); + signer->destroy(signer); + if (!valid) + { + DBG1(DBG_IKE, "MAC in AT_MAC attribute verification failed"); + return FAILED; + } + } + + /* compare received RES against stored precalculated XRES */ + if (!chunk_equals(res, this->xres)) + { + DBG1(DBG_IKE, "received RES does not match XRES"); + DBG3(DBG_IKE, "RES %Bb XRES %B", &res, &this->xres); + return FAILED; + } + return SUCCESS; +} + +/** + * Implementation of eap_method_t.process for EAP_AKA servers + */ +static status_t server_process(private_eap_aka_t *this, + eap_payload_t *in, eap_payload_t **out) +{ + chunk_t message; + aka_subtype_t type; + + message = in->get_data(in); + type = read_header(&message); + + DBG3(DBG_IKE, "received EAP message %B", &message); + + switch (type) + { + case AKA_CHALLENGE: + { + return server_process_challenge(this, in); + } + case AKA_AUTHENTICATION_REJECT: + case AKA_CLIENT_ERROR: + { + DBG1(DBG_IKE, "received %N, authentication failed", + aka_subtype_names, type); + return FAILED; + } + case AKA_SYNCHRONIZATION_FAILURE: + { + DBG1(DBG_IKE, "received %N, retrying with received SQN", + aka_subtype_names, type); + return server_process_synchronize(this, in, out); + } + default: + DBG1(DBG_IKE, "received unknown AKA subtype %N, authentication failed", + aka_subtype_names, type); + return FAILED; + } +} + +/** + * Process an incoming AKA-Challenge client side + */ +static status_t peer_process_challenge(private_eap_aka_t *this, + eap_payload_t *in, eap_payload_t **out) +{ + chunk_t attr = chunk_empty; + chunk_t autn = chunk_empty, at_mac = chunk_empty; + chunk_t ak, sqn, sqn_ak, mac, xmac, res, amf, message, pos; + u_int8_t identifier; + + ak = chunk_alloca(AK_LENGTH); + xmac = chunk_alloca(MAC_LENGTH); + res = chunk_alloca(RES_LENGTH); + chunk_free(&this->rand); + + message = in->get_data(in); + pos = message; + read_header(&pos); + identifier = in->get_identifier(in); + + DBG3(DBG_IKE, "reading attributes from %B", &pos); + + /* iterate over attributes */ + while (TRUE) + { + aka_attribute_t attribute = read_attribute(&pos, &attr); + switch (attribute) + { + case AT_END: + break; + case AT_RAND: + this->rand = chunk_clone(chunk_skip(attr, 2)); + continue; + case AT_AUTN: + autn = chunk_skip(attr, 2); + continue; + case AT_MAC: + attr = chunk_skip(attr, 2); + at_mac = chunk_clonea(attr); + /* set MAC in message to zero for own MAC verification */ + memset(attr.ptr, 0, attr.len); + continue; + default: + if (attribute >= 0 && attribute <= 127) + { + /* non skippable attribute, abort */ + *out = build_aka_payload(this, EAP_RESPONSE, identifier, AKA_CLIENT_ERROR, + AT_CLIENT_ERROR_CODE, client_error_code, AT_END); + DBG1(DBG_IKE, "found non skippable attribute %N, sending %N %d", + aka_attribute_names, attribute, + aka_attribute_names, AT_CLIENT_ERROR_CODE, 0); + return NEED_MORE; + } + DBG1(DBG_IKE, "ignoring skippable attribute %N", + aka_attribute_names, attribute); + continue; + } + break; + } + + if (this->rand.len != RAND_LENGTH || autn.len != AUTN_LENGTH) + { + /* required attributes wrong/not found, abort */ + *out = build_aka_payload(this, EAP_RESPONSE, identifier, AKA_CLIENT_ERROR, + AT_CLIENT_ERROR_CODE, client_error_code, AT_END); + DBG1(DBG_IKE, "could not find valid RAND/AUTN attribute, sending %N %d", + aka_attribute_names, AT_CLIENT_ERROR_CODE, 0); + return NEED_MORE; + } + + DBG3(DBG_IKE, "using autn %B", &autn); + /* split up AUTN = SQN xor AK | AMF | MAC */ + chunk_split(autn, "mmm", SQN_LENGTH, &sqn_ak, AMF_LENGTH, &amf, MAC_LENGTH, &mac); + + /* Get the shared key K: */ + chunk_free(&this->k); + if (load_key(this->peer, this->server, &this->k) != SUCCESS) + { + *out = build_aka_payload(this, EAP_RESPONSE, identifier, + AKA_AUTHENTICATION_REJECT, AT_END); + DBG3(DBG_IKE, "no shared key found for IDs '%D' - '%D' to authenticate " + "with EAP-AKA, sending %N", this->peer, this->server, + aka_subtype_names, AKA_AUTHENTICATION_REJECT); + return NEED_MORE; + } + DBG3(DBG_IKE, "using K %B", &this->k); +# ifdef TEST_VECTORS + /* Test vector for K */ + u_int8_t test_k[] = { + 0xad,0x1b,0x5a,0x15,0x9b,0xe8,0x6b,0x2c, + 0xa6,0x6c,0x7a,0xe4,0x0b,0xba,0x9b,0x9d, + }; + memcpy(this->k.ptr, test_k, this->k.len); +# endif /* TEST_VECTORS */ + + /* calculate anonymity key AK */ + f5(this->k, this->rand, ak.ptr); + DBG3(DBG_IKE, "using rand %B", &this->rand); + DBG3(DBG_IKE, "using ak %B", &ak); + /* XOR AK into SQN to decrypt it */ + + sqn = chunk_clonea(sqn_ak); + + DBG3(DBG_IKE, "using ak xor sqn %B", &sqn_ak); + memxor(sqn.ptr, ak.ptr, sqn.len); + DBG3(DBG_IKE, "using sqn %B", &sqn); + + /* calculate expected MAC and compare against received one */ + f1(this->k, this->rand, sqn, amf, xmac.ptr); + if (!chunk_equals(mac, xmac)) + { + *out = build_aka_payload(this, EAP_RESPONSE, identifier, + AKA_AUTHENTICATION_REJECT, AT_END); + DBG1(DBG_IKE, "received MAC does not match XMAC, sending %N", + aka_subtype_names, AKA_AUTHENTICATION_REJECT); + DBG3(DBG_IKE, "MAC %B\nXMAC %B", &mac, &xmac); + return NEED_MORE; + } + +#if SEQ_CHECK + if (memcmp(peer_sqn.ptr, sqn.ptr, sqn.len) >= 0) + { + /* sequence number invalid. send AUTS */ + chunk_t auts, macs, aks, amf; + + macs = chunk_alloca(MAC_LENGTH); + aks = chunk_alloca(AK_LENGTH); + amf = chunk_alloca(AMF_LENGTH); + + /* AMF is set to zero in AKA_SYNCHRONIZATION_FAILURE */ + memset(amf.ptr, 0, amf.len); + /* AKS = f5*(RAND) */ + f5star(this->k, this->rand, aks.ptr); + /* MACS = f1*(RAND) */ + f1star(this->k, this->rand, peer_sqn, amf, macs.ptr); + /* AUTS = SQN xor AKS | MACS */ + memxor(aks.ptr, peer_sqn.ptr, aks.len); + auts = chunk_cata("cc", aks, macs); + + *out = build_aka_payload(this, EAP_RESPONSE, identifier, + AKA_SYNCHRONIZATION_FAILURE, + AT_AUTS, auts, AT_END); + DBG1(DBG_IKE, "received SQN invalid, sending %N", + aka_subtype_names, AKA_SYNCHRONIZATION_FAILURE); + DBG3(DBG_IKE, "received SQN %B\ncurrent SQN %B", &sqn, &peer_sqn); + return NEED_MORE; + } +#endif /* SEQ_CHECK */ + + /* derive K_encr, K_auth, MSK, EMSK */ + derive_keys(this, this->peer); + + /* verify EAP message MAC AT_MAC */ + { + bool valid; + signer_t *signer = signer_create(AUTH_HMAC_SHA1_128); + signer->set_key(signer, this->k_auth); + + DBG3(DBG_IKE, "verifying AT_MAC signature of %B", &message); + DBG3(DBG_IKE, "using key %B", &this->k_auth); + valid = signer->verify_signature(signer, message, at_mac); + signer->destroy(signer); + if (!valid) + { + *out = build_aka_payload(this, EAP_RESPONSE, identifier, AKA_CLIENT_ERROR, + AT_CLIENT_ERROR_CODE, client_error_code, AT_END); + DBG1(DBG_IKE, "MAC in AT_MAC attribute verification " + "failed, sending %N %d", aka_attribute_names, + AT_CLIENT_ERROR_CODE, 0); + return NEED_MORE; + } + } + + /* update stored SQN to the received one */ + memcpy(peer_sqn.ptr, sqn.ptr, sqn.len); + + /* calculate RES */ + f2(this->k, this->rand, res.ptr); + + /* build response */ + *out = build_aka_payload(this, EAP_RESPONSE, identifier, AKA_CHALLENGE, + AT_RES, res, AT_MAC, chunk_empty, AT_END); + return NEED_MORE; +} + +/** + * Process an incoming AKA-Notification as client + */ +static status_t peer_process_notification(private_eap_aka_t *this, + eap_payload_t *in, eap_payload_t **out) +{ + chunk_t message, pos, attr; + u_int8_t identifier; + + message = in->get_data(in); + pos = message; + read_header(&pos); + identifier = in->get_identifier(in); + + DBG3(DBG_IKE, "reading attributes from %B", &pos); + + /* iterate over attributes */ + while (TRUE) + { + aka_attribute_t attribute = read_attribute(&pos, &attr); + switch (attribute) + { + case AT_END: + break; + case AT_NOTIFICATION: + { + u_int16_t code; + + if (attr.len != 2) + { + DBG1(DBG_IKE, "received invalid AKA notification, ignored"); + continue; + } + code = ntohs(*(u_int16_t*)attr.ptr); + switch (code) + { + case 0: + DBG1(DBG_IKE, "received AKA notification 'general " + "failure after authentication' (%d)", code); + return FAILED; + case 16384: + DBG1(DBG_IKE, "received AKA notification 'general " + "failure' (%d)", code); + return FAILED; + case 32768: + DBG1(DBG_IKE, "received AKA notification 'successfully " + "authenticated' (%d)", code); + continue; + case 1026: + DBG1(DBG_IKE, "received AKA notification 'access " + "temporarily denied' (%d)", code); + return FAILED; + case 1031: + DBG1(DBG_IKE, "received AKA notification 'not " + "subscribed to service' (%d)", code); + return FAILED; + default: + DBG1(DBG_IKE, "received AKA notification code %d, " + "ignored", code); + continue; + } + } + default: + if (attribute >= 0 && attribute <= 127) + { + DBG1(DBG_IKE, "ignoring non-skippable attribute %N in %N", + aka_attribute_names, attribute, aka_subtype_names, + AKA_NOTIFICATION); + } + else + { + DBG1(DBG_IKE, "ignoring skippable attribute %N", + aka_attribute_names, attribute); + } + continue; + } + break; + } + return NEED_MORE; +} + +/** + * Implementation of eap_method_t.process for an EAP_AKA peer + */ +static status_t peer_process(private_eap_aka_t *this, + eap_payload_t *in, eap_payload_t **out) +{ + aka_subtype_t type; + chunk_t message; + u_int8_t identifier; + + message = in->get_data(in); + type = read_header(&message); + identifier = in->get_identifier(in); + + DBG3(DBG_IKE, "received EAP message %B", &message); + + switch (type) + { + case AKA_CHALLENGE: + { + return peer_process_challenge(this, in, out); + } + case AKA_NOTIFICATION: + { + return peer_process_notification(this, in, out); + } + default: + { + *out = build_aka_payload(this, EAP_RESPONSE, identifier, AKA_CLIENT_ERROR, + AT_CLIENT_ERROR_CODE, client_error_code, AT_END); + DBG1(DBG_IKE, "received unsupported %N request, sending %N %d", + aka_subtype_names, type, + aka_attribute_names, AT_CLIENT_ERROR_CODE, 0); + return NEED_MORE; + } + } +} + +/** + * Implementation of eap_method_t.initiate for an EAP AKA peer + */ +static status_t peer_initiate(private_eap_aka_t *this, eap_payload_t **out) +{ + /* peer never initiates */ + return FAILED; +} + +/** + * Implementation of eap_method_t.get_type. + */ +static eap_type_t get_type(private_eap_aka_t *this, u_int32_t *vendor) +{ + *vendor = 0; + return EAP_AKA; +} + +/** + * Implementation of eap_method_t.get_msk. + */ +static status_t get_msk(private_eap_aka_t *this, chunk_t *msk) +{ + if (this->msk.ptr) + { + *msk = this->msk; + return SUCCESS; + } + return FAILED; +} + +/** + * Implementation of eap_method_t.is_mutual. + */ +static bool is_mutual(private_eap_aka_t *this) +{ + return TRUE; +} + +/** + * Implementation of eap_method_t.destroy. + */ +static void destroy(private_eap_aka_t *this) +{ + chunk_free(&this->k_encr); + chunk_free(&this->k_auth); + chunk_free(&this->msk); + chunk_free(&this->emsk); + chunk_free(&this->xres); + chunk_free(&this->k); + chunk_free(&this->rand); + free(this); +} + +/* + * Described in header. + */ +eap_aka_t *eap_create(eap_role_t role, + identification_t *server, identification_t *peer) +{ + private_eap_aka_t *this = malloc_thing(private_eap_aka_t); + + /* public functions */ + switch (role) + { + case EAP_SERVER: + this->public.eap_method_interface.initiate = (status_t(*)(eap_method_t*,eap_payload_t**))server_initiate; + this->public.eap_method_interface.process = (status_t(*)(eap_method_t*,eap_payload_t*,eap_payload_t**))server_process; + break; + case EAP_PEER: + this->public.eap_method_interface.initiate = (status_t(*)(eap_method_t*,eap_payload_t**))peer_initiate; + this->public.eap_method_interface.process = (status_t(*)(eap_method_t*,eap_payload_t*,eap_payload_t**))peer_process; + break; + default: + free(this); + return NULL; + } + this->public.eap_method_interface.get_type = (eap_type_t(*)(eap_method_t*,u_int32_t*))get_type; + this->public.eap_method_interface.is_mutual = (bool(*)(eap_method_t*))is_mutual; + this->public.eap_method_interface.get_msk = (status_t(*)(eap_method_t*,chunk_t*))get_msk; + this->public.eap_method_interface.destroy = (void(*)(eap_method_t*))destroy; + + /* private data */ + this->server = server; + this->peer = peer; + this->k_encr = chunk_empty; + this->k_auth = chunk_empty; + this->msk = chunk_empty; + this->emsk = chunk_empty; + this->xres = chunk_empty; + this->k = chunk_empty; + this->rand = chunk_empty; + + return &this->public; +} diff --git a/src/charon/sa/authenticators/eap/eap_aka.h b/src/charon/sa/authenticators/eap/eap_aka.h new file mode 100644 index 000000000..a886863be --- /dev/null +++ b/src/charon/sa/authenticators/eap/eap_aka.h @@ -0,0 +1,141 @@ +/** + * @file eap_aka.h + * + * @brief Interface of eap_aka_t. + * + */ + +/* + * Copyright (C) 2006 Martin Willi + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#ifndef EAP_AKA_H_ +#define EAP_AKA_H_ + +typedef struct eap_aka_t eap_aka_t; +typedef enum aka_subtype_t aka_subtype_t; +typedef enum aka_attribute_t aka_attribute_t; + +#include + + +/** + * Subtypes of AKA messages + */ +enum aka_subtype_t { + AKA_CHALLENGE = 1, + AKA_AUTHENTICATION_REJECT = 2, + AKA_SYNCHRONIZATION_FAILURE = 4, + AKA_IDENTITY = 5, + AKA_NOTIFICATION = 12, + AKA_REAUTHENTICATION = 13, + AKA_CLIENT_ERROR = 14, +}; + +/** + * enum names for aka_subtype_t + */ +extern enum_name_t *aka_subtype_names; + +/** + * Attribute types in AKA messages + */ +enum aka_attribute_t { + /** defines the end of attribute list */ + AT_END = -1, + AT_RAND = 1, + AT_AUTN = 2, + AT_RES = 3, + AT_AUTS = 4, + AT_PADDING = 6, + AT_NONCE_MT = 7, + AT_PERMANENT_ID_REQ = 10, + AT_MAC = 11, + AT_NOTIFICATION = 12, + AT_ANY_ID_REQ = 13, + AT_IDENTITY = 14, + AT_VERSION_LIST = 15, + AT_SELECTED_VERSION = 16, + AT_FULLAUTH_ID_REQ = 17, + AT_COUNTER = 19, + AT_COUNTER_TOO_SMALL = 20, + AT_NONCE_S = 21, + AT_CLIENT_ERROR_CODE = 22, + AT_IV = 129, + AT_ENCR_DATA = 130, + AT_NEXT_PSEUDONYM = 132, + AT_NEXT_REAUTH_ID = 133, + AT_CHECKCODE = 134, + AT_RESULT_IND = 135, +}; + +/** + * enum names for aka_attribute_t + */ +extern enum_name_t *aka_attribute_names; + +/** check SEQ values as client for validity, disabled by default */ +#ifndef SEQ_CHECK +# define SEQ_CHECK 0 +#endif + +/** + * @brief Implementation of the eap_method_t interface using EAP-AKA. + * + * EAP-AKA uses 3rd generation mobile phone standard authentication + * mechanism for authentication. It is a mutual authentication + * mechanism which establishs a shared key and therefore supports EAP_ONLY + * authentication. This implementation follows the standard of the + * 3GPP2 (S.S0055) and not the one of 3GGP. + * The shared key used for authentication is from ipsec.secrets. The + * peers ID is used to query it. + * The AKA mechanism uses sequence numbers to detect replay attacks. The + * peer stores the sequence number normally in a USIM and accepts + * incremental sequence numbers (incremental for lifetime of the USIM). To + * prevent a complex sequence number management, this implementation uses + * a sequence number derived from time. It is initialized to the startup + * time of the daemon. As long as the (UTC) time of the system is not + * turned back while the daemon is not running, this method is secure. + * To enable time based SEQs, #define SEQ_CHECK as 1. Default is to accept + * any SEQ numbers. This allows an attacker to do replay attacks. But since + * the server has proven his identity via IKE, such an attack is only + * possible between server and AAA (if any). + * + * @b Constructors: + * - eap_aka_create() + * - eap_client_create() using eap_method EAP_AKA + * + * @ingroup eap + */ +struct eap_aka_t { + + /** + * Implemented eap_method_t interface. + */ + eap_method_t eap_method_interface; +}; + +/** + * @brief Creates the EAP method EAP-AKA. + * + * @param server ID of the EAP server + * @param peer ID of the EAP client + * @return eap_aka_t object + * + * @ingroup eap + */ +eap_aka_t *eap_create(eap_role_t role, + identification_t *server, identification_t *peer); + +#endif /* EAP_AKA_H_ */ diff --git a/src/charon/sa/authenticators/eap/eap_md5.c b/src/charon/sa/authenticators/eap/eap_md5.c new file mode 100644 index 000000000..0ca9fc566 --- /dev/null +++ b/src/charon/sa/authenticators/eap/eap_md5.c @@ -0,0 +1,282 @@ +/** + * @file eap_md5.c + * + * @brief Implementation of eap_md5_t. + * + */ + +/* + * Copyright (C) 2007 Martin Willi + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#include "eap_md5.h" + +#include +#include + +typedef struct private_eap_md5_t private_eap_md5_t; + +/** + * Private data of an eap_md5_t object. + */ +struct private_eap_md5_t { + + /** + * Public authenticator_t interface. + */ + eap_md5_t public; + + /** + * ID of the server + */ + identification_t *server; + + /** + * ID of the peer + */ + identification_t *peer; + + /** + * challenge sent by the server + */ + chunk_t challenge; + + /** + * EAP message identififier + */ + u_int8_t identifier; +}; + +typedef struct eap_md5_header_t eap_md5_header_t; + +/** + * packed eap MD5 header struct + */ +struct eap_md5_header_t { + /** EAP code (REQUEST/RESPONSE) */ + u_int8_t code; + /** unique message identifier */ + u_int8_t identifier; + /** length of whole message */ + u_int16_t length; + /** EAP type */ + u_int8_t type; + /** length of value (challenge) */ + u_int8_t value_size; + /** actual value */ + u_int8_t value[]; +} __attribute__((__packed__)); + +#define CHALLENGE_LEN 16 +#define PAYLOAD_LEN (CHALLENGE_LEN + sizeof(eap_md5_header_t)) + +/** + * Hash the challenge string, create response + */ +static status_t hash_challenge(private_eap_md5_t *this, chunk_t *response) +{ + chunk_t concat, secret; + hasher_t *hasher; + + if (charon->credentials->get_eap_key(charon->credentials, this->server, + this->peer, &secret) != SUCCESS) + { + DBG1(DBG_IKE, "no EAP key found for hosts '%D' - '%D'", + this->server, this->peer); + return NOT_FOUND; + } + concat = chunk_cata("cmc", chunk_from_thing(this->identifier), + secret, this->challenge); + hasher = hasher_create(HASH_MD5); + hasher->allocate_hash(hasher, concat, response); + hasher->destroy(hasher); + return SUCCESS; +} + +/** + * Implementation of eap_method_t.initiate for the peer + */ +static status_t initiate_peer(private_eap_md5_t *this, eap_payload_t **out) +{ + /* peer never initiates */ + return FAILED; +} + +/** + * Implementation of eap_method_t.initiate for the server + */ +static status_t initiate_server(private_eap_md5_t *this, eap_payload_t **out) +{ + randomizer_t *randomizer; + status_t status; + eap_md5_header_t *req; + + randomizer = randomizer_create(); + status = randomizer->allocate_pseudo_random_bytes(randomizer, CHALLENGE_LEN, + &this->challenge); + randomizer->destroy(randomizer); + if (status != SUCCESS) + { + return FAILED; + } + + req = alloca(PAYLOAD_LEN); + req->length = htons(PAYLOAD_LEN); + req->code = EAP_REQUEST; + req->identifier = this->identifier; + req->type = EAP_MD5; + req->value_size = this->challenge.len; + memcpy(req->value, this->challenge.ptr, this->challenge.len); + + *out = eap_payload_create_data(chunk_create((void*)req, PAYLOAD_LEN)); + return NEED_MORE; +} + +/** + * Implementation of eap_method_t.process for the peer + */ +static status_t process_peer(private_eap_md5_t *this, + eap_payload_t *in, eap_payload_t **out) +{ + chunk_t response; + chunk_t data; + eap_md5_header_t *req; + + this->identifier = in->get_identifier(in); + data = in->get_data(in); + this->challenge = chunk_clone(chunk_skip(data, 6)); + if (data.len < 6 || this->challenge.len < *(data.ptr + 5)) + { + DBG1(DBG_IKE, "received invalid EAP-MD5 message"); + return FAILED; + } + if (hash_challenge(this, &response) != SUCCESS) + { + return FAILED; + } + req = alloca(PAYLOAD_LEN); + req->length = htons(PAYLOAD_LEN); + req->code = EAP_RESPONSE; + req->identifier = this->identifier; + req->type = EAP_MD5; + req->value_size = response.len; + memcpy(req->value, response.ptr, response.len); + chunk_free(&response); + + *out = eap_payload_create_data(chunk_create((void*)req, PAYLOAD_LEN)); + return NEED_MORE; +} + +/** + * Implementation of eap_method_t.process for the server + */ +static status_t process_server(private_eap_md5_t *this, + eap_payload_t *in, eap_payload_t **out) +{ + chunk_t response, expected; + chunk_t data; + + if (this->identifier != in->get_identifier(in)) + { + DBG1(DBG_IKE, "received invalid EAP-MD5 message"); + return FAILED; + } + if (hash_challenge(this, &expected) != SUCCESS) + { + return FAILED; + } + data = in->get_data(in); + response = chunk_skip(data, 6); + + if (response.len < expected.len || + !memeq(response.ptr, expected.ptr, expected.len)) + { + chunk_free(&expected); + DBG1(DBG_IKE, "EAP-MD5 verification failed"); + return FAILED; + } + chunk_free(&expected); + return SUCCESS; +} + +/** + * Implementation of eap_method_t.get_type. + */ +static eap_type_t get_type(private_eap_md5_t *this, u_int32_t *vendor) +{ + *vendor = 0; + return EAP_MD5; +} + +/** + * Implementation of eap_method_t.get_msk. + */ +static status_t get_msk(private_eap_md5_t *this, chunk_t *msk) +{ + return FAILED; +} + +/** + * Implementation of eap_method_t.is_mutual. + */ +static bool is_mutual(private_eap_md5_t *this) +{ + return FALSE; +} + +/** + * Implementation of eap_method_t.destroy. + */ +static void destroy(private_eap_md5_t *this) +{ + chunk_free(&this->challenge); + free(this); +} + +/* + * Described in header. + */ +eap_md5_t *eap_create(eap_role_t role, + identification_t *server, identification_t *peer) +{ + private_eap_md5_t *this = malloc_thing(private_eap_md5_t); + + /* public functions */ + switch (role) + { + case EAP_SERVER: + this->public.eap_method_interface.initiate = (status_t(*)(eap_method_t*,eap_payload_t**))initiate_server; + this->public.eap_method_interface.process = (status_t(*)(eap_method_t*,eap_payload_t*,eap_payload_t**))process_server; + break; + case EAP_PEER: + this->public.eap_method_interface.initiate = (status_t(*)(eap_method_t*,eap_payload_t**))initiate_peer; + this->public.eap_method_interface.process = (status_t(*)(eap_method_t*,eap_payload_t*,eap_payload_t**))process_peer; + break; + default: + free(this); + return NULL; + } + this->public.eap_method_interface.get_type = (eap_type_t(*)(eap_method_t*,u_int32_t*))get_type; + this->public.eap_method_interface.is_mutual = (bool(*)(eap_method_t*))is_mutual; + this->public.eap_method_interface.get_msk = (status_t(*)(eap_method_t*,chunk_t*))get_msk; + this->public.eap_method_interface.destroy = (void(*)(eap_method_t*))destroy; + + /* private data */ + this->peer = peer; + this->server = server; + this->challenge = chunk_empty; + this->identifier = random(); + + return &this->public; +} diff --git a/src/charon/sa/authenticators/eap/eap_md5.h b/src/charon/sa/authenticators/eap/eap_md5.h new file mode 100644 index 000000000..260210b59 --- /dev/null +++ b/src/charon/sa/authenticators/eap/eap_md5.h @@ -0,0 +1,59 @@ +/** + * @file eap_md5.h + * + * @brief Interface of eap_md5_t. + * + */ + +/* + * Copyright (C) 2007 Martin Willi + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#ifndef EAP_MD5_H_ +#define EAP_MD5_H_ + +typedef struct eap_md5_t eap_md5_t; + +#include + +/** + * @brief Implementation of the eap_method_t interface using EAP-MD5 (CHAP). + * + * @b Constructors: + * - eap_md5_create() + * - eap_client_create() using eap_method EAP_MD5 + * + * @ingroup eap + */ +struct eap_md5_t { + + /** + * Implemented eap_method_t interface. + */ + eap_method_t eap_method_interface; +}; + +/** + * @brief Creates the EAP method EAP-MD5. + * + * @param server ID of the EAP server + * @param peer ID of the EAP client + * @return eap_md5_t object + * + * @ingroup eap + */ +eap_md5_t *eap_create(eap_role_t role, + identification_t *server, identification_t *peer); + +#endif /* EAP_MD5_H_ */ diff --git a/src/charon/sa/authenticators/eap/eap_method.c b/src/charon/sa/authenticators/eap/eap_method.c index e4a58f0a3..7434ca2a1 100644 --- a/src/charon/sa/authenticators/eap/eap_method.c +++ b/src/charon/sa/authenticators/eap/eap_method.c @@ -45,7 +45,10 @@ ENUM_NEXT(eap_type_names, EAP_SIM, EAP_SIM, EAP_TOKEN_CARD, "EAP_SIM"); ENUM_NEXT(eap_type_names, EAP_AKA, EAP_AKA, EAP_SIM, "EAP_AKA"); -ENUM_END(eap_type_names, EAP_AKA); +ENUM_NEXT(eap_type_names, EAP_EXPANDED, EAP_EXPERIMENTAL, EAP_AKA, + "EAP_EXPANDED", + "EAP_EXPERIMENTAL"); +ENUM_END(eap_type_names, EAP_EXPERIMENTAL); ENUM(eap_code_names, EAP_REQUEST, EAP_FAILURE, "EAP_REQUEST", @@ -67,6 +70,7 @@ typedef struct module_entry_t module_entry_t; */ struct module_entry_t { eap_type_t type; + u_int32_t vendor; void *handle; eap_constructor_t constructor; }; @@ -85,7 +89,8 @@ void eap_method_unload() while (modules->remove_last(modules, (void**)&entry) == SUCCESS) { - DBG2(DBG_CFG, "unloaded module for %N", eap_type_names, entry->type); + DBG2(DBG_CFG, "unloaded module EAP module %d-%d", + entry->type, entry->vendor); dlclose(entry->handle); free(entry); } @@ -165,11 +170,19 @@ void eap_method_load(char *directory) dlclose(module.handle); continue; } - module.type = method->get_type(method); + module.type = method->get_type(method, &module.vendor); method->destroy(method); - DBG1(DBG_CFG, " loaded EAP method %N successfully from %s", - eap_type_names, module.type, entry->d_name); + if (module.vendor) + { + DBG1(DBG_CFG, " loaded EAP method %d, vendor %d successfully from %s", + module.type, module.vendor, entry->d_name); + } + else + { + DBG1(DBG_CFG, " loaded EAP method %N successfully from %s", + eap_type_names, module.type, entry->d_name); + } loaded_module = malloc_thing(module_entry_t); memcpy(loaded_module, &module, sizeof(module)); @@ -181,9 +194,8 @@ void eap_method_load(char *directory) /* * Described in header. */ -eap_method_t *eap_method_create(eap_type_t type, eap_role_t role, - identification_t *server, - identification_t *peer) +eap_method_t *eap_method_create(eap_type_t type, u_int32_t vendor, eap_role_t role, + identification_t *server, identification_t *peer) { eap_method_t *method = NULL; iterator_t *iterator; @@ -192,7 +204,7 @@ eap_method_t *eap_method_create(eap_type_t type, eap_role_t role, iterator = modules->create_iterator(modules, TRUE); while (iterator->iterate(iterator, (void**)&entry)) { - if (entry->type == type) + if (entry->type == type && entry->vendor == vendor) { method = entry->constructor(role, server, peer); if (method) @@ -205,8 +217,16 @@ eap_method_t *eap_method_create(eap_type_t type, eap_role_t role, if (method == NULL) { - DBG1(DBG_CFG, "no EAP module found for %N %N", - eap_type_names, type, eap_role_names, role); + if (vendor) + { + DBG1(DBG_CFG, "no vendor %d specific EAP module found for method " + "%d %N", vendor, type, eap_role_names, role); + } + else + { + DBG1(DBG_CFG, "no EAP module found for %N %N", + eap_type_names, type, eap_role_names, role); + } } return method; } diff --git a/src/charon/sa/authenticators/eap/eap_method.h b/src/charon/sa/authenticators/eap/eap_method.h index d43dc001f..8675fd8ec 100644 --- a/src/charon/sa/authenticators/eap/eap_method.h +++ b/src/charon/sa/authenticators/eap/eap_method.h @@ -62,6 +62,8 @@ enum eap_type_t { EAP_TOKEN_CARD = 6, EAP_SIM = 18, EAP_AKA = 23, + EAP_EXPANDED = 254, + EAP_EXPERIMENTAL = 255, }; /** @@ -148,9 +150,10 @@ struct eap_method_t { * @brief Get the EAP type implemented in this method. * * @param this calling object + * @param vendor pointer receiving vendor identifier for type, 0 for none * @return type of the EAP method */ - eap_type_t (*get_type) (eap_method_t *this); + eap_type_t (*get_type) (eap_method_t *this, u_int32_t *vendor); /** * @brief Check if this EAP method authenticates the server. @@ -188,6 +191,7 @@ struct eap_method_t { * @brief Creates an EAP method for a specific type and role. * * @param eap_type EAP type to use + * @param eap_vendor vendor identifier if a vendor specifc EAP type is used * @param role role of the eap_method, server or peer * @param server ID of acting server * @param peer ID of involved peer (client) @@ -195,8 +199,9 @@ struct eap_method_t { * * @ingroup eap */ -eap_method_t *eap_method_create(eap_type_t eap_type, eap_role_t role, - identification_t *server, identification_t *peer); +eap_method_t *eap_method_create(eap_type_t eap_type, u_int32_t eap_vendor, + eap_role_t role, identification_t *server, + identification_t *peer); /** * @brief (Re-)Load all EAP modules in the EAP modules directory. diff --git a/src/charon/sa/authenticators/eap/eap_sim.c b/src/charon/sa/authenticators/eap/eap_sim.c index 38d7f2534..c9eb5ce8f 100644 --- a/src/charon/sa/authenticators/eap/eap_sim.c +++ b/src/charon/sa/authenticators/eap/eap_sim.c @@ -264,6 +264,7 @@ static eap_payload_t *build_payload(private_eap_sim_t *this, u_int8_t identifier } case AT_IDENTITY: { + u_int16_t act_len = data.len; /* align up to four byte */ if (data.len % 4) { @@ -275,7 +276,7 @@ static eap_payload_t *build_payload(private_eap_sim_t *this, u_int8_t identifier *pos.ptr = data.len/4 + 1; pos = chunk_skip(pos, 1); /* actual length in bytes */ - *(u_int16_t*)pos.ptr = htons(data.len); + *(u_int16_t*)pos.ptr = htons(act_len); pos = chunk_skip(pos, sizeof(u_int16_t)); memcpy(pos.ptr, data.ptr, data.len); pos = chunk_skip(pos, data.len); @@ -697,8 +698,9 @@ static status_t initiate(private_eap_sim_t *this, eap_payload_t **out) /** * Implementation of eap_method_t.get_type. */ -static eap_type_t get_type(private_eap_sim_t *this) +static eap_type_t get_type(private_eap_sim_t *this, u_int32_t *vendor) { + *vendor = 0; return EAP_SIM; } @@ -785,7 +787,7 @@ eap_sim_t *eap_create(eap_role_t role, /* public functions */ this->public.eap_method_interface.initiate = (status_t(*)(eap_method_t*,eap_payload_t**))initiate; this->public.eap_method_interface.process = (status_t(*)(eap_method_t*,eap_payload_t*,eap_payload_t**))process; - this->public.eap_method_interface.get_type = (eap_type_t(*)(eap_method_t*))get_type; + this->public.eap_method_interface.get_type = (eap_type_t(*)(eap_method_t*,u_int32_t*))get_type; this->public.eap_method_interface.is_mutual = (bool(*)(eap_method_t*))is_mutual; this->public.eap_method_interface.get_msk = (status_t(*)(eap_method_t*,chunk_t*))get_msk; this->public.eap_method_interface.destroy = (void(*)(eap_method_t*))destroy; diff --git a/src/charon/sa/authenticators/eap_authenticator.c b/src/charon/sa/authenticators/eap_authenticator.c index 6e2f73a43..6250604a6 100644 --- a/src/charon/sa/authenticators/eap_authenticator.c +++ b/src/charon/sa/authenticators/eap_authenticator.c @@ -138,7 +138,7 @@ static status_t build(private_eap_authenticator_t *this, chunk_t ike_sa_init, * Implementation of eap_authenticator_t.initiate */ static status_t initiate(private_eap_authenticator_t *this, eap_type_t type, - eap_payload_t **out) + u_int32_t vendor, eap_payload_t **out) { /* if initiate() is called, role is always server */ this->role = EAP_SERVER; @@ -151,21 +151,30 @@ static status_t initiate(private_eap_authenticator_t *this, eap_type_t type, return FAILED; } - DBG1(DBG_IKE, "requesting %N authentication", eap_type_names, type); - this->method = eap_method_create(type, this->role, + if (vendor) + { + DBG1(DBG_IKE, "requesting vendor specific EAP authentication %d-%d", + type, vendor); + } + else + { + DBG1(DBG_IKE, "requesting %N authentication", eap_type_names, type); + } + this->method = eap_method_create(type, vendor, this->role, this->ike_sa->get_my_id(this->ike_sa), this->ike_sa->get_other_id(this->ike_sa)); if (this->method == NULL) { - DBG1(DBG_IKE, "configured EAP server method %N not supported, sending %N", - eap_type_names, type, eap_code_names, EAP_FAILURE); + + DBG1(DBG_IKE, "configured EAP server method not supported, sending %N", + eap_code_names, EAP_FAILURE); *out = eap_payload_create_code(EAP_FAILURE); return FAILED; } if (this->method->initiate(this->method, out) != NEED_MORE) { - DBG1(DBG_IKE, "failed to initiate %N, sending %N", + DBG1(DBG_IKE, "failed to initiate EAP exchange, sending %N", eap_type_names, type, eap_code_names, EAP_FAILURE); *out = eap_payload_create_code(EAP_FAILURE); return FAILED; @@ -179,11 +188,14 @@ static status_t initiate(private_eap_authenticator_t *this, eap_type_t type, static status_t process_peer(private_eap_authenticator_t *this, eap_payload_t *in, eap_payload_t **out) { - eap_type_t type = in->get_type(in); + eap_type_t type; + u_int32_t vendor; - if (type == EAP_IDENTITY) + type = in->get_type(in, &vendor); + + if (!vendor && type == EAP_IDENTITY) { - eap_method_t *method = eap_method_create(type, EAP_PEER, + eap_method_t *method = eap_method_create(type, 0, EAP_PEER, this->ike_sa->get_other_id(this->ike_sa), this->ike_sa->get_my_id(this->ike_sa)); @@ -205,32 +217,57 @@ static status_t process_peer(private_eap_authenticator_t *this, /* create an eap_method for the first call */ if (this->method == NULL) { - DBG1(DBG_IKE, "EAP server requested %N authentication", - eap_type_names, type); - this->method = eap_method_create(type, EAP_PEER, + if (vendor) + { + DBG1(DBG_IKE, "EAP server requested vendor specific EAP method %d-%d", + type, vendor); + } + else + { + DBG1(DBG_IKE, "EAP server requested %N authentication", + eap_type_names, type); + } + this->method = eap_method_create(type, vendor, EAP_PEER, this->ike_sa->get_other_id(this->ike_sa), this->ike_sa->get_my_id(this->ike_sa)); if (this->method == NULL) { DBG1(DBG_IKE, "EAP server requested unsupported " - "EAP method %N, sending EAP_NAK", eap_type_names, type); + "EAP method, sending EAP_NAK"); *out = eap_payload_create_nak(); return NEED_MORE; } } + type = this->method->get_type(this->method, &vendor); + switch (this->method->process(this->method, in, out)) { case NEED_MORE: return NEED_MORE; case SUCCESS: - DBG1(DBG_IKE, "EAP method %N succeded", - eap_type_names, this->method->get_type(this->method)); + if (vendor) + { + DBG1(DBG_IKE, "EAP vendor specific method %d-%d succeded", + type, vendor); + } + else + { + DBG1(DBG_IKE, "EAP method %N succeded", eap_type_names, type); + } return SUCCESS; case FAILED: default: - DBG1(DBG_IKE, "EAP method %N failed", - eap_type_names, this->method->get_type(this->method)); + if (vendor) + { + DBG1(DBG_IKE, "EAP vendor specific method %d-%d failed", + type, vendor); + } + else + { + DBG1(DBG_IKE, "EAP method %N failed", + eap_type_names, type); + } return FAILED; } } @@ -241,6 +278,11 @@ static status_t process_peer(private_eap_authenticator_t *this, static status_t process_server(private_eap_authenticator_t *this, eap_payload_t *in, eap_payload_t **out) { + eap_type_t type; + u_int32_t vendor; + + type = this->method->get_type(this->method, &vendor); + switch (this->method->process(this->method, in, out)) { case NEED_MORE: @@ -248,22 +290,35 @@ static status_t process_server(private_eap_authenticator_t *this, case SUCCESS: if (this->method->get_msk(this->method, &this->msk) == SUCCESS) { - DBG1(DBG_IKE, "EAP method %N succeded, MSK established", - eap_type_names, this->method->get_type(this->method)); this->msk = chunk_clone(this->msk); } + if (vendor) + { + DBG1(DBG_IKE, "EAP vendor specific method %d-%d succeded, " + "%sMSK established", type, vendor, + this->msk.ptr ? "" : "no "); + } else { - DBG1(DBG_IKE, "EAP method %N succeded, no MSK established", - eap_type_names, this->method->get_type(this->method)); + DBG1(DBG_IKE, "EAP method %N succeded, %sMSK established", + eap_type_names, type, this->msk.ptr ? "" : "no "); } *out = eap_payload_create_code(EAP_SUCCESS); return SUCCESS; case FAILED: default: - DBG1(DBG_IKE, "EAP method %N failed for peer %D", - eap_type_names, this->method->get_type(this->method), - this->ike_sa->get_other_id(this->ike_sa)); + if (vendor) + { + DBG1(DBG_IKE, "EAP vendor specific method %d-%d failed for " + "peer %D", type, vendor, + this->ike_sa->get_other_id(this->ike_sa)); + } + else + { + DBG1(DBG_IKE, "EAP method %N failed for peer %D", + eap_type_names, type, + this->ike_sa->get_other_id(this->ike_sa)); + } *out = eap_payload_create_code(EAP_FAILURE); return FAILED; } @@ -363,7 +418,7 @@ eap_authenticator_t *eap_authenticator_create(ike_sa_t *ike_sa) this->public.authenticator_interface.destroy = (void(*)(authenticator_t*))destroy; this->public.is_mutual = (bool(*)(eap_authenticator_t*))is_mutual; - this->public.initiate = (status_t(*)(eap_authenticator_t*,eap_type_t,eap_payload_t**))initiate; + this->public.initiate = (status_t(*)(eap_authenticator_t*,eap_type_t,u_int32_t,eap_payload_t**))initiate; this->public.process = (status_t(*)(eap_authenticator_t*,eap_payload_t*,eap_payload_t**))process; /* private data */ diff --git a/src/charon/sa/authenticators/eap_authenticator.h b/src/charon/sa/authenticators/eap_authenticator.h index 64a3267d7..cf2180ee3 100644 --- a/src/charon/sa/authenticators/eap_authenticator.h +++ b/src/charon/sa/authenticators/eap_authenticator.h @@ -105,15 +105,16 @@ struct eap_authenticator_t { * this method. If initiate() returns NEED_MORE, the EAP authentication * process started. In any case, a payload is created in "out". * - * @param this calling object - * @param type EAP method to use to authenticate client - * @param out created initiaal EAP message to send + * @param this calling object + * @param type EAP method to use to authenticate client + * @param vendor EAP vendor identifier, if type is vendor specific, or 0 + * @param out created initiaal EAP message to send * @return * - FAILED, if initiation failed * - NEED_MORE, if more EAP exchanges reqired */ status_t (*initiate) (eap_authenticator_t* this, eap_type_t type, - eap_payload_t **out); + u_int32_t vendor, eap_payload_t **out); /** * @brief Process an EAP message. diff --git a/src/charon/sa/child_sa.c b/src/charon/sa/child_sa.c index 44f0298d5..b6c71a8b5 100644 --- a/src/charon/sa/child_sa.c +++ b/src/charon/sa/child_sa.c @@ -354,7 +354,7 @@ static void updown(private_child_sa_t *this, bool up) up ? "up" : "down", policy->my_ts->is_host(policy->my_ts, this->me.addr) ? "-host" : "-client", - this->me.addr->get_family(this->me.addr) == AF_INET ? "" : "-ipv6", + this->me.addr->get_family(this->me.addr) == AF_INET ? "" : "-v6", this->config->get_name(this->config), this->iface ? this->iface : "unknown", this->reqid, diff --git a/src/charon/sa/connect_manager.c b/src/charon/sa/connect_manager.c index d583e01bb..d0f3cde8d 100644 --- a/src/charon/sa/connect_manager.c +++ b/src/charon/sa/connect_manager.c @@ -32,13 +32,13 @@ #include #include -// base timeout -// the sending interval is P2P_INTERVAL * active checklists (N) -// retransmission timeout is P2P_INTERVAL * N * checks in waiting state (NW) -#define P2P_INTERVAL 20 // 20 ms -// min retransmission timeout (RTO is P2P_INTERVAL * N * checks in waiting state) -#define P2P_RTO_MIN 100 // 100 ms -// max number of retransmissions (+ the initial check) +/* base timeout + * the sending interval is P2P_INTERVAL * active checklists (N) + * retransmission timeout is P2P_INTERVAL * N * checks in waiting state (NW) */ +#define P2P_INTERVAL 20 /* ms */ +/* min retransmission timeout (RTO is P2P_INTERVAL * N * checks in waiting state) */ +#define P2P_RTO_MIN 100 /* ms */ +/* max number of retransmissions (+ the initial check) */ #define P2P_MAX_RETRANS 2 @@ -212,7 +212,8 @@ static void check_list_destroy(check_list_t *this) DESTROY_OFFSET_IF(this->responder.endpoints, offsetof(endpoint_notify_t, destroy)); DESTROY_FUNCTION_IF(this->pairs, (void*)endpoint_pair_destroy); - DESTROY_IF(this->triggered); // this list contains some of the same elements as contained in this->pairs + /* this list contains some of the same elements as contained in this->pairs */ + DESTROY_IF(this->triggered); free(this); } @@ -489,8 +490,6 @@ static initiate_data_t *initiate_data_create(check_list_t *checklist, initiated_ return this; } -// ----------------------------------------------------------------------------- - /** * Find an initiated connection by the peers' ids */ @@ -641,9 +640,6 @@ static status_t endpoints_contain(linked_list_t *endpoints, host_t *host, endpoi return status; } -// ----------------------------------------------------------------------------- - - /** * Updates the state of the whole checklist */ @@ -659,7 +655,8 @@ static void update_checklist_state(check_list_t *checklist) switch(current->state) { case CHECK_WAITING: - // at least one is still waiting -> checklist remains in waiting state + /* at least one is still waiting -> checklist remains + * in waiting state */ iterator->destroy(iterator); return; case CHECK_IN_PROGRESS: @@ -668,6 +665,8 @@ static void update_checklist_state(check_list_t *checklist) case CHECK_SUCCEEDED: succeeded = TRUE; break; + default: + break; } } iterator->destroy(iterator); @@ -832,7 +831,6 @@ static void prune_pairs(linked_list_t *pairs) { iterator_t *iterator, *search; endpoint_pair_t *current, *other; - bool inserted = FALSE; u_int32_t id = 0; iterator = pairs->create_iterator(pairs, TRUE); @@ -851,10 +849,10 @@ static void prune_pairs(linked_list_t *pairs) if (current->local->equals(current->local, other->local) && current->remote->equals(current->remote, other->remote)) { - // since the list of pairs is sorted by priority in descending - // order, and we iterate the list from the beginning, we are - // sure that the priority of 'other' is lower than that of - // 'current', remove it + /* since the list of pairs is sorted by priority in descending + * order, and we iterate the list from the beginning, we are + * sure that the priority of 'other' is lower than that of + * 'current', remove it */ DBG1(DBG_IKE, "pruning endpoint pair %H - %H with priority %d", other->local, other->remote, other->priority); search->remove(search); @@ -896,8 +894,6 @@ static void build_pairs(check_list_t *checklist) prune_pairs(checklist->pairs); } -// ----------------------------------------------------------------------------- - /** * Processes the payloads of a connectivity check and returns the extracted data */ @@ -936,7 +932,7 @@ static status_t process_payloads(message_t *message, check_t *check) } check->endpoint = endpoint; check->endpoint_raw = chunk_clone(notify->get_notification_data(notify)); - DBG3(DBG_IKE, "received P2P_ENDPOINT notify"); + DBG2(DBG_IKE, "received P2P_ENDPOINT notify"); break; } case P2P_SESSIONID: @@ -1000,9 +996,6 @@ static chunk_t build_signature(private_connect_manager_t *this, return sig_hash; } -// ----------------------------------------------------------------------------- - -// forward declarations static void queue_retransmission(private_connect_manager_t *this, chunk_t session_id, u_int32_t mid); static void schedule_checks(private_connect_manager_t *this, check_list_t *checklist, u_int32_t time); static void finish_checks(private_connect_manager_t *this, check_list_t *checklist); @@ -1061,11 +1054,13 @@ retransmit_end: case CHECK_FAILED: finish_checks(this, checklist); break; + default: + break; } pthread_mutex_unlock(&(this->mutex)); - // we reschedule it manually + /* we reschedule it manually */ return JOB_REQUEUE_NONE; } @@ -1192,13 +1187,13 @@ static job_requeue_t sender(sender_data_t *data) check_destroy(check); - // schedule this job again + /* schedule this job again */ u_int32_t N = this->checklists->get_count(this->checklists); schedule_checks(this, checklist, P2P_INTERVAL * N); pthread_mutex_unlock(&(this->mutex)); - // we reschedule it manually + /* we reschedule it manually */ return JOB_REQUEUE_NONE; } @@ -1240,8 +1235,10 @@ static job_requeue_t initiate_mediated(initiate_data_t *data) } else { - // this should (can?) not happen + /* this should (can?) not happen */ } + + return JOB_REQUEUE_NONE; } /** @@ -1270,9 +1267,10 @@ static void finish_checks(private_connect_manager_t *this, check_list_t *checkli } } - //remove_checklist(this, checklist); - //check_list_destroy(checklist); - // FIXME: we should do this ^^^ after a specific timeout on the responder side + /* remove_checklist(this, checklist); + * check_list_destroy(checklist); + * FIXME: we should do this ^^^ after a specific timeout on the + * responder side */ } /** @@ -1313,6 +1311,8 @@ static void process_response(private_connect_manager_t *this, check_t *check, case CHECK_FAILED: finish_checks(this, checklist); break; + default: + break; } } else @@ -1343,16 +1343,16 @@ static void process_request(private_connect_manager_t *this, check_t *check, switch(pair->state) { case CHECK_IN_PROGRESS: - pair->retransmitted = P2P_MAX_RETRANS; // prevent retransmissions - // FIXME: we should wait to the next rto to send the triggered check - // fall-through + /* prevent retransmissions */ + pair->retransmitted = P2P_MAX_RETRANS; + /* FIXME: we should wait to the next rto to send the triggered check + * fall-through */ case CHECK_WAITING: case CHECK_FAILED: queue_triggered_check(checklist, pair); break; case CHECK_SUCCEEDED: default: - // do nothing break; } } @@ -1451,8 +1451,6 @@ static void process_check(private_connect_manager_t *this, message_t *message) check_destroy(check); } -// ----------------------------------------------------------------------------- - /** * Implementation of connect_manager_t.check_and_register. */ @@ -1568,7 +1566,8 @@ static status_t set_responder_data(private_connect_manager_t *this, build_pairs(checklist); - schedule_checks(this, checklist, 0); // send the first check immediately + /* send the first check immediately */ + schedule_checks(this, checklist, 0); pthread_mutex_unlock(&(this->mutex)); diff --git a/src/charon/sa/ike_sa.c b/src/charon/sa/ike_sa.c index 9d7a17e89..9cada2cb5 100644 --- a/src/charon/sa/ike_sa.c +++ b/src/charon/sa/ike_sa.c @@ -51,6 +51,7 @@ #include #include #include +#include #include #include #include @@ -68,6 +69,7 @@ #ifdef P2P #include +#include #endif #ifndef RESOLV_CONF @@ -248,6 +250,8 @@ struct private_ike_sa_t { u_int32_t established; /** when IKE_SA gets rekeyed */ u_int32_t rekey; + /** when IKE_SA gets reauthenticated */ + u_int32_t reauth; /** when IKE_SA gets deleted */ u_int32_t delete; } time; @@ -256,6 +260,11 @@ struct private_ike_sa_t { * how many times we have retried so far (keyingtries) */ u_int32_t keyingtry; + + /** + * are we the initiator of this IKE_SA (rekeying does not affect this flag) + */ + bool ike_initiator; }; /** @@ -307,16 +316,31 @@ static char *get_name(private_ike_sa_t *this) return "(unnamed)"; } - /** - * Implementation of ike_sa_t.get_stats. + * Implementation of ike_sa_t.get_statistic. */ -static void get_stats(private_ike_sa_t *this, u_int32_t *next_rekeying) +static u_int32_t get_statistic(private_ike_sa_t *this, statistic_t kind) { - if (next_rekeying) + time_t now = time(NULL); + + switch (kind) { - *next_rekeying = this->time.rekey; + case STAT_REKEY_TIME: + if (this->time.rekey > now) + { + return this->time.rekey - now; + } + break; + case STAT_REAUTH_TIME: + if (this->time.reauth > now) + { + return this->time.reauth - now; + } + break; + default: + break; } + return 0; } /** @@ -493,10 +517,6 @@ static void set_condition(private_ike_sa_t *this, ike_condition_t condition, this->conditions |= condition; switch (condition) { - case COND_STALE: - DBG1(DBG_IKE, "no route to %H, setting IKE_SA to stale", - this->other_host); - break; case COND_NAT_HERE: DBG1(DBG_IKE, "local host is behind NAT, sending keep alives"); this->conditions |= COND_NAT_ANY; @@ -519,9 +539,6 @@ static void set_condition(private_ike_sa_t *this, ike_condition_t condition, this->conditions &= ~condition; switch (condition) { - case COND_STALE: - DBG1(DBG_IKE, "new route to %H found", this->other_host); - break; case COND_NAT_HERE: case COND_NAT_FAKE: case COND_NAT_THERE: @@ -610,36 +627,58 @@ static void set_state(private_ike_sa_t *this, ike_sa_state_t state) if (this->state == IKE_CONNECTING) { job_t *job; - u_int32_t now = time(NULL); - u_int32_t soft, hard; - bool reauth; + u_int32_t t; - this->time.established = now; - /* start DPD checks */ - send_dpd(this); + /* calculate rekey, reauth and lifetime */ + this->time.established = time(NULL); - /* schedule rekeying/reauthentication */ - soft = this->peer_cfg->get_lifetime(this->peer_cfg, TRUE); - hard = this->peer_cfg->get_lifetime(this->peer_cfg, FALSE); - reauth = this->peer_cfg->use_reauth(this->peer_cfg); - DBG1(DBG_IKE, "scheduling %s in %ds, maximum lifetime %ds", - reauth ? "reauthentication": "rekeying", soft, hard); - - if (soft) + /* schedule rekeying if we have a time which is smaller than + * an already scheduled rekeying */ + t = this->peer_cfg->get_rekey_time(this->peer_cfg); + if (t && (this->time.rekey == 0 || + (this->time.rekey > t + this->time.established))) { - this->time.rekey = now + soft; - job = (job_t*)rekey_ike_sa_job_create(this->ike_sa_id, reauth); - charon->scheduler->schedule_job(charon->scheduler, job, - soft * 1000); + this->time.rekey = t + this->time.established; + job = (job_t*)rekey_ike_sa_job_create(this->ike_sa_id, FALSE); + charon->scheduler->schedule_job(charon->scheduler, + job, t * 1000); + DBG1(DBG_IKE, "scheduling rekeying in %ds", t); } - - if (hard) + t = this->peer_cfg->get_reauth_time(this->peer_cfg); + if (t && (this->time.reauth == 0 || + (this->time.reauth > t + this->time.established))) { - this->time.delete = now + hard; + this->time.reauth = t + this->time.established; + job = (job_t*)rekey_ike_sa_job_create(this->ike_sa_id, TRUE); + charon->scheduler->schedule_job(charon->scheduler, + job, t * 1000); + DBG1(DBG_IKE, "scheduling reauthentication in %ds", t); + } + t = this->peer_cfg->get_over_time(this->peer_cfg); + if (this->time.rekey || this->time.reauth) + { + if (this->time.reauth == 0) + { + this->time.delete = this->time.rekey; + } + else if (this->time.rekey == 0) + { + this->time.delete = this->time.reauth; + } + else + { + this->time.delete = min(this->time.rekey, this->time.reauth); + } + this->time.delete += t; + t = this->time.delete - this->time.established; job = (job_t*)delete_ike_sa_job_create(this->ike_sa_id, TRUE); charon->scheduler->schedule_job(charon->scheduler, job, - hard * 1000); + t * 1000); + DBG1(DBG_IKE, "maximum IKE_SA lifetime %ds", t); } + + /* start DPD checks */ + send_dpd(this); } break; } @@ -681,17 +720,17 @@ static void set_virtual_ip(private_ike_sa_t *this, bool local, host_t *ip) { if (local) { - if (this->my_virtual_ip) - { - DBG1(DBG_IKE, "removing old virtual IP %H", this->my_virtual_ip); - charon->kernel_interface->del_ip(charon->kernel_interface, - this->my_virtual_ip); - this->my_virtual_ip->destroy(this->my_virtual_ip); - } DBG1(DBG_IKE, "installing new virtual IP %H", ip); if (charon->kernel_interface->add_ip(charon->kernel_interface, ip, this->my_host) == SUCCESS) { + if (this->my_virtual_ip) + { + DBG1(DBG_IKE, "removing old virtual IP %H", this->my_virtual_ip); + charon->kernel_interface->del_ip(charon->kernel_interface, + this->my_virtual_ip); + } + DESTROY_IF(this->my_virtual_ip); this->my_virtual_ip = ip->clone(ip); } else @@ -859,6 +898,8 @@ static void send_notify_response(private_ike_sa_t *this, message_t *request, this->other_host = request->get_source(request); this->other_host = this->other_host->clone(this->other_host); } + response->set_source(response, this->my_host->clone(this->my_host)); + response->set_destination(response, this->other_host->clone(this->other_host)); if (generate_message(this, response, &packet) == SUCCESS) { charon->sender->send(charon->sender, packet); @@ -973,6 +1014,8 @@ static status_t initiate(private_ike_sa_t *this, child_cfg_t *child_cfg) return DESTROY_ME; } + this->ike_initiator = TRUE; + task = (task_t*)ike_init_create(&this->public, TRUE, NULL); this->task_manager->queue_task(this->task_manager, task); task = (task_t*)ike_natd_create(&this->public, TRUE); @@ -983,6 +1026,8 @@ static status_t initiate(private_ike_sa_t *this, child_cfg_t *child_cfg) this->task_manager->queue_task(this->task_manager, task); task = (task_t*)ike_config_create(&this->public, TRUE); this->task_manager->queue_task(this->task_manager, task); + task = (task_t*)ike_auth_lifetime_create(&this->public, TRUE); + this->task_manager->queue_task(this->task_manager, task); if (this->peer_cfg->use_mobike(this->peer_cfg)) { task = (task_t*)ike_mobike_create(&this->public, TRUE); @@ -997,7 +1042,7 @@ static status_t initiate(private_ike_sa_t *this, child_cfg_t *child_cfg) #ifdef P2P if (this->peer_cfg->get_mediated_by(this->peer_cfg)) { - // mediated connection, initiate mediation process + /* mediated connection, initiate mediation process */ job_t *job = (job_t*)initiate_mediation_job_create(this->ike_sa_id, child_cfg); child_cfg->destroy(child_cfg); charon->processor->queue_job(charon->processor, job); @@ -1006,14 +1051,14 @@ static status_t initiate(private_ike_sa_t *this, child_cfg_t *child_cfg) else if (this->peer_cfg->is_mediation(this->peer_cfg)) { if (this->state == IKE_ESTABLISHED) - {// FIXME: we should try to find a better solution to this + { /* FIXME: we should try to find a better solution to this */ SIG(CHILD_UP_SUCCESS, "mediation connection is already up and running"); } } else #endif /* P2P */ { - // normal IKE_SA with CHILD_SA + /* normal IKE_SA with CHILD_SA */ task = (task_t*)child_create_create(&this->public, child_cfg); child_cfg->destroy(child_cfg); this->task_manager->queue_task(this->task_manager, task); @@ -1026,7 +1071,7 @@ static status_t initiate(private_ike_sa_t *this, child_cfg_t *child_cfg) * Implementation of ike_sa_t.acquire. */ static status_t acquire(private_ike_sa_t *this, u_int32_t reqid) -{// FIXME: P2P-NAT-T +{ /* FIXME: P2P-NAT-T */ child_cfg_t *child_cfg; iterator_t *iterator; child_sa_t *current, *child_sa = NULL; @@ -1073,6 +1118,8 @@ static status_t acquire(private_ike_sa_t *this, u_int32_t reqid) this->task_manager->queue_task(this->task_manager, task); task = (task_t*)ike_config_create(&this->public, TRUE); this->task_manager->queue_task(this->task_manager, task); + task = (task_t*)ike_auth_lifetime_create(&this->public, TRUE); + this->task_manager->queue_task(this->task_manager, task); if (this->peer_cfg->use_mobike(this->peer_cfg)) { task = (task_t*)ike_mobike_create(&this->public, TRUE); @@ -1350,7 +1397,7 @@ static status_t process_message(private_ike_sa_t *this, message_t *message) * Implementation of ike_sa_t.retransmit. */ static status_t retransmit(private_ike_sa_t *this, u_int32_t message_id) -{// FIXME: P2P-NAT-T +{ /* FIXME: P2P-NAT-T */ this->time.outbound = time(NULL); if (this->task_manager->retransmit(this->task_manager, message_id) != SUCCESS) { @@ -1467,6 +1514,8 @@ static status_t retransmit(private_ike_sa_t *this, u_int32_t message_id) task = (task_t*)child_create_create(&new->public, child_cfg); new->task_manager->queue_task(new->task_manager, task); } + task = (task_t*)ike_auth_lifetime_create(&new->public, TRUE); + new->task_manager->queue_task(new->task_manager, task); if (this->peer_cfg->use_mobike(this->peer_cfg)) { task = (task_t*)ike_mobike_create(&new->public, TRUE); @@ -1900,13 +1949,58 @@ static status_t rekey(private_ike_sa_t *this) static status_t reestablish(private_ike_sa_t *this) { task_t *task; - + + /* we can't reauthenticate as responder when we use EAP or virtual IPs. + * If the peer does not support RFC4478, there is no way to keep the + * IKE_SA up. */ + if (!this->ike_initiator) + { + DBG1(DBG_IKE, "initiator did not reauthenticate as requested"); + if (this->other_virtual_ip != NULL || + has_condition(this, COND_EAP_AUTHENTICATED)) + { + time_t now = time(NULL); + + DBG1(DBG_IKE, "IKE_SA will timeout in %#V", &now, &this->time.delete); + return FAILED; + } + else + { + DBG1(DBG_IKE, "reauthenticating actively"); + } + } task = (task_t*)ike_reauth_create(&this->public); this->task_manager->queue_task(this->task_manager, task); - + return this->task_manager->initiate(this->task_manager); } +/** + * Implementation of ike_sa_t.set_auth_lifetime. + */ +static void set_auth_lifetime(private_ike_sa_t *this, u_int32_t lifetime) +{ + job_t *job; + u_int32_t reduction = this->peer_cfg->get_over_time(this->peer_cfg); + + this->time.reauth = time(NULL) + lifetime - reduction; + job = (job_t*)rekey_ike_sa_job_create(this->ike_sa_id, TRUE); + + if (lifetime < reduction) + { + DBG1(DBG_IKE, "received AUTH_LIFETIME of %ds, starting reauthentication", + lifetime); + charon->processor->queue_job(charon->processor, job); + } + else + { + DBG1(DBG_IKE, "received AUTH_LIFETIME of %ds, scheduling reauthentication" + " in %ds", lifetime, lifetime - reduction); + charon->scheduler->schedule_job(charon->scheduler, job, + (lifetime - reduction) * 1000); + } +} + /** * Implementation of ike_sa_t.roam. */ @@ -1933,7 +2027,6 @@ static status_t roam(private_ike_sa_t *this, bool address) me = charon->kernel_interface->get_source_addr(charon->kernel_interface, other); - set_condition(this, COND_STALE, FALSE); if (me) { if (me->ip_equals(me, this->my_host) && @@ -1977,6 +2070,7 @@ static status_t inherit(private_ike_sa_t *this, private_ike_sa_t *other) this->other_host = other->other_host->clone(other->other_host); this->my_id = other->my_id->clone(other->my_id); this->other_id = other->other_id->clone(other->other_id); + this->ike_initiator = other->ike_initiator; /* apply virtual assigned IPs... */ if (other->my_virtual_ip) @@ -2007,6 +2101,24 @@ static status_t inherit(private_ike_sa_t *this, private_ike_sa_t *other) /* move pending tasks to the new IKE_SA */ this->task_manager->adopt_tasks(this->task_manager, other->task_manager); + /* reauthentication timeout survives a rekeying */ + if (other->time.reauth) + { + time_t reauth, delete, now = time(NULL); + + this->time.reauth = other->time.reauth; + reauth = this->time.reauth - now; + delete = reauth + this->peer_cfg->get_over_time(this->peer_cfg); + this->time.delete = this->time.reauth + delete; + DBG1(DBG_IKE, "rescheduling reauthentication in %ds after rekeying, " + "lifetime reduced to %ds", reauth, delete); + charon->scheduler->schedule_job(charon->scheduler, + (job_t*)rekey_ike_sa_job_create(this->ike_sa_id, TRUE), + reauth * 1000); + charon->scheduler->schedule_job(charon->scheduler, + (job_t*)delete_ike_sa_job_create(this->ike_sa_id, TRUE), + delete * 1000); + } /* we have to initate here, there may be new tasks to handle */ return this->task_manager->initiate(this->task_manager); } @@ -2177,7 +2289,7 @@ static void destroy(private_ike_sa_t *this) if (this->peer_cfg && this->peer_cfg->is_mediation(this->peer_cfg) && !this->ike_sa_id->is_initiator(this->ike_sa_id)) { - // mediation server + /* mediation server */ charon->mediation_manager->remove(charon->mediation_manager, this->ike_sa_id); } DESTROY_IF(this->server_reflexive_host); @@ -2207,8 +2319,8 @@ ike_sa_t * ike_sa_create(ike_sa_id_t *ike_sa_id) /* Public functions */ this->public.get_state = (ike_sa_state_t (*)(ike_sa_t*)) get_state; this->public.set_state = (void (*)(ike_sa_t*,ike_sa_state_t)) set_state; - this->public.get_stats = (void (*)(ike_sa_t*,u_int32_t*))get_stats; this->public.get_name = (char* (*)(ike_sa_t*))get_name; + this->public.get_statistic = (u_int32_t(*)(ike_sa_t*, statistic_t kind))get_statistic; this->public.process_message = (status_t (*)(ike_sa_t*, message_t*)) process_message; this->public.initiate = (status_t (*)(ike_sa_t*,child_cfg_t*)) initiate; this->public.route = (status_t (*)(ike_sa_t*,child_cfg_t*)) route; @@ -2256,6 +2368,7 @@ ike_sa_t * ike_sa_create(ike_sa_id_t *ike_sa_id) this->public.destroy_child_sa = (status_t (*)(ike_sa_t*,protocol_id_t,u_int32_t))destroy_child_sa; this->public.rekey = (status_t (*)(ike_sa_t*))rekey; this->public.reestablish = (status_t (*)(ike_sa_t*))reestablish; + this->public.set_auth_lifetime = (void(*)(ike_sa_t*, u_int32_t lifetime))set_auth_lifetime; this->public.roam = (status_t(*)(ike_sa_t*,bool))roam; this->public.inherit = (status_t (*)(ike_sa_t*,ike_sa_t*))inherit; this->public.generate_message = (status_t (*)(ike_sa_t*,message_t*,packet_t**))generate_message; @@ -2296,6 +2409,7 @@ ike_sa_t * ike_sa_create(ike_sa_id_t *ike_sa_id) this->time.inbound = this->time.outbound = time(NULL); this->time.established = 0; this->time.rekey = 0; + this->time.reauth = 0; this->time.delete = 0; this->ike_cfg = NULL; this->peer_cfg = NULL; @@ -2307,6 +2421,7 @@ ike_sa_t * ike_sa_create(ike_sa_id_t *ike_sa_id) this->additional_addresses = linked_list_create(); this->pending_updates = 0; this->keyingtry = 0; + this->ike_initiator = FALSE; #ifdef P2P this->server_reflexive_host = NULL; #endif /* P2P */ diff --git a/src/charon/sa/ike_sa.h b/src/charon/sa/ike_sa.h index 99f09e98a..975447d9c 100644 --- a/src/charon/sa/ike_sa.h +++ b/src/charon/sa/ike_sa.h @@ -29,6 +29,7 @@ typedef enum ike_extension_t ike_extension_t; typedef enum ike_condition_t ike_condition_t; typedef enum ike_sa_state_t ike_sa_state_t; +typedef enum statistic_t statistic_t; typedef struct ike_sa_t ike_sa_t; #include @@ -115,9 +116,25 @@ enum ike_condition_t { COND_NAT_FAKE = (1<<3), /** - * peer is currently not reachable (due missing route, ...) + * peer has ben authenticated using EAP */ - COND_STALE = (1<<4), + COND_EAP_AUTHENTICATED = (1<<4), +}; + +/** + * Information and statistics to query from an SA + */ +enum statistic_t { + + /** + * Relative time for scheduled rekeying + */ + STAT_REKEY_TIME, + + /** + * Relative time for scheduled reauthentication + */ + STAT_REAUTH_TIME, }; /** @@ -233,13 +250,6 @@ struct ike_sa_t { */ ike_sa_state_t (*get_state) (ike_sa_t *this); - /** - * @brief Get some statistics about this IKE_SA. - * - * @param next_rekeying when the next rekeying is scheduled - */ - void (*get_stats)(ike_sa_t *this, u_int32_t *next_rekeying); - /** * @brief Set the state of the IKE_SA. * @@ -256,6 +266,15 @@ struct ike_sa_t { */ char* (*get_name) (ike_sa_t *this); + /** + * @brief Get statistic values from the IKE_SA. + * + * @param this calling object + * @param kind kind of requested value + * @return value as integer + */ + u_int32_t (*get_statistic)(ike_sa_t *this, statistic_t kind); + /** * @brief Get the own host address. * @@ -845,6 +864,14 @@ struct ike_sa_t { */ status_t (*reestablish) (ike_sa_t *this); + /** + * @brief Set the lifetime limit received from a AUTH_LIFETIME notify. + * + * @param this calling object + * @param lifetime lifetime in seconds + */ + void (*set_auth_lifetime)(ike_sa_t *this, u_int32_t lifetime); + /** * @brief Set the virtual IP to use for this IKE_SA and its children. * diff --git a/src/charon/sa/mediation_manager.c b/src/charon/sa/mediation_manager.c index fca53a940..f6137304d 100644 --- a/src/charon/sa/mediation_manager.c +++ b/src/charon/sa/mediation_manager.c @@ -240,7 +240,7 @@ static void update_sa_id(private_mediation_manager_t *this, identification_t *pe DBG2(DBG_IKE, "changing registered IKE_SA ID of peer '%D'", peer_id); peer->ike_sa_id = ike_sa_id ? ike_sa_id->clone(ike_sa_id) : NULL; - // send callbacks to registered peers + /* send callbacks to registered peers */ identification_t *requester; while(peer->requested_by->remove_last(peer->requested_by, (void**)&requester) == SUCCESS) { @@ -295,7 +295,7 @@ static ike_sa_id_t *check_and_register(private_mediation_manager_t *this, if (!peer->ike_sa_id) { - // the peer is not online + /* the peer is not online */ DBG2(DBG_IKE, "requested peer '%D' is offline, registering peer '%D'", peer_id, requester); register_peer(peer, requester); pthread_mutex_unlock(&(this->mutex)); diff --git a/src/charon/sa/task_manager.c b/src/charon/sa/task_manager.c index f4484774e..89f527aba 100644 --- a/src/charon/sa/task_manager.c +++ b/src/charon/sa/task_manager.c @@ -30,6 +30,7 @@ #include #include #include +#include #include #include #include @@ -338,6 +339,7 @@ static status_t build_request(private_task_manager_t *this) activate_task(this, IKE_AUTHENTICATE); activate_task(this, IKE_CONFIG); activate_task(this, CHILD_CREATE); + activate_task(this, IKE_AUTH_LIFETIME); activate_task(this, IKE_MOBIKE); } break; @@ -690,19 +692,21 @@ static status_t process_request(private_task_manager_t *this, #ifdef P2P task = (task_t*)ike_p2p_create(this->ike_sa, FALSE); this->passive_tasks->insert_last(this->passive_tasks, task); -#endif /* P2P */ +#endif /* P2P */ task = (task_t*)ike_auth_create(this->ike_sa, FALSE); this->passive_tasks->insert_last(this->passive_tasks, task); task = (task_t*)ike_config_create(this->ike_sa, FALSE); this->passive_tasks->insert_last(this->passive_tasks, task); task = (task_t*)child_create_create(this->ike_sa, NULL); this->passive_tasks->insert_last(this->passive_tasks, task); + task = (task_t*)ike_auth_lifetime_create(this->ike_sa, FALSE); + this->passive_tasks->insert_last(this->passive_tasks, task); task = (task_t*)ike_mobike_create(this->ike_sa, FALSE); this->passive_tasks->insert_last(this->passive_tasks, task); break; } case CREATE_CHILD_SA: - {//FIXME: we should prevent this on mediation connections + { /* FIXME: we should prevent this on mediation connections */ bool notify_found = FALSE, ts_found = FALSE; iterator = message->get_payload_iterator(message); while (iterator->iterate(iterator, (void**)&payload)) @@ -772,8 +776,12 @@ static status_t process_request(private_task_manager_t *this, case UNACCEPTABLE_ADDRESSES: case UNEXPECTED_NAT_DETECTED: case COOKIE2: - task = (task_t*)ike_mobike_create(this->ike_sa, - FALSE); + task = (task_t*)ike_mobike_create( + this->ike_sa, FALSE); + break; + case AUTH_LIFETIME: + task = (task_t*)ike_auth_lifetime_create( + this->ike_sa, FALSE); break; default: break; diff --git a/src/charon/sa/tasks/ike_auth.c b/src/charon/sa/tasks/ike_auth.c index a3cd6a2bc..de88a0abe 100644 --- a/src/charon/sa/tasks/ike_auth.c +++ b/src/charon/sa/tasks/ike_auth.c @@ -297,6 +297,7 @@ static status_t collect_other_init_data(private_ike_auth_t *this, message_t *mes return NEED_MORE; } + /** * Implementation of task_t.build to create AUTH payload from EAP data */ @@ -520,6 +521,7 @@ static status_t process_r(private_ike_auth_t *this, message_t *message) break; case NOT_FOUND: /* use EAP if no AUTH payload found */ + this->ike_sa->set_condition(this->ike_sa, COND_EAP_AUTHENTICATED, TRUE); this->eap_auth = eap_authenticator_create(this->ike_sa); break; default: @@ -546,6 +548,7 @@ static status_t build_r(private_ike_auth_t *this, message_t *message) { peer_cfg_t *config; eap_type_t eap_type; + u_int32_t eap_vendor; eap_payload_t *eap_payload; status_t status; @@ -590,10 +593,11 @@ static status_t build_r(private_ike_auth_t *this, message_t *message) message->add_notify(message, TRUE, AUTHENTICATION_FAILED, chunk_empty); return FAILED; } - + /* initiate EAP authenitcation */ - eap_type = config->get_eap_type(config); - status = this->eap_auth->initiate(this->eap_auth, eap_type, &eap_payload); + eap_type = config->get_eap_type(config, &eap_vendor); + status = this->eap_auth->initiate(this->eap_auth, eap_type, + eap_vendor, &eap_payload); message->add_payload(message, (payload_t*)eap_payload); if (status != NEED_MORE) { @@ -645,6 +649,12 @@ static status_t process_i(private_ike_auth_t *this, message_t *message) case ADDITIONAL_IP6_ADDRESS: /* handled in ike_mobike task */ break; + case AUTH_LIFETIME: + /* handled in ike_auth_lifetime task */ + break; + case P2P_ENDPOINT: + /* handled in ike_p2p task */ + break; default: { if (type < 16383) diff --git a/src/charon/sa/tasks/ike_auth_lifetime.c b/src/charon/sa/tasks/ike_auth_lifetime.c new file mode 100644 index 000000000..9d37ec608 --- /dev/null +++ b/src/charon/sa/tasks/ike_auth_lifetime.c @@ -0,0 +1,200 @@ +/** + * @file ike_auth_lifetime.c + * + * @brief Implementation of the ike_auth_lifetime task. + * + */ + +/* + * Copyright (C) 2007 Martin Willi + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#include "ike_auth_lifetime.h" + +#include +#include + + +typedef struct private_ike_auth_lifetime_t private_ike_auth_lifetime_t; + +/** + * Private members of a ike_auth_lifetime_t task. + */ +struct private_ike_auth_lifetime_t { + + /** + * Public methods and task_t interface. + */ + ike_auth_lifetime_t public; + + /** + * Assigned IKE_SA. + */ + ike_sa_t *ike_sa; +}; + +/** + * add the AUTH_LIFETIME notify to the message + */ +static void add_auth_lifetime(private_ike_auth_lifetime_t *this, message_t *message) +{ + chunk_t chunk; + u_int32_t lifetime; + + lifetime = this->ike_sa->get_statistic(this->ike_sa, STAT_REAUTH_TIME); + if (lifetime) + { + chunk = chunk_from_thing(lifetime); + *(u_int32_t*)chunk.ptr = htonl(lifetime); + message->add_notify(message, FALSE, AUTH_LIFETIME, chunk); + } +} + +/** + * read notifys from message and evaluate them + */ +static void process_payloads(private_ike_auth_lifetime_t *this, message_t *message) +{ + iterator_t *iterator; + payload_t *payload; + notify_payload_t *notify; + + iterator = message->get_payload_iterator(message); + while (iterator->iterate(iterator, (void**)&payload)) + { + if (payload->get_type(payload) == NOTIFY) + { + notify = (notify_payload_t*)payload; + switch (notify->get_notify_type(notify)) + { + case AUTH_LIFETIME: + { + chunk_t data = notify->get_notification_data(notify); + u_int32_t lifetime = ntohl(*(u_int32_t*)data.ptr); + this->ike_sa->set_auth_lifetime(this->ike_sa, lifetime); + break; + } + default: + break; + } + } + } + iterator->destroy(iterator); +} + +/** + * Implementation of task_t.process for initiator + */ +static status_t build_i(private_ike_auth_lifetime_t *this, message_t *message) +{ + if (message->get_exchange_type(message) == INFORMATIONAL) + { + add_auth_lifetime(this, message); + return SUCCESS; + } + return NEED_MORE; +} + +/** + * Implementation of task_t.process for responder + */ +static status_t process_r(private_ike_auth_lifetime_t *this, message_t *message) +{ + if (message->get_exchange_type(message) == INFORMATIONAL) + { + process_payloads(this, message); + return SUCCESS; + } + return NEED_MORE; +} + +/** + * Implementation of task_t.build for responder + */ +static status_t build_r(private_ike_auth_lifetime_t *this, message_t *message) +{ + if (message->get_exchange_type(message) == IKE_AUTH && + this->ike_sa->get_state(this->ike_sa) == IKE_ESTABLISHED) + { + add_auth_lifetime(this, message); + return SUCCESS; + } + return NEED_MORE; +} + +/** + * Implementation of task_t.process for initiator + */ +static status_t process_i(private_ike_auth_lifetime_t *this, message_t *message) +{ + if (message->get_exchange_type(message) == IKE_AUTH && + this->ike_sa->get_state(this->ike_sa) == IKE_ESTABLISHED) + { + process_payloads(this, message); + return SUCCESS; + } + return NEED_MORE; +} + +/** + * Implementation of task_t.get_type + */ +static task_type_t get_type(private_ike_auth_lifetime_t *this) +{ + return IKE_AUTH_LIFETIME; +} + +/** + * Implementation of task_t.migrate + */ +static void migrate(private_ike_auth_lifetime_t *this, ike_sa_t *ike_sa) +{ + this->ike_sa = ike_sa; +} + +/** + * Implementation of task_t.destroy + */ +static void destroy(private_ike_auth_lifetime_t *this) +{ + free(this); +} + +/* + * Described in header. + */ +ike_auth_lifetime_t *ike_auth_lifetime_create(ike_sa_t *ike_sa, bool initiator) +{ + private_ike_auth_lifetime_t *this = malloc_thing(private_ike_auth_lifetime_t); + + this->public.task.get_type = (task_type_t(*)(task_t*))get_type; + this->public.task.migrate = (void(*)(task_t*,ike_sa_t*))migrate; + this->public.task.destroy = (void(*)(task_t*))destroy; + + if (initiator) + { + this->public.task.build = (status_t(*)(task_t*,message_t*))build_i; + this->public.task.process = (status_t(*)(task_t*,message_t*))process_i; + } + else + { + this->public.task.build = (status_t(*)(task_t*,message_t*))build_r; + this->public.task.process = (status_t(*)(task_t*,message_t*))process_r; + } + + this->ike_sa = ike_sa; + + return &this->public; +} + diff --git a/src/charon/sa/tasks/ike_auth_lifetime.h b/src/charon/sa/tasks/ike_auth_lifetime.h new file mode 100644 index 000000000..500b89d39 --- /dev/null +++ b/src/charon/sa/tasks/ike_auth_lifetime.h @@ -0,0 +1,61 @@ +/** + * @file ike_auth_lifetime.h + * + * @brief Interface ike_auth_lifetime_t. + * + */ + +/* + * Copyright (C) 2007 Martin Willi + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#ifndef IKE_AUTH_LIFETIME_H_ +#define IKE_AUTH_LIFETIME_H_ + +typedef struct ike_auth_lifetime_t ike_auth_lifetime_t; + +#include +#include +#include + +/** + * @brief Task of type IKE_AUTH_LIFETIME, implements RFC4478. + * + * This task exchanges lifetimes for IKE_AUTH to force a client to + * reauthenticate before the responders lifetime reaches the limit. + * + * @b Constructors: + * - ike_auth_lifetime_create() + * + * @ingroup tasks + */ +struct ike_auth_lifetime_t { + + /** + * Implements the task_t interface + */ + task_t task; +}; + +/** + * @brief Create a new IKE_AUTH_LIFETIME task. + * + * @param ike_sa IKE_SA this task works for + * @param initiator TRUE if taks is initiated by us + * @return ike_auth_lifetime task to handle by the task_manager + */ +ike_auth_lifetime_t *ike_auth_lifetime_create(ike_sa_t *ike_sa, bool initiator); + +#endif /* IKE_MOBIKE_H_ */ + diff --git a/src/charon/sa/tasks/ike_mobike.c b/src/charon/sa/tasks/ike_mobike.c index d1fc8c695..a53c243f0 100644 --- a/src/charon/sa/tasks/ike_mobike.c +++ b/src/charon/sa/tasks/ike_mobike.c @@ -287,7 +287,7 @@ static void transmit(private_ike_mobike_t *this, packet_t *packet) static status_t build_i(private_ike_mobike_t *this, message_t *message) { if (message->get_exchange_type(message) == IKE_AUTH && - message->get_payload(message, SECURITY_ASSOCIATION)) + message->get_payload(message, ID_INITIATOR)) { message->add_notify(message, FALSE, MOBIKE_SUPPORTED, chunk_empty); build_address_list(this, message); @@ -317,7 +317,7 @@ static status_t build_i(private_ike_mobike_t *this, message_t *message) static status_t process_r(private_ike_mobike_t *this, message_t *message) { if (message->get_exchange_type(message) == IKE_AUTH && - message->get_payload(message, SECURITY_ASSOCIATION)) + message->get_payload(message, ID_INITIATOR)) { process_payloads(this, message); } @@ -348,7 +348,7 @@ static status_t process_r(private_ike_mobike_t *this, message_t *message) static status_t build_r(private_ike_mobike_t *this, message_t *message) { if (message->get_exchange_type(message) == IKE_AUTH && - message->get_payload(message, SECURITY_ASSOCIATION)) + this->ike_sa->get_state(this->ike_sa) == IKE_ESTABLISHED) { if (this->ike_sa->supports_extension(this->ike_sa, EXT_MOBIKE)) { @@ -378,7 +378,7 @@ static status_t build_r(private_ike_mobike_t *this, message_t *message) static status_t process_i(private_ike_mobike_t *this, message_t *message) { if (message->get_exchange_type(message) == IKE_AUTH && - message->get_payload(message, SECURITY_ASSOCIATION)) + this->ike_sa->get_state(this->ike_sa) == IKE_ESTABLISHED) { process_payloads(this, message); return SUCCESS; diff --git a/src/charon/sa/tasks/ike_p2p.c b/src/charon/sa/tasks/ike_p2p.c index de5a2e30e..84b88e16b 100644 --- a/src/charon/sa/tasks/ike_p2p.c +++ b/src/charon/sa/tasks/ike_p2p.c @@ -34,7 +34,7 @@ #define P2P_SESSIONID_LEN 8 #define P2P_SESSIONKEY_LEN 16 -// FIXME: proposed values +/* FIXME: proposed values */ #define P2P_SESSIONID_MIN_LEN 4 #define P2P_SESSIONID_MAX_LEN 16 #define P2P_SESSIONKEY_MIN_LEN 8 @@ -119,8 +119,6 @@ struct private_ike_p2p_t { }; -// ----------------------------------------------------------------------------- - /** * Adds a list of endpoints as notifies to a given message */ @@ -146,7 +144,7 @@ static void gather_and_add_endpoints(private_ike_p2p_t *this, message_t *message host_t *addr, *host; u_int16_t port; - // get the port that is used to communicate with the ms + /* get the port that is used to communicate with the ms */ host = this->ike_sa->get_my_host(this->ike_sa); port = host->get_port(host); @@ -215,7 +213,8 @@ static void process_payloads(private_ike_p2p_t *this, message_t *message) DBG1(DBG_IKE, "received invalid P2P_ENDPOINT notify"); break; } - DBG2(DBG_IKE, "received P2P_ENDPOINT notify"); + DBG1(DBG_IKE, "received %N P2P_ENDPOINT %#H", p2p_endpoint_type_names, + endpoint->get_type(endpoint), endpoint->get_host(endpoint)); this->remote_endpoints->insert_last(this->remote_endpoints, endpoint); break; @@ -253,8 +252,6 @@ static void process_payloads(private_ike_p2p_t *this, message_t *message) iterator->destroy(iterator); } -// ----------------------------------------------------------------------------- - /** * Implementation of task_t.process for initiator */ @@ -296,8 +293,8 @@ static status_t build_i(private_ike_p2p_t *this, message_t *message) if (!this->response) { - // only the initiator creates a session ID. the responder returns - // the session ID that it received from the initiator + /* only the initiator creates a session ID. the responder returns + * the session ID that it received from the initiator */ if (rand->allocate_pseudo_random_bytes(rand, P2P_SESSIONID_LEN, &this->session_id) != SUCCESS) { @@ -326,7 +323,7 @@ static status_t build_i(private_ike_p2p_t *this, message_t *message) } else { - // FIXME: should we make that configurable + /* FIXME: should we make that configurable */ message->add_notify(message, FALSE, P2P_CALLBACK, chunk_empty); } @@ -334,8 +331,9 @@ static status_t build_i(private_ike_p2p_t *this, message_t *message) break; } + default: + break; } - return NEED_MORE; } @@ -387,11 +385,11 @@ static status_t process_r(private_ike_p2p_t *this, message_t *message) } DBG1(DBG_IKE, "received P2P_CONNECT"); - break; } + default: + break; } - return NEED_MORE; } @@ -420,16 +418,16 @@ static status_t build_r(private_ike_p2p_t *this, message_t *message) if (this->response) { - // FIXME: handle result of set_responder_data - // as initiator, upon receiving a response from another peer, - // update the checklist and start sending checks + /* FIXME: handle result of set_responder_data + * as initiator, upon receiving a response from another peer, + * update the checklist and start sending checks */ charon->connect_manager->set_responder_data(charon->connect_manager, this->session_id, this->session_key, this->remote_endpoints); } else { - // FIXME: handle result of set_initiator_data - // as responder, create a checklist with the initiator's data + /* FIXME: handle result of set_initiator_data + * as responder, create a checklist with the initiator's data */ charon->connect_manager->set_initiator_data(charon->connect_manager, this->peer_id, this->ike_sa->get_my_id(this->ike_sa), this->session_id, this->session_key, this->remote_endpoints, @@ -440,9 +438,10 @@ static status_t build_r(private_ike_p2p_t *this, message_t *message) return FAILED; } } - break; } + default: + break; } return SUCCESS; } @@ -469,20 +468,19 @@ static status_t process_i(private_ike_p2p_t *this, message_t *message) case IKE_AUTH: { process_payloads(this, message); - - //FIXME: we should update the server reflexive endpoint somehow, if mobike notices a change - + /* FIXME: we should update the server reflexive endpoint somehow, + * if mobike notices a change */ endpoint_notify_t *reflexive; - if (this->remote_endpoints->get_first(this->remote_endpoints, (void**)&reflexive) == SUCCESS && - reflexive->get_type(reflexive) == SERVER_REFLEXIVE) - {//FIXME: should we accept this endpoint even if we did not send a request? + if (this->remote_endpoints->get_first(this->remote_endpoints, + (void**)&reflexive) == SUCCESS && + reflexive->get_type(reflexive) == SERVER_REFLEXIVE) + { /* FIXME: should we accept this endpoint even if we did not send + * a request? */ host_t *endpoint = reflexive->get_host(reflexive); - DBG2(DBG_IKE, "received server reflexive endpoint %#H", endpoint); this->ike_sa->set_server_reflexive_host(this->ike_sa, endpoint->clone(endpoint)); } - - // FIXME: what if it failed? e.g. AUTH failure + /* FIXME: what if it failed? e.g. AUTH failure */ SIG(CHILD_UP_SUCCESS, "established mediation connection without CHILD_SA successfully"); break; @@ -494,22 +492,23 @@ static status_t process_i(private_ike_p2p_t *this, message_t *message) if (this->failed) { DBG1(DBG_IKE, "peer '%D' is not online", this->peer_id); - // FIXME: notify the mediated connection (job?) - // FIXME: probably delete the created checklist, at least as responder + /* FIXME: notify the mediated connection (job?) + * FIXME: probably delete the created checklist, at least as + * responder */ } else { if (this->response) { - // FIXME: handle result of set_responder_data - // as responder, we update the checklist and start sending checks + /* FIXME: handle result of set_responder_data. + * as responder, we update the checklist and start sending checks */ charon->connect_manager->set_responder_data(charon->connect_manager, this->session_id, this->session_key, this->local_endpoints); } else { - // FIXME: handle result of set_initiator_data - // as initiator, we create a checklist and set the initiator's data + /* FIXME: handle result of set_initiator_data + * as initiator, we create a checklist and set the initiator's data */ charon->connect_manager->set_initiator_data(charon->connect_manager, this->ike_sa->get_my_id(this->ike_sa), this->peer_id, this->session_id, this->session_key, this->local_endpoints, @@ -518,12 +517,12 @@ static status_t process_i(private_ike_p2p_t *this, message_t *message) } break; } + default: + break; } return SUCCESS; } -// ----------------------------------------------------------------------------- - /** * Implementation of task_t.process for initiator (mediation server) */ @@ -542,21 +541,19 @@ static status_t build_i_ms(private_ike_p2p_t *this, message_t *message) } else { - notify_payload_t *notify; - if (this->response) { message->add_notify(message, FALSE, P2P_RESPONSE, chunk_empty); - } - + } message->add_notify(message, FALSE, P2P_SESSIONID, this->session_id); message->add_notify(message, FALSE, P2P_SESSIONKEY, this->session_key); add_endpoints_to_message(message, this->remote_endpoints); } - break; } + default: + break; } return NEED_MORE; @@ -614,9 +611,10 @@ static status_t process_r_ms(private_ike_p2p_t *this, message_t *message) this->invalid_syntax = TRUE; break; } - break; } + default: + break; } return NEED_MORE; @@ -679,7 +677,7 @@ static status_t build_r_ms(private_ike_p2p_t *this, message_t *message) if (!peer_sa) { - // the peer is not online + /* the peer is not online */ message->add_notify(message, TRUE, P2P_CONNECT_FAILED, chunk_empty); break; } @@ -691,6 +689,8 @@ static status_t build_r_ms(private_ike_p2p_t *this, message_t *message) break; } + default: + break; } return SUCCESS; } @@ -700,18 +700,9 @@ static status_t build_r_ms(private_ike_p2p_t *this, message_t *message) */ static status_t process_i_ms(private_ike_p2p_t *this, message_t *message) { - switch(message->get_exchange_type(message)) - { - case P2P_CONNECT: - { - break; - } - } return SUCCESS; } -// ----------------------------------------------------------------------------- - /** * Implementation of ike_p2p.connect */ @@ -813,7 +804,7 @@ ike_p2p_t *ike_p2p_create(ike_sa_t *ike_sa, bool initiator) } else { - // mediation server + /* mediation server */ if (initiator) { this->public.task.build = (status_t(*)(task_t*,message_t*))build_i_ms; diff --git a/src/charon/sa/tasks/task.c b/src/charon/sa/tasks/task.c index e9d0c4da1..cc20a8861 100644 --- a/src/charon/sa/tasks/task.c +++ b/src/charon/sa/tasks/task.c @@ -28,6 +28,7 @@ ENUM(task_type_names, IKE_INIT, CHILD_REKEY, "IKE_NATD", "IKE_MOBIKE", "IKE_AUTHENTICATE", + "IKE_AUTH_LIFETIME", "IKE_CERT", "IKE_CONFIG", "IKE_REKEY", diff --git a/src/charon/sa/tasks/task.h b/src/charon/sa/tasks/task.h index dd2bb8a83..a59207711 100644 --- a/src/charon/sa/tasks/task.h +++ b/src/charon/sa/tasks/task.h @@ -45,6 +45,8 @@ enum task_type_t { IKE_MOBIKE, /** authenticate the initiated IKE_SA */ IKE_AUTHENTICATE, + /** AUTH_LIFETIME negotiation, RFC4478 */ + IKE_AUTH_LIFETIME, /** exchange certificates and requests */ IKE_CERT, /** Configuration payloads, virtual IP and such */ diff --git a/src/ipsec/ipsec.in b/src/ipsec/ipsec.in index 5b35c87a5..707612e92 100755 --- a/src/ipsec/ipsec.in +++ b/src/ipsec/ipsec.in @@ -14,7 +14,11 @@ # or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License # for more details. # -# RCSID $Id: ipsec.in 3268 2007-10-08 19:59:18Z andreas $ +# RCSID $Id: ipsec.in 3390 2007-12-12 22:27:40Z andreas $ + +# define a minimum PATH environment in case it is not set +PATH="/sbin:/bin:/usr/sbin:/usr/bin:@IPSEC_SBINDIR@" +export PATH # name and version of the ipsec implementation IPSEC_NAME="@IPSEC_NAME@" @@ -97,26 +101,36 @@ down) if [ "$#" -ne 1 ] then echo "Usage: ipsec down " - exit 1 + exit 2 fi - if test -e $IPSEC_PLUTO_PID + rc=7 + if [ -e $IPSEC_PLUTO_PID ] then $IPSEC_WHACK --name "$1" --terminate + rc="$?" fi - if test -e $IPSEC_CHARON_PID + if [ -e $IPSEC_CHARON_PID ] then $IPSEC_STROKE down "$1" + rc="$?" fi - exit 0 + exit "$rc" ;; listalgs|listpubkeys|\listcards|\rereadgroups) op="$1" shift - if test -e $IPSEC_PLUTO_PID + if [ -e $IPSEC_PLUTO_PID ] then $IPSEC_WHACK "$@" "--$op" + exit "$?" + else + if [ -e $IPSEC_CHARON_PID ] + then + exit 3 + else + exit 7 + fi fi - exit 0 ;; listcerts|listcacerts|listaacerts|\ listacerts|listgroups|listocspcerts|\ @@ -125,75 +139,92 @@ rereadsecrets|rereadcacerts|rereadaacerts|\ rereadacerts|rereadocspcerts|rereadcrls|\ rereadall|purgeocsp) op="$1" + rc=7 shift - if test -e $IPSEC_PLUTO_PID + if [ -e $IPSEC_PLUTO_PID ] then $IPSEC_WHACK "$@" "--$op" + rc="$?" fi - if test -e $IPSEC_CHARON_PID + if [ -e $IPSEC_CHARON_PID ] then $IPSEC_STROKE "$op" "$@" + rc="$?" fi - exit 0 + exit "$rc" ;; ready) shift - if test -e $IPSEC_PLUTO_PID + if [ -e $IPSEC_PLUTO_PID ] then $IPSEC_WHACK --listen + exit 0 + else + exit 7 fi - exit 0 ;; reload) - if test -e $IPSEC_STARTER_PID + rc=7 + if [ -e $IPSEC_STARTER_PID ] then - echo "Reloading strongSwan IPsec configuration..." >&2 - kill -s USR1 `cat $IPSEC_STARTER_PID` + echo "Reloading strongSwan IPsec configuration..." >&2 + kill -s USR1 `cat $IPSEC_STARTER_PID` 2>/dev/null && rc=0 else - echo "ipsec starter is not running" >&2 + echo "Reloading strongSwan IPsec failed: starter is not running" >&2 fi - exit 0 + exit "$rc" ;; restart) $IPSEC_SBINDIR/ipsec stop sleep 2 shift - $IPSEC_SBINDIR/ipsec start "$@" - exit 0 + exec $IPSEC_SBINDIR/ipsec start "$@" ;; route|unroute) op="$1" + rc=7 shift if [ "$#" -ne 1 ] then - echo "Usage: ipsec $op " - exit 1 + echo "Usage: ipsec $op " + exit 2 fi - if test -e $IPSEC_PLUTO_PID + if [ -e $IPSEC_PLUTO_PID ] then $IPSEC_WHACK --name "$1" "--$op" + rc="$?" fi - if test -e $IPSEC_CHARON_PID + if [ -e $IPSEC_CHARON_PID ] then $IPSEC_STROKE "$op" "$1" + rc="$?" fi - exit 0 + exit "$rc" ;; scencrypt|scdecrypt) op="$1" shift - if test -e $IPSEC_PLUTO_PID + if [ -e $IPSEC_PLUTO_PID ] then $IPSEC_WHACK "--$op" "$@" + exit "$?" + else + exit 7 fi - exit 0 ;; secrets) - if test -e $IPSEC_PLUTO_PID + rc=7 + if [ -e $IPSEC_PLUTO_PID ] then $IPSEC_WHACK --rereadsecrets + rc="$?" fi - exit 0 + if [ -e $IPSEC_CHARON_PID ] + then + $IPSEC_STROKE rereadsecrets + rc="$?" + fi + exit "$rc" ;; start) shift @@ -201,36 +232,64 @@ start) ;; status|statusall) op="$1" + # Return value is slightly different for the status command: + # 0 - service up and running + # 1 - service dead, but /var/run/ pid file exists + # 2 - service dead, but /var/lock/ lock file exists + # 3 - service not running (unused) + # 4 - service status unknown :-( + # 5--199 reserved (5--99 LSB, 100--149 distro, 150--199 appl.) shift - if test $# -eq 0 + if [ $# -eq 0 ] then - if test -e $IPSEC_PLUTO_PID + if [ -e $IPSEC_PLUTO_PID ] then $IPSEC_WHACK "--$op" fi - if test -e $IPSEC_CHARON_PID + if [ -e $IPSEC_CHARON_PID ] then $IPSEC_STROKE "$op" fi else - if test -e $IPSEC_PLUTO_PID + if [ -e $IPSEC_PLUTO_PID ] then $IPSEC_WHACK --name "$1" "--$op" fi - if test -e $IPSEC_CHARON_PID + if [ -e $IPSEC_CHARON_PID ] then $IPSEC_STROKE "$op" "$1" fi fi - exit 0 + if [ -e $IPSEC_STARTER_PID ] + then + kill -0 `cat $IPSEC_STARTER_PID` 2>/dev/null + exit $? + fi + exit 3 ;; stop) - if test -e $IPSEC_STARTER_PID + # stopping a not-running service is considered as success + if [ -e $IPSEC_STARTER_PID ] then - echo "Stopping strongSwan IPsec..." >&2 - kill `cat $IPSEC_STARTER_PID` + echo "Stopping strongSwan IPsec..." >&2 + spid=`cat $IPSEC_STARTER_PID` + if [ -n "$spid" ] + then + kill $spid 2>/dev/null + loop=5 + while [ $loop -gt 0 ] ; do + kill -s 0 $spid 2>/dev/null || break + sleep 1 + loop=$(($loop - 1)) + done + if [ $loop -eq 0 ] + then + kill -s KILL $spid 2>/dev/null + rm -f $IPSEC_STARTER_PID + fi + fi else - echo "ipsec starter is not running" >&2 + echo "Stopping strongSwan IPsec failed: starter is not running" >&2 fi exit 0 ;; @@ -239,27 +298,31 @@ up) if [ "$#" -ne 1 ] then echo "Usage: ipsec up " - exit 1 + exit 2 fi - if test -e $IPSEC_PLUTO_PID + rc=7 + if [ -e $IPSEC_PLUTO_PID ] then $IPSEC_WHACK --name "$1" --initiate + rc="$?" fi - if test -e $IPSEC_CHARON_PID + if [ -e $IPSEC_CHARON_PID ] then - $IPSEC_STROKE up "$1" + $IPSEC_STROKE up "$1" + rc="$?" fi - exit 0 + exit "$rc" ;; update) - if test -e $IPSEC_STARTER_PID + if [ -e $IPSEC_STARTER_PID ] then echo "Updating strongSwan IPsec configuration..." >&2 kill -s HUP `cat $IPSEC_STARTER_PID` + exit 0 else - echo "ipsec starter is not running" >&2 + echo "Updating strongSwan IPsec failed: starter is not running" >&2 + exit 7 fi - exit 0 ;; version|--version) echo "Linux $IPSEC_NAME $IPSEC_VERSION" @@ -269,7 +332,7 @@ version|--version) ;; --*) echo "$0: unknown option \`$1' (perhaps command name was omitted?)" >&2 - exit 1 + exit 2 ;; esac @@ -278,13 +341,13 @@ shift path="$IPSEC_DIR/$cmd" -if test ! -x "$path" +if [ ! -x "$path" ] then path="$IPSEC_DIR/$cmd" - if test ! -x "$path" + if [ ! -x "$path" ] then echo "$0: unknown IPsec command \`$cmd' (\`ipsec --help' for list)" >&2 - exit 1 + exit 2 fi fi diff --git a/src/libstrongswan/crypto/ac.c b/src/libstrongswan/crypto/ac.c index 1367494f8..641ce5d64 100644 --- a/src/libstrongswan/crypto/ac.c +++ b/src/libstrongswan/crypto/ac.c @@ -20,7 +20,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: ac.c 3300 2007-10-12 21:53:18Z andreas $ + * RCSID $Id: ac.c 3355 2007-11-20 12:06:40Z martin $ */ #include @@ -544,7 +544,7 @@ static void list(const private_x509ac_t *this, FILE *out, bool utc) fprintf(out, " validity: not before %#T, ", &this->notBefore, utc); if (now < this->notBefore) { - fprintf(out, "not valid yet (valid in %V)\n", &now, &this->notBefore); + fprintf(out, "not valid yet (valid in %#V)\n", &now, &this->notBefore); } else { @@ -554,14 +554,14 @@ static void list(const private_x509ac_t *this, FILE *out, bool utc) fprintf(out, " not after %#T, ", &this->notAfter, utc); if (now > this->notAfter) { - fprintf(out, "expired (%V ago)\n", &now, &this->notAfter); + fprintf(out, "expired (%#V ago)\n", &now, &this->notAfter); } else { fprintf(out, "ok"); if (now > this->notAfter - ACERT_WARNING_INTERVAL * 60 * 60 * 24) { - fprintf(out, " (expires in %V)", &now, &this->notAfter); + fprintf(out, " (expires in %#V)", &now, &this->notAfter); } fprintf(out, " \n"); } diff --git a/src/libstrongswan/crypto/ca.c b/src/libstrongswan/crypto/ca.c index a78590954..510e3528e 100644 --- a/src/libstrongswan/crypto/ca.c +++ b/src/libstrongswan/crypto/ca.c @@ -279,11 +279,11 @@ static void list_certinfos(private_ca_info_t *this, FILE *out, bool utc) fprintf(out, "%#T, until %#T, ", &thisUpdate, utc, &nextUpdate, utc); if (now > nextUpdate) { - fprintf(out, "expired (%V ago)\n", &now, &nextUpdate); + fprintf(out, "expired (%#V ago)\n", &now, &nextUpdate); } else { - fprintf(out, "ok (expires in %V)\n", &now, &nextUpdate); + fprintf(out, "ok (expires in %#V)\n", &now, &nextUpdate); } fprintf(out, " serial: %#B, %N\n", &serial, cert_status_names, certinfo->get_status(certinfo)); @@ -654,7 +654,7 @@ static cert_status_t verify_by_ocsp(private_ca_info_t* this, if (comparison > 0) { - iterator->insert_after(iterator, (void *)cached_certinfo); + this->certinfos->insert_last(this->certinfos, (void *)cached_certinfo); } else { diff --git a/src/libstrongswan/crypto/crl.c b/src/libstrongswan/crypto/crl.c index d52078ea9..ab23bb9ec 100755 --- a/src/libstrongswan/crypto/crl.c +++ b/src/libstrongswan/crypto/crl.c @@ -19,7 +19,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: crl.c 3300 2007-10-12 21:53:18Z andreas $ + * RCSID $Id: crl.c 3355 2007-11-20 12:06:40Z martin $ */ #include @@ -463,11 +463,11 @@ static void list(private_crl_t *this, FILE* out, bool utc) } else if (now > this->nextUpdate) { - fprintf(out, "expired (%V ago)\n", &now, &this->nextUpdate); + fprintf(out, "expired (%#V ago)\n", &now, &this->nextUpdate); } else if (now > this->nextUpdate - CRL_WARNING_INTERVAL * 60 * 60 * 24) { - fprintf(out, "ok (expires in %V)\n", &now, &this->nextUpdate); + fprintf(out, "ok (expires in %#V)\n", &now, &this->nextUpdate); } else { diff --git a/src/libstrongswan/crypto/x509.c b/src/libstrongswan/crypto/x509.c index d9093fc62..6f154b36f 100755 --- a/src/libstrongswan/crypto/x509.c +++ b/src/libstrongswan/crypto/x509.c @@ -24,7 +24,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: x509.c 3301 2007-10-12 21:56:30Z andreas $ + * RCSID $Id: x509.c 3355 2007-11-20 12:06:40Z martin $ */ #include @@ -1182,7 +1182,7 @@ static void list(private_x509_t *this, FILE *out, bool utc) fprintf(out, " validity: not before %#T, ", &this->notBefore, utc); if (now < this->notBefore) { - fprintf(out, "not valid yet (valid in %V)\n", &now, &this->notBefore); + fprintf(out, "not valid yet (valid in %#V)\n", &now, &this->notBefore); } else { @@ -1192,14 +1192,14 @@ static void list(private_x509_t *this, FILE *out, bool utc) fprintf(out, " not after %#T, ", &this->notAfter, utc); if (now > this->notAfter) { - fprintf(out, "expired (%V ago)\n", &now, &this->notAfter); + fprintf(out, "expired (%#V ago)\n", &now, &this->notAfter); } else { fprintf(out, "ok"); if (now > this->notAfter - CERT_WARNING_INTERVAL * 60 * 60 * 24) { - fprintf(out, " (expires in %V)", &now, &this->notAfter); + fprintf(out, " (expires in %#V)", &now, &this->notAfter); } fprintf(out, " \n"); } diff --git a/src/libstrongswan/library.c b/src/libstrongswan/library.c index 9f96d119c..f66818bc2 100644 --- a/src/libstrongswan/library.c +++ b/src/libstrongswan/library.c @@ -150,11 +150,20 @@ static int print_time(FILE *stream, const struct printf_info *info, static int print_time_delta(FILE *stream, const struct printf_info *info, const void *const *args) { - time_t *start = *((time_t**)(args[0])); - time_t *end = *((time_t**)(args[1])); - u_int delta = abs(*end - *start); - char* unit = "second"; + time_t *arg1, *arg2; + time_t delta; + + arg1 = *((time_t**)(args[0])); + if (info->alt) + { + arg2 = *((time_t**)(args[1])); + delta = abs(*arg1 - *arg2); + } + else + { + delta = *arg1; + } if (delta > 2 * 60 * 60 * 24) { @@ -180,5 +189,5 @@ static int print_time_delta(FILE *stream, const struct printf_info *info, static void __attribute__ ((constructor))print_register() { register_printf_function(PRINTF_TIME, print_time, arginfo_ptr_alt_ptr_int); - register_printf_function(PRINTF_TIME_DELTA, print_time_delta, arginfo_ptr_ptr); + register_printf_function(PRINTF_TIME_DELTA, print_time_delta, arginfo_ptr_alt_ptr_ptr); } diff --git a/src/libstrongswan/printf_hook.c b/src/libstrongswan/printf_hook.c index 0407e8c82..baf339640 100644 --- a/src/libstrongswan/printf_hook.c +++ b/src/libstrongswan/printf_hook.c @@ -116,3 +116,26 @@ int arginfo_ptr_alt_ptr_int(const struct printf_info *info, size_t n, int *argty } return 1; } + +/** + * special arginfo handler respecting alt flag + */ +int arginfo_ptr_alt_ptr_ptr(const struct printf_info *info, size_t n, int *argtypes) +{ + if (info->alt) + { + if (n > 1) + { + argtypes[0] = PA_POINTER; + argtypes[1] = PA_POINTER; + } + return 2; + } + + if (n > 0) + { + argtypes[0] = PA_POINTER; + } + return 1; +} + diff --git a/src/libstrongswan/printf_hook.h b/src/libstrongswan/printf_hook.h index 03bcf447d..77b228da0 100644 --- a/src/libstrongswan/printf_hook.h +++ b/src/libstrongswan/printf_hook.h @@ -44,7 +44,7 @@ #define PRINTF_TRAFFIC_SELECTOR 'R' /** 1 argument: time_t *time; with #-modifier 2 arguments: time_t *time, bool utc */ #define PRINTF_TIME 'T' -/** 2 arguments: time_t *begin, time_t *end */ +/** 1 argument: time_t *delta; with #-modifier 2 arguments: time_t *begin, time_t *end */ #define PRINTF_TIME_DELTA 'V' /** @@ -55,6 +55,7 @@ int arginfo_ptr_ptr(const struct printf_info *info, size_t n, int *argtypes); int arginfo_ptr_int(const struct printf_info *info, size_t n, int *argtypes); int arginfo_int_int(const struct printf_info *info, size_t n, int *argtypes); int arginfo_ptr_alt_ptr_int(const struct printf_info *info, size_t n, int *argtypes); +int arginfo_ptr_alt_ptr_ptr(const struct printf_info *info, size_t n, int *argtypes); int arginfo_int_alt_int_int(const struct printf_info *info, size_t n, int *argtypes); #endif /* PRINTF_HOOK_H_ */ diff --git a/src/libstrongswan/utils/lexparser.c b/src/libstrongswan/utils/lexparser.c index 9d3f06593..7cc89fc90 100644 --- a/src/libstrongswan/utils/lexparser.c +++ b/src/libstrongswan/utils/lexparser.c @@ -17,8 +17,12 @@ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. + * + * RCSID $Id: lexparser.c 3353 2007-11-19 12:27:08Z martin $ */ +/* memrchr is a GNU extension */ +#define _GNU_SOURCE #include #include "lexparser.h" @@ -45,7 +49,7 @@ bool match(const char *pattern, const chunk_t *ch) } /** - * extracts a token ending with a given termination symbol + * extracts a token ending with the first occurrence of a given termination symbol */ bool extract_token(chunk_t *token, const char termination, chunk_t *src) { @@ -70,6 +74,32 @@ bool extract_token(chunk_t *token, const char termination, chunk_t *src) return TRUE; } +/** + * extracts a token ending with the last occurrence of a given termination symbol + */ +bool extract_last_token(chunk_t *token, const char termination, chunk_t *src) +{ + u_char *eot = memrchr(src->ptr, termination, src->len); + + /* initialize empty token */ + *token = chunk_empty; + + if (eot == NULL) /* termination symbol not found */ + { + return FALSE; + } + + /* extract token */ + token->ptr = src->ptr; + token->len = (u_int)(eot - src->ptr); + + /* advance src pointer after termination symbol */ + src->ptr = eot + 1; + src->len -= (token->len + 1); + + return TRUE; +} + /** * fetches a new line terminated by \n or \r\n */ diff --git a/src/libstrongswan/utils/lexparser.h b/src/libstrongswan/utils/lexparser.h index e3c2c4c70..775898139 100644 --- a/src/libstrongswan/utils/lexparser.h +++ b/src/libstrongswan/utils/lexparser.h @@ -17,6 +17,8 @@ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. + * + * RCSID $Id: lexparser.h 3346 2007-11-16 20:23:29Z andreas $ */ #include @@ -32,10 +34,15 @@ bool eat_whitespace(chunk_t *src); bool match(const char *pattern, const chunk_t *ch); /** - * @brief Extracts a token ending with a given termination symbol + * @brief Extracts a token ending with the first occurence a given termination symbol */ bool extract_token(chunk_t *token, const char termination, chunk_t *src); +/** + * @brief Extracts a token ending with the last occurence a given termination symbol + */ +bool extract_last_token(chunk_t *token, const char termination, chunk_t *src); + /** * @brief Fetches a new text line terminated by \n or \r\n */ diff --git a/src/manager/Makefile.am b/src/manager/Makefile.am index 17eecdbab..7f77d1dba 100644 --- a/src/manager/Makefile.am +++ b/src/manager/Makefile.am @@ -3,7 +3,9 @@ ipsec_PROGRAMS = manager.fcgi manager_fcgi_SOURCES = \ main.c manager.c manager.h gateway.h gateway.c database.h database.c \ controller/auth_controller.c controller/auth_controller.h \ -controller/status_controller.c controller/status_controller.h \ +controller/ikesa_controller.c controller/ikesa_controller.h \ +controller/control_controller.c controller/control_controller.h \ +controller/config_controller.c controller/config_controller.h \ controller/gateway_controller.c controller/gateway_controller.h manager_fcgi_LDADD = $(top_builddir)/src/manager/libappserv.la -lsqlite3 @@ -34,20 +36,31 @@ ipsec_templates_auth_DATA = templates/auth/login.cs ipsec_templates_gatewaydir = ${ipsec_templatesdir}/gateway ipsec_templates_gateway_DATA = templates/gateway/list.cs -ipsec_templates_statusdir = ${ipsec_templatesdir}/status -ipsec_templates_status_DATA = templates/status/ikesalist.cs +ipsec_templates_ikesadir = ${ipsec_templatesdir}/ikesa +ipsec_templates_ikesa_DATA = templates/ikesa/list.cs + +ipsec_templates_controldir = ${ipsec_templatesdir}/control +ipsec_templates_control_DATA = templates/control/result.cs + +ipsec_templates_configdir = ${ipsec_templatesdir}/config +ipsec_templates_config_DATA = templates/config/list.cs ipsec_templates_staticdir = ${ipsec_templatesdir}/static ipsec_templates_static_DATA = templates/static/style.css templates/static/script.js templates/static/jquery.js \ templates/static/pipe.png templates/static/pipe-good.png templates/static/pipe-bad.png \ templates/static/pipe-thin.png templates/static/pipe-thin-left.png templates/static/pipe-thin-right.png \ +templates/static/pipe-thin-green.png templates/static/pipe-thin-left-green.png templates/static/pipe-thin-right-green.png \ templates/static/gateway-left.png templates/static/client-left.png templates/static/strongswan.png \ -templates/static/router.png templates/static/gateway-right.png templates/static/client-right.png +templates/static/router.png templates/static/gateway-right.png templates/static/client-right.png \ +templates/static/close.png templates/static/initiate.png EXTRA_DIST = manager.db templates/header.cs templates/footer.cs templates/error.cs \ -templates/auth/login.cs templates/gateway/list.cs templates/status/ikesalist.cs \ +templates/auth/login.cs templates/gateway/list.cs templates/ikesa/list.cs \ +templates/config/list.cs templates/control/result.cs \ templates/static/style.css templates/static/script.js templates/static/jquery.js \ templates/static/pipe.png templates/static/pipe-good.png templates/static/pipe-bad.png \ templates/static/pipe-thin.png templates/static/pipe-thin-left.png templates/static/pipe-thin-right.png \ +templates/static/pipe-thin-green.png templates/static/pipe-thin-left-green.png templates/static/pipe-thin-right-green.png \ templates/static/gateway-left.png templates/static/client-left.png templates/static/strongswan.png \ -templates/static/router.png templates/static/gateway-right.png templates/static/client-right.png +templates/static/router.png templates/static/gateway-right.png templates/static/client-right.png \ +templates/static/close.png templates/static/initiate.png diff --git a/src/manager/Makefile.in b/src/manager/Makefile.in index 5c09c22d4..3830d37fc 100644 --- a/src/manager/Makefile.in +++ b/src/manager/Makefile.in @@ -52,9 +52,11 @@ am__strip_dir = `echo $$p | sed -e 's|^.*/||'`; am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(ipsecdir)" \ "$(DESTDIR)$(ipsecdir)" "$(DESTDIR)$(ipsec_templatesdir)" \ "$(DESTDIR)$(ipsec_templates_authdir)" \ + "$(DESTDIR)$(ipsec_templates_configdir)" \ + "$(DESTDIR)$(ipsec_templates_controldir)" \ "$(DESTDIR)$(ipsec_templates_gatewaydir)" \ - "$(DESTDIR)$(ipsec_templates_staticdir)" \ - "$(DESTDIR)$(ipsec_templates_statusdir)" + "$(DESTDIR)$(ipsec_templates_ikesadir)" \ + "$(DESTDIR)$(ipsec_templates_staticdir)" libLTLIBRARIES_INSTALL = $(INSTALL) LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = @@ -67,7 +69,8 @@ ipsecPROGRAMS_INSTALL = $(INSTALL_PROGRAM) PROGRAMS = $(ipsec_PROGRAMS) am_manager_fcgi_OBJECTS = main.$(OBJEXT) manager.$(OBJEXT) \ gateway.$(OBJEXT) database.$(OBJEXT) auth_controller.$(OBJEXT) \ - status_controller.$(OBJEXT) gateway_controller.$(OBJEXT) + ikesa_controller.$(OBJEXT) control_controller.$(OBJEXT) \ + config_controller.$(OBJEXT) gateway_controller.$(OBJEXT) manager_fcgi_OBJECTS = $(am_manager_fcgi_OBJECTS) manager_fcgi_DEPENDENCIES = $(top_builddir)/src/manager/libappserv.la DEFAULT_INCLUDES = -I.@am__isrc@ @@ -87,12 +90,16 @@ DIST_SOURCES = $(libappserv_la_SOURCES) $(manager_fcgi_SOURCES) ipsecDATA_INSTALL = $(INSTALL_DATA) ipsec_templatesDATA_INSTALL = $(INSTALL_DATA) ipsec_templates_authDATA_INSTALL = $(INSTALL_DATA) +ipsec_templates_configDATA_INSTALL = $(INSTALL_DATA) +ipsec_templates_controlDATA_INSTALL = $(INSTALL_DATA) ipsec_templates_gatewayDATA_INSTALL = $(INSTALL_DATA) +ipsec_templates_ikesaDATA_INSTALL = $(INSTALL_DATA) ipsec_templates_staticDATA_INSTALL = $(INSTALL_DATA) -ipsec_templates_statusDATA_INSTALL = $(INSTALL_DATA) DATA = $(ipsec_DATA) $(ipsec_templates_DATA) \ - $(ipsec_templates_auth_DATA) $(ipsec_templates_gateway_DATA) \ - $(ipsec_templates_static_DATA) $(ipsec_templates_status_DATA) + $(ipsec_templates_auth_DATA) $(ipsec_templates_config_DATA) \ + $(ipsec_templates_control_DATA) \ + $(ipsec_templates_gateway_DATA) $(ipsec_templates_ikesa_DATA) \ + $(ipsec_templates_static_DATA) ETAGS = etags CTAGS = ctags DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) @@ -229,7 +236,9 @@ xml_LIBS = @xml_LIBS@ manager_fcgi_SOURCES = \ main.c manager.c manager.h gateway.h gateway.c database.h database.c \ controller/auth_controller.c controller/auth_controller.h \ -controller/status_controller.c controller/status_controller.h \ +controller/ikesa_controller.c controller/ikesa_controller.h \ +controller/control_controller.c controller/control_controller.h \ +controller/config_controller.c controller/config_controller.h \ controller/gateway_controller.c controller/gateway_controller.h manager_fcgi_LDADD = $(top_builddir)/src/manager/libappserv.la -lsqlite3 @@ -251,22 +260,31 @@ ipsec_templates_authdir = ${ipsec_templatesdir}/auth ipsec_templates_auth_DATA = templates/auth/login.cs ipsec_templates_gatewaydir = ${ipsec_templatesdir}/gateway ipsec_templates_gateway_DATA = templates/gateway/list.cs -ipsec_templates_statusdir = ${ipsec_templatesdir}/status -ipsec_templates_status_DATA = templates/status/ikesalist.cs +ipsec_templates_ikesadir = ${ipsec_templatesdir}/ikesa +ipsec_templates_ikesa_DATA = templates/ikesa/list.cs +ipsec_templates_controldir = ${ipsec_templatesdir}/control +ipsec_templates_control_DATA = templates/control/result.cs +ipsec_templates_configdir = ${ipsec_templatesdir}/config +ipsec_templates_config_DATA = templates/config/list.cs ipsec_templates_staticdir = ${ipsec_templatesdir}/static ipsec_templates_static_DATA = templates/static/style.css templates/static/script.js templates/static/jquery.js \ templates/static/pipe.png templates/static/pipe-good.png templates/static/pipe-bad.png \ templates/static/pipe-thin.png templates/static/pipe-thin-left.png templates/static/pipe-thin-right.png \ +templates/static/pipe-thin-green.png templates/static/pipe-thin-left-green.png templates/static/pipe-thin-right-green.png \ templates/static/gateway-left.png templates/static/client-left.png templates/static/strongswan.png \ -templates/static/router.png templates/static/gateway-right.png templates/static/client-right.png +templates/static/router.png templates/static/gateway-right.png templates/static/client-right.png \ +templates/static/close.png templates/static/initiate.png EXTRA_DIST = manager.db templates/header.cs templates/footer.cs templates/error.cs \ -templates/auth/login.cs templates/gateway/list.cs templates/status/ikesalist.cs \ +templates/auth/login.cs templates/gateway/list.cs templates/ikesa/list.cs \ +templates/config/list.cs templates/control/result.cs \ templates/static/style.css templates/static/script.js templates/static/jquery.js \ templates/static/pipe.png templates/static/pipe-good.png templates/static/pipe-bad.png \ templates/static/pipe-thin.png templates/static/pipe-thin-left.png templates/static/pipe-thin-right.png \ +templates/static/pipe-thin-green.png templates/static/pipe-thin-left-green.png templates/static/pipe-thin-right-green.png \ templates/static/gateway-left.png templates/static/client-left.png templates/static/strongswan.png \ -templates/static/router.png templates/static/gateway-right.png templates/static/client-right.png +templates/static/router.png templates/static/gateway-right.png templates/static/client-right.png \ +templates/static/close.png templates/static/initiate.png all: all-am @@ -369,15 +387,17 @@ distclean-compile: -rm -f *.tab.c @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/auth_controller.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/config_controller.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/control_controller.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/database.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/dispatcher.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gateway.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gateway_controller.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ikesa_controller.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/main.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/manager.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/request.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/session.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/status_controller.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/xml.Plo@am__quote@ .c.o: @@ -443,19 +463,47 @@ auth_controller.obj: controller/auth_controller.c @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o auth_controller.obj `if test -f 'controller/auth_controller.c'; then $(CYGPATH_W) 'controller/auth_controller.c'; else $(CYGPATH_W) '$(srcdir)/controller/auth_controller.c'; fi` -status_controller.o: controller/status_controller.c -@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT status_controller.o -MD -MP -MF $(DEPDIR)/status_controller.Tpo -c -o status_controller.o `test -f 'controller/status_controller.c' || echo '$(srcdir)/'`controller/status_controller.c -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/status_controller.Tpo $(DEPDIR)/status_controller.Po -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='controller/status_controller.c' object='status_controller.o' libtool=no @AMDEPBACKSLASH@ +ikesa_controller.o: controller/ikesa_controller.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT ikesa_controller.o -MD -MP -MF $(DEPDIR)/ikesa_controller.Tpo -c -o ikesa_controller.o `test -f 'controller/ikesa_controller.c' || echo '$(srcdir)/'`controller/ikesa_controller.c +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/ikesa_controller.Tpo $(DEPDIR)/ikesa_controller.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='controller/ikesa_controller.c' object='ikesa_controller.o' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o status_controller.o `test -f 'controller/status_controller.c' || echo '$(srcdir)/'`controller/status_controller.c +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o ikesa_controller.o `test -f 'controller/ikesa_controller.c' || echo '$(srcdir)/'`controller/ikesa_controller.c -status_controller.obj: controller/status_controller.c -@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT status_controller.obj -MD -MP -MF $(DEPDIR)/status_controller.Tpo -c -o status_controller.obj `if test -f 'controller/status_controller.c'; then $(CYGPATH_W) 'controller/status_controller.c'; else $(CYGPATH_W) '$(srcdir)/controller/status_controller.c'; fi` -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/status_controller.Tpo $(DEPDIR)/status_controller.Po -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='controller/status_controller.c' object='status_controller.obj' libtool=no @AMDEPBACKSLASH@ +ikesa_controller.obj: controller/ikesa_controller.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT ikesa_controller.obj -MD -MP -MF $(DEPDIR)/ikesa_controller.Tpo -c -o ikesa_controller.obj `if test -f 'controller/ikesa_controller.c'; then $(CYGPATH_W) 'controller/ikesa_controller.c'; else $(CYGPATH_W) '$(srcdir)/controller/ikesa_controller.c'; fi` +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/ikesa_controller.Tpo $(DEPDIR)/ikesa_controller.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='controller/ikesa_controller.c' object='ikesa_controller.obj' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o status_controller.obj `if test -f 'controller/status_controller.c'; then $(CYGPATH_W) 'controller/status_controller.c'; else $(CYGPATH_W) '$(srcdir)/controller/status_controller.c'; fi` +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o ikesa_controller.obj `if test -f 'controller/ikesa_controller.c'; then $(CYGPATH_W) 'controller/ikesa_controller.c'; else $(CYGPATH_W) '$(srcdir)/controller/ikesa_controller.c'; fi` + +control_controller.o: controller/control_controller.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT control_controller.o -MD -MP -MF $(DEPDIR)/control_controller.Tpo -c -o control_controller.o `test -f 'controller/control_controller.c' || echo '$(srcdir)/'`controller/control_controller.c +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/control_controller.Tpo $(DEPDIR)/control_controller.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='controller/control_controller.c' object='control_controller.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o control_controller.o `test -f 'controller/control_controller.c' || echo '$(srcdir)/'`controller/control_controller.c + +control_controller.obj: controller/control_controller.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT control_controller.obj -MD -MP -MF $(DEPDIR)/control_controller.Tpo -c -o control_controller.obj `if test -f 'controller/control_controller.c'; then $(CYGPATH_W) 'controller/control_controller.c'; else $(CYGPATH_W) '$(srcdir)/controller/control_controller.c'; fi` +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/control_controller.Tpo $(DEPDIR)/control_controller.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='controller/control_controller.c' object='control_controller.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o control_controller.obj `if test -f 'controller/control_controller.c'; then $(CYGPATH_W) 'controller/control_controller.c'; else $(CYGPATH_W) '$(srcdir)/controller/control_controller.c'; fi` + +config_controller.o: controller/config_controller.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT config_controller.o -MD -MP -MF $(DEPDIR)/config_controller.Tpo -c -o config_controller.o `test -f 'controller/config_controller.c' || echo '$(srcdir)/'`controller/config_controller.c +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/config_controller.Tpo $(DEPDIR)/config_controller.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='controller/config_controller.c' object='config_controller.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o config_controller.o `test -f 'controller/config_controller.c' || echo '$(srcdir)/'`controller/config_controller.c + +config_controller.obj: controller/config_controller.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT config_controller.obj -MD -MP -MF $(DEPDIR)/config_controller.Tpo -c -o config_controller.obj `if test -f 'controller/config_controller.c'; then $(CYGPATH_W) 'controller/config_controller.c'; else $(CYGPATH_W) '$(srcdir)/controller/config_controller.c'; fi` +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/config_controller.Tpo $(DEPDIR)/config_controller.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='controller/config_controller.c' object='config_controller.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o config_controller.obj `if test -f 'controller/config_controller.c'; then $(CYGPATH_W) 'controller/config_controller.c'; else $(CYGPATH_W) '$(srcdir)/controller/config_controller.c'; fi` gateway_controller.o: controller/gateway_controller.c @am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT gateway_controller.o -MD -MP -MF $(DEPDIR)/gateway_controller.Tpo -c -o gateway_controller.o `test -f 'controller/gateway_controller.c' || echo '$(srcdir)/'`controller/gateway_controller.c @@ -527,6 +575,40 @@ uninstall-ipsec_templates_authDATA: echo " rm -f '$(DESTDIR)$(ipsec_templates_authdir)/$$f'"; \ rm -f "$(DESTDIR)$(ipsec_templates_authdir)/$$f"; \ done +install-ipsec_templates_configDATA: $(ipsec_templates_config_DATA) + @$(NORMAL_INSTALL) + test -z "$(ipsec_templates_configdir)" || $(MKDIR_P) "$(DESTDIR)$(ipsec_templates_configdir)" + @list='$(ipsec_templates_config_DATA)'; for p in $$list; do \ + if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ + f=$(am__strip_dir) \ + echo " $(ipsec_templates_configDATA_INSTALL) '$$d$$p' '$(DESTDIR)$(ipsec_templates_configdir)/$$f'"; \ + $(ipsec_templates_configDATA_INSTALL) "$$d$$p" "$(DESTDIR)$(ipsec_templates_configdir)/$$f"; \ + done + +uninstall-ipsec_templates_configDATA: + @$(NORMAL_UNINSTALL) + @list='$(ipsec_templates_config_DATA)'; for p in $$list; do \ + f=$(am__strip_dir) \ + echo " rm -f '$(DESTDIR)$(ipsec_templates_configdir)/$$f'"; \ + rm -f "$(DESTDIR)$(ipsec_templates_configdir)/$$f"; \ + done +install-ipsec_templates_controlDATA: $(ipsec_templates_control_DATA) + @$(NORMAL_INSTALL) + test -z "$(ipsec_templates_controldir)" || $(MKDIR_P) "$(DESTDIR)$(ipsec_templates_controldir)" + @list='$(ipsec_templates_control_DATA)'; for p in $$list; do \ + if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ + f=$(am__strip_dir) \ + echo " $(ipsec_templates_controlDATA_INSTALL) '$$d$$p' '$(DESTDIR)$(ipsec_templates_controldir)/$$f'"; \ + $(ipsec_templates_controlDATA_INSTALL) "$$d$$p" "$(DESTDIR)$(ipsec_templates_controldir)/$$f"; \ + done + +uninstall-ipsec_templates_controlDATA: + @$(NORMAL_UNINSTALL) + @list='$(ipsec_templates_control_DATA)'; for p in $$list; do \ + f=$(am__strip_dir) \ + echo " rm -f '$(DESTDIR)$(ipsec_templates_controldir)/$$f'"; \ + rm -f "$(DESTDIR)$(ipsec_templates_controldir)/$$f"; \ + done install-ipsec_templates_gatewayDATA: $(ipsec_templates_gateway_DATA) @$(NORMAL_INSTALL) test -z "$(ipsec_templates_gatewaydir)" || $(MKDIR_P) "$(DESTDIR)$(ipsec_templates_gatewaydir)" @@ -544,6 +626,23 @@ uninstall-ipsec_templates_gatewayDATA: echo " rm -f '$(DESTDIR)$(ipsec_templates_gatewaydir)/$$f'"; \ rm -f "$(DESTDIR)$(ipsec_templates_gatewaydir)/$$f"; \ done +install-ipsec_templates_ikesaDATA: $(ipsec_templates_ikesa_DATA) + @$(NORMAL_INSTALL) + test -z "$(ipsec_templates_ikesadir)" || $(MKDIR_P) "$(DESTDIR)$(ipsec_templates_ikesadir)" + @list='$(ipsec_templates_ikesa_DATA)'; for p in $$list; do \ + if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ + f=$(am__strip_dir) \ + echo " $(ipsec_templates_ikesaDATA_INSTALL) '$$d$$p' '$(DESTDIR)$(ipsec_templates_ikesadir)/$$f'"; \ + $(ipsec_templates_ikesaDATA_INSTALL) "$$d$$p" "$(DESTDIR)$(ipsec_templates_ikesadir)/$$f"; \ + done + +uninstall-ipsec_templates_ikesaDATA: + @$(NORMAL_UNINSTALL) + @list='$(ipsec_templates_ikesa_DATA)'; for p in $$list; do \ + f=$(am__strip_dir) \ + echo " rm -f '$(DESTDIR)$(ipsec_templates_ikesadir)/$$f'"; \ + rm -f "$(DESTDIR)$(ipsec_templates_ikesadir)/$$f"; \ + done install-ipsec_templates_staticDATA: $(ipsec_templates_static_DATA) @$(NORMAL_INSTALL) test -z "$(ipsec_templates_staticdir)" || $(MKDIR_P) "$(DESTDIR)$(ipsec_templates_staticdir)" @@ -561,23 +660,6 @@ uninstall-ipsec_templates_staticDATA: echo " rm -f '$(DESTDIR)$(ipsec_templates_staticdir)/$$f'"; \ rm -f "$(DESTDIR)$(ipsec_templates_staticdir)/$$f"; \ done -install-ipsec_templates_statusDATA: $(ipsec_templates_status_DATA) - @$(NORMAL_INSTALL) - test -z "$(ipsec_templates_statusdir)" || $(MKDIR_P) "$(DESTDIR)$(ipsec_templates_statusdir)" - @list='$(ipsec_templates_status_DATA)'; for p in $$list; do \ - if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ - f=$(am__strip_dir) \ - echo " $(ipsec_templates_statusDATA_INSTALL) '$$d$$p' '$(DESTDIR)$(ipsec_templates_statusdir)/$$f'"; \ - $(ipsec_templates_statusDATA_INSTALL) "$$d$$p" "$(DESTDIR)$(ipsec_templates_statusdir)/$$f"; \ - done - -uninstall-ipsec_templates_statusDATA: - @$(NORMAL_UNINSTALL) - @list='$(ipsec_templates_status_DATA)'; for p in $$list; do \ - f=$(am__strip_dir) \ - echo " rm -f '$(DESTDIR)$(ipsec_templates_statusdir)/$$f'"; \ - rm -f "$(DESTDIR)$(ipsec_templates_statusdir)/$$f"; \ - done ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -657,7 +739,7 @@ check-am: all-am check: check-am all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(ipsecdir)" "$(DESTDIR)$(ipsecdir)" "$(DESTDIR)$(ipsec_templatesdir)" "$(DESTDIR)$(ipsec_templates_authdir)" "$(DESTDIR)$(ipsec_templates_gatewaydir)" "$(DESTDIR)$(ipsec_templates_staticdir)" "$(DESTDIR)$(ipsec_templates_statusdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(ipsecdir)" "$(DESTDIR)$(ipsecdir)" "$(DESTDIR)$(ipsec_templatesdir)" "$(DESTDIR)$(ipsec_templates_authdir)" "$(DESTDIR)$(ipsec_templates_configdir)" "$(DESTDIR)$(ipsec_templates_controldir)" "$(DESTDIR)$(ipsec_templates_gatewaydir)" "$(DESTDIR)$(ipsec_templates_ikesadir)" "$(DESTDIR)$(ipsec_templates_staticdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -707,9 +789,11 @@ info-am: install-data-am: install-ipsecDATA install-ipsecPROGRAMS \ install-ipsec_templatesDATA install-ipsec_templates_authDATA \ + install-ipsec_templates_configDATA \ + install-ipsec_templates_controlDATA \ install-ipsec_templates_gatewayDATA \ - install-ipsec_templates_staticDATA \ - install-ipsec_templates_statusDATA + install-ipsec_templates_ikesaDATA \ + install-ipsec_templates_staticDATA install-dvi: install-dvi-am @@ -748,9 +832,11 @@ ps-am: uninstall-am: uninstall-ipsecDATA uninstall-ipsecPROGRAMS \ uninstall-ipsec_templatesDATA \ uninstall-ipsec_templates_authDATA \ + uninstall-ipsec_templates_configDATA \ + uninstall-ipsec_templates_controlDATA \ uninstall-ipsec_templates_gatewayDATA \ - uninstall-ipsec_templates_staticDATA \ - uninstall-ipsec_templates_statusDATA uninstall-libLTLIBRARIES + uninstall-ipsec_templates_ikesaDATA \ + uninstall-ipsec_templates_staticDATA uninstall-libLTLIBRARIES .MAKE: install-am install-strip @@ -763,9 +849,11 @@ uninstall-am: uninstall-ipsecDATA uninstall-ipsecPROGRAMS \ install-exec-am install-html install-html-am install-info \ install-info-am install-ipsecDATA install-ipsecPROGRAMS \ install-ipsec_templatesDATA install-ipsec_templates_authDATA \ + install-ipsec_templates_configDATA \ + install-ipsec_templates_controlDATA \ install-ipsec_templates_gatewayDATA \ - install-ipsec_templates_staticDATA \ - install-ipsec_templates_statusDATA install-libLTLIBRARIES \ + install-ipsec_templates_ikesaDATA \ + install-ipsec_templates_staticDATA install-libLTLIBRARIES \ install-man install-pdf install-pdf-am install-ps \ install-ps-am install-strip installcheck installcheck-am \ installdirs maintainer-clean maintainer-clean-generic \ @@ -774,9 +862,11 @@ uninstall-am: uninstall-ipsecDATA uninstall-ipsecPROGRAMS \ uninstall-am uninstall-ipsecDATA uninstall-ipsecPROGRAMS \ uninstall-ipsec_templatesDATA \ uninstall-ipsec_templates_authDATA \ + uninstall-ipsec_templates_configDATA \ + uninstall-ipsec_templates_controlDATA \ uninstall-ipsec_templates_gatewayDATA \ - uninstall-ipsec_templates_staticDATA \ - uninstall-ipsec_templates_statusDATA uninstall-libLTLIBRARIES + uninstall-ipsec_templates_ikesaDATA \ + uninstall-ipsec_templates_staticDATA uninstall-libLTLIBRARIES # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. diff --git a/src/manager/controller/auth_controller.c b/src/manager/controller/auth_controller.c index fd4a3c7a5..e9b86941a 100644 --- a/src/manager/controller/auth_controller.c +++ b/src/manager/controller/auth_controller.c @@ -60,7 +60,7 @@ static void check(private_auth_controller_t *this, request_t *request) if (username && password && this->manager->login(this->manager, username, password)) { - request->redirect(request, "status/ikesalist"); + request->redirect(request, "ikesa/list"); } else { diff --git a/src/manager/controller/config_controller.c b/src/manager/controller/config_controller.c new file mode 100644 index 000000000..e7941ada4 --- /dev/null +++ b/src/manager/controller/config_controller.c @@ -0,0 +1,214 @@ +/** + * @file config_controller.c + * + * @brief Implementation of config_controller_t. + * + */ + +/* + * Copyright (C) 2007 Martin Willi + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#include "config_controller.h" +#include "../manager.h" +#include "../gateway.h" + +#include + +#include + + +typedef struct private_config_controller_t private_config_controller_t; + +/** + * private data of the task manager + */ +struct private_config_controller_t { + + /** + * public functions + */ + config_controller_t public; + + /** + * manager instance + */ + manager_t *manager; +}; + +/** + * read XML of a peerconfig element and fill template + */ +static void process_peerconfig(private_config_controller_t *this, + enumerator_t *e, request_t *r) +{ + xml_t *xml; + enumerator_t *e1, *e2, *e3; + char *name, *value, *config = "", *child = "", *section = ""; + + while (e->enumerate(e, &xml, &name, &value)) + { + if (streq(name, "name")) + { + config = value; + } + else if (streq(name, "ikeconfig")) + { + e1 = xml->children(xml); + while (e1->enumerate(e1, &xml, &name, &value)) + { + if (streq(name, "local") || streq(name, "remote")) + { + if (streq(value, "0.0.0.0") || streq(value, "::")) + { + value = "%any"; + } + r->setf(r, "peercfgs.%s.ikecfg.%s=%s", config, name, value); + } + } + e1->destroy(e1); + } + else if (streq(name, "childconfiglist")) + { + e1 = xml->children(xml); + while (e1->enumerate(e1, &xml, &name, &value)) + { + if (streq(name, "childconfig")) + { + int num = 0; + + e2 = xml->children(xml); + while (e2->enumerate(e2, &xml, &name, &value)) + { + if (streq(name, "name")) + { + child = value; + } + else if (streq(name, "local") || streq(name, "remote")) + { + section = name; + e3 = xml->children(xml); + while (e3->enumerate(e3, &xml, &name, &value)) + { + if (streq(name, "network")) + { + r->setf(r, "peercfgs.%s.childcfgs.%s.%s.networks.%d=%s", + config, child, section, ++num, value); + } + } + e3->destroy(e3); + } + } + e2->destroy(e2); + } + } + e1->destroy(e1); + } + else + { + r->setf(r, "peercfgs.%s.%s=%s", config, name, value); + } + } +} + +static void list(private_config_controller_t *this, request_t *r) +{ + gateway_t *gateway; + xml_t *xml; + enumerator_t *e1, *e2; + char *name, *value; + + gateway = this->manager->select_gateway(this->manager, 0); + e1 = gateway->query_configlist(gateway); + if (e1 == NULL) + { + r->set(r, "title", "Error"); + r->set(r, "error", "querying the gateway failed"); + r->render(r, "templates/error.cs"); + } + else + { + r->set(r, "title", "Configuration overview"); + + while (e1->enumerate(e1, &xml, &name, &value)) + { + if (streq(name, "peerconfig")) + { + e2 = xml->children(xml); + process_peerconfig(this, e2, r); + e2->destroy(e2); + } + } + e1->destroy(e1); + + r->render(r, "templates/config/list.cs"); + } +} + +/** + * Implementation of controller_t.get_name + */ +static char* get_name(private_config_controller_t *this) +{ + return "config"; +} + +/** + * Implementation of controller_t.handle + */ +static void handle(private_config_controller_t *this, + request_t *request, char *action) +{ + if (!this->manager->logged_in(this->manager)) + { + return request->redirect(request, "auth/login"); + } + if (this->manager->select_gateway(this->manager, 0) == NULL) + { + return request->redirect(request, "gateway/list"); + } + if (action) + { + if (streq(action, "list")) + { + return list(this, request); + } + } + return request->redirect(request, "config/list"); +} + +/** + * Implementation of controller_t.destroy + */ +static void destroy(private_config_controller_t *this) +{ + free(this); +} + +/* + * see header file + */ +controller_t *config_controller_create(context_t *context, void *param) +{ + private_config_controller_t *this = malloc_thing(private_config_controller_t); + + this->public.controller.get_name = (char*(*)(controller_t*))get_name; + this->public.controller.handle = (void(*)(controller_t*,request_t*,char*,char*,char*,char*,char*))handle; + this->public.controller.destroy = (void(*)(controller_t*))destroy; + + this->manager = (manager_t*)context; + + return &this->public.controller; +} + diff --git a/src/manager/controller/config_controller.h b/src/manager/controller/config_controller.h new file mode 100644 index 000000000..fcf5f5c49 --- /dev/null +++ b/src/manager/controller/config_controller.h @@ -0,0 +1,47 @@ +/** + * @file config_controller.h + * + * @brief Interface of config_controller_t. + * + */ + +/* + * Copyright (C) 2007 Martin Willi + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#ifndef CONFIG_CONTROLLER_H_ +#define CONFIG_CONTROLLER_H_ + + +#include + +typedef struct config_controller_t config_controller_t; + +/** + * @brief Status controller. + */ +struct config_controller_t { + + /** + * Implements controller_t interface. + */ + controller_t controller; +}; + +/** + * @brief Create a config_controller controller instance. + */ +controller_t *config_controller_create(context_t *context, void *param); + +#endif /* CONFIG_CONTROLLER_H_ */ diff --git a/src/manager/controller/control_controller.c b/src/manager/controller/control_controller.c new file mode 100644 index 000000000..12cb5e907 --- /dev/null +++ b/src/manager/controller/control_controller.c @@ -0,0 +1,211 @@ +/** + * @file control_controller.c + * + * @brief Implementation of control_controller_t. + * + */ + +/* + * Copyright (C) 2007 Martin Willi + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#include "control_controller.h" +#include "../manager.h" +#include "../gateway.h" + +#include + +#include + + +typedef struct private_control_controller_t private_control_controller_t; + +/** + * private data of the task manager + */ +struct private_control_controller_t { + + /** + * public functions + */ + control_controller_t public; + + /** + * manager instance + */ + manager_t *manager; +}; + +/** + * handle the result of a control operation + */ +static void handle_result(private_control_controller_t *this, request_t *r, + enumerator_t *e) +{ + enumerator_t *e1; + xml_t *xml; + char *name, *value; + int num = 0; + + if (e) + { + while (e->enumerate(e, &xml, &name, &value)) + { + if (streq(name, "status")) + { + if (value && atoi(value) == 0) + { + r->set(r, "result", "Operation executed successfully:"); + } + else + { + r->set(r, "result", "Operation failed:"); + } + } + else if (streq(name, "log")) + { + e1 = xml->children(xml); + while (e1->enumerate(e1, &xml, &name, &value)) + { + if (streq(name, "item")) + { + r->setf(r, "log.%d=%s", ++num, value); + } + } + e1->destroy(e1); + } + } + e->destroy(e); + r->render(r, "templates/control/result.cs"); + } + else + { + r->set(r, "title", "Error"); + r->set(r, "error", "controlling the gateway failed"); + r->render(r, "templates/error.cs"); + } +} + +/** + * initiate an IKE or CHILD SA + */ +static void initiate(private_control_controller_t *this, request_t *r, + bool ike, char *config) +{ + gateway_t *gateway; + enumerator_t *e; + + r->setf(r, "title=Establishing %s SA %s", ike ? "IKE" : "CHILD", config); + gateway = this->manager->select_gateway(this->manager, 0); + e = gateway->initiate(gateway, ike, config); + handle_result(this, r, e); +} + +/** + * terminate an IKE or CHILD SA + */ +static void terminate(private_control_controller_t *this, request_t *r, + bool ike, u_int32_t id) +{ + gateway_t *gateway; + enumerator_t *e; + + r->setf(r, "title=Terminate %s SA %d", ike ? "IKE" : "CHILD", id); + gateway = this->manager->select_gateway(this->manager, 0); + e = gateway->terminate(gateway, ike, id); + handle_result(this, r, e); +} + +/** + * Implementation of controller_t.get_name + */ +static char* get_name(private_control_controller_t *this) +{ + return "control"; +} + +/** + * Implementation of controller_t.handle + */ +static void handle(private_control_controller_t *this, + request_t *request, char *action, char *str) +{ + if (!this->manager->logged_in(this->manager)) + { + return request->redirect(request, "auth/login"); + } + if (this->manager->select_gateway(this->manager, 0) == NULL) + { + return request->redirect(request, "gateway/list"); + } + if (action) + { + u_int32_t id; + + if (streq(action, "terminateike")) + { + if (str && (id = atoi(str))) + { + return terminate(this, request, TRUE, id); + } + } + if (streq(action, "terminatechild")) + { + if (str && (id = atoi(str))) + { + return terminate(this, request, FALSE, id); + } + } + if (streq(action, "initiateike")) + { + if (str) + { + return initiate(this, request, TRUE, str); + } + } + if (streq(action, "initiatechild")) + { + if (str) + { + return initiate(this, request, FALSE, str); + } + } + } + return request->redirect(request, "ikesa/list"); +} + +/** + * Implementation of controller_t.destroy + */ +static void destroy(private_control_controller_t *this) +{ + free(this); +} + +/* + * see header file + */ +controller_t *control_controller_create(context_t *context, void *param) +{ + private_control_controller_t *this = malloc_thing(private_control_controller_t); + + this->public.controller.get_name = (char*(*)(controller_t*))get_name; + this->public.controller.handle = (void(*)(controller_t*,request_t*,char*,char*,char*,char*,char*))handle; + this->public.controller.destroy = (void(*)(controller_t*))destroy; + + this->manager = (manager_t*)context; + + return &this->public.controller; +} + diff --git a/src/manager/controller/control_controller.h b/src/manager/controller/control_controller.h new file mode 100644 index 000000000..6a55170aa --- /dev/null +++ b/src/manager/controller/control_controller.h @@ -0,0 +1,47 @@ +/** + * @file control_controller.h + * + * @brief Interface of control_controller_t. + * + */ + +/* + * Copyright (C) 2007 Martin Willi + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#ifndef CONTROL_CONTROLLER_H_ +#define CONTROL_CONTROLLER_H_ + + +#include + +typedef struct control_controller_t control_controller_t; + +/** + * @brief Status controller. + */ +struct control_controller_t { + + /** + * Implements controller_t interface. + */ + controller_t controller; +}; + +/** + * @brief Create a control_controller controller instance. + */ +controller_t *control_controller_create(context_t *context, void *param); + +#endif /* CONTROL_CONTROLLER_H_ */ diff --git a/src/manager/controller/gateway_controller.c b/src/manager/controller/gateway_controller.c index bdc779256..dff1cf3cf 100644 --- a/src/manager/controller/gateway_controller.c +++ b/src/manager/controller/gateway_controller.c @@ -82,7 +82,7 @@ static void _select(private_gateway_controller_t *this, request_t *request) { if (this->manager->select_gateway(this->manager, atoi(id))) { - request->redirect(request, "status/ikesalist"); + request->redirect(request, "ikesa/list"); return; } } diff --git a/src/manager/controller/ikesa_controller.c b/src/manager/controller/ikesa_controller.c new file mode 100644 index 000000000..2b282b79c --- /dev/null +++ b/src/manager/controller/ikesa_controller.c @@ -0,0 +1,238 @@ +/** + * @file ikesa_controller.c + * + * @brief Implementation of ikesa_controller_t. + * + */ + +/* + * Copyright (C) 2007 Martin Willi + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#include "ikesa_controller.h" +#include "../manager.h" +#include "../gateway.h" + +#include + +#include + + +typedef struct private_ikesa_controller_t private_ikesa_controller_t; + +/** + * private data of the task manager + */ +struct private_ikesa_controller_t { + + /** + * public functions + */ + ikesa_controller_t public; + + /** + * manager instance + */ + manager_t *manager; +}; + +/** + * read XML of a childsa element and fill template + */ +static void process_childsa(private_ikesa_controller_t *this, char *id, + enumerator_t *e, request_t *r) +{ + xml_t *xml; + enumerator_t *e1, *e2; + char *name, *value, *reqid = "", *section = ""; + int num = 0; + + while (e->enumerate(e, &xml, &name, &value)) + { + if (streq(name, "reqid")) + { + reqid = value; + } + else if (streq(name, "local") || streq(name, "remote")) + { + section = name; + e1 = xml->children(xml); + while (e1->enumerate(e1, &xml, &name, &value)) + { + if (streq(name, "networks")) + { + e2 = xml->children(xml); + while (e2->enumerate(e2, &xml, &name, &value)) + { + if (streq(name, "network")) + { + r->setf(r, "ikesas.%s.childsas.%s.%s.networks.%d=%s", + id, reqid, section, ++num, value); + } + } + e2->destroy(e2); + } + else + { + r->setf(r, "ikesas.%s.childsas.%s.%s.%s=%s", + id, reqid, section, name, value); + } + } + e1->destroy(e1); + } + else + { + r->setf(r, "ikesas.%s.childsas.%s.%s=%s", + id, reqid, name, value); + } + } +} + +/** + * read XML of a ikesa element and fill template + */ +static void process_ikesa(private_ikesa_controller_t *this, + enumerator_t *e, request_t *r) +{ + xml_t *xml; + enumerator_t *e1, *e2; + char *name, *value, *id = "", *section = ""; + + while (e->enumerate(e, &xml, &name, &value)) + { + if (streq(name, "id")) + { + id = value; + } + else if (streq(name, "local") || streq(name, "remote")) + { + section = name; + e1 = xml->children(xml); + while (e1->enumerate(e1, &xml, &name, &value)) + { + r->setf(r, "ikesas.%s.%s.%s=%s", id, section, name, value); + } + e1->destroy(e1); + } + else if (streq(name, "childsalist")) + { + e1 = xml->children(xml); + while (e1->enumerate(e1, &xml, &name, &value)) + { + if (streq(name, "childsa")) + { + e2 = xml->children(xml); + process_childsa(this, id, e2, r); + e2->destroy(e2); + } + } + e1->destroy(e1); + } + else + { + r->setf(r, "ikesas.%s.%s=%s", id, name, value); + } + } +} + +static void list(private_ikesa_controller_t *this, request_t *r) +{ + gateway_t *gateway; + xml_t *xml; + enumerator_t *e1, *e2; + char *name, *value; + + gateway = this->manager->select_gateway(this->manager, 0); + e1 = gateway->query_ikesalist(gateway); + if (e1 == NULL) + { + r->set(r, "title", "Error"); + r->set(r, "error", "querying the gateway failed"); + r->render(r, "templates/error.cs"); + } + else + { + r->set(r, "title", "IKE SA overview"); + + while (e1->enumerate(e1, &xml, &name, &value)) + { + if (streq(name, "ikesa")) + { + e2 = xml->children(xml); + process_ikesa(this, e2, r); + e2->destroy(e2); + } + } + e1->destroy(e1); + + r->render(r, "templates/ikesa/list.cs"); + } +} + +/** + * Implementation of controller_t.get_name + */ +static char* get_name(private_ikesa_controller_t *this) +{ + return "ikesa"; +} + +/** + * Implementation of controller_t.handle + */ +static void handle(private_ikesa_controller_t *this, + request_t *request, char *action) +{ + if (!this->manager->logged_in(this->manager)) + { + return request->redirect(request, "auth/login"); + } + if (this->manager->select_gateway(this->manager, 0) == NULL) + { + return request->redirect(request, "gateway/list"); + } + if (action) + { + if (streq(action, "list")) + { + return list(this, request); + } + } + return request->redirect(request, "ikesa/list"); +} + +/** + * Implementation of controller_t.destroy + */ +static void destroy(private_ikesa_controller_t *this) +{ + free(this); +} + +/* + * see header file + */ +controller_t *ikesa_controller_create(context_t *context, void *param) +{ + private_ikesa_controller_t *this = malloc_thing(private_ikesa_controller_t); + + this->public.controller.get_name = (char*(*)(controller_t*))get_name; + this->public.controller.handle = (void(*)(controller_t*,request_t*,char*,char*,char*,char*,char*))handle; + this->public.controller.destroy = (void(*)(controller_t*))destroy; + + this->manager = (manager_t*)context; + + return &this->public.controller; +} + diff --git a/src/manager/controller/ikesa_controller.h b/src/manager/controller/ikesa_controller.h new file mode 100644 index 000000000..753cccad1 --- /dev/null +++ b/src/manager/controller/ikesa_controller.h @@ -0,0 +1,47 @@ +/** + * @file ikesa_controller.h + * + * @brief Interface of ikesa_controller_t. + * + */ + +/* + * Copyright (C) 2007 Martin Willi + * Hochschule fuer Technik Rapperswil + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#ifndef IKESA_CONTROLLER_H_ +#define IKESA_CONTROLLER_H_ + + +#include + +typedef struct ikesa_controller_t ikesa_controller_t; + +/** + * @brief Status controller. + */ +struct ikesa_controller_t { + + /** + * Implements controller_t interface. + */ + controller_t controller; +}; + +/** + * @brief Create a ikesa_controller controller instance. + */ +controller_t *ikesa_controller_create(context_t *context, void *param); + +#endif /* IKESA_CONTROLLER_H_ */ diff --git a/src/manager/controller/status_controller.c b/src/manager/controller/status_controller.c deleted file mode 100644 index bcdbd26ea..000000000 --- a/src/manager/controller/status_controller.c +++ /dev/null @@ -1,238 +0,0 @@ -/** - * @file status_controller.c - * - * @brief Implementation of status_controller_t. - * - */ - -/* - * Copyright (C) 2007 Martin Willi - * Hochschule fuer Technik Rapperswil - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. See . - * - * This program is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY - * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - * for more details. - */ - -#include "status_controller.h" -#include "../manager.h" -#include "../gateway.h" - -#include - -#include - - -typedef struct private_status_controller_t private_status_controller_t; - -/** - * private data of the task manager - */ -struct private_status_controller_t { - - /** - * public functions - */ - status_controller_t public; - - /** - * manager instance - */ - manager_t *manager; -}; - -/** - * read XML of a childsa element and fill template - */ -static void process_childsa(private_status_controller_t *this, char *id, - enumerator_t *e, request_t *r) -{ - xml_t *xml; - enumerator_t *e1, *e2; - char *name, *value, *reqid = "", *section = ""; - int num = 0; - - while (e->enumerate(e, &xml, &name, &value)) - { - if (streq(name, "reqid")) - { - reqid = value; - } - else if (streq(name, "local") || streq(name, "remote")) - { - section = name; - e1 = xml->children(xml); - while (e1->enumerate(e1, &xml, &name, &value)) - { - if (streq(name, "networks")) - { - e2 = xml->children(xml); - while (e2->enumerate(e2, &xml, &name, &value)) - { - if (streq(name, "network")) - { - r->setf(r, "ikesas.%s.childsas.%s.%s.networks.%d=%s", - id, reqid, section, ++num, value); - } - } - e2->destroy(e2); - } - else - { - r->setf(r, "ikesas.%s.childsas.%s.%s.%s=%s", - id, reqid, section, name, value); - } - } - e1->destroy(e1); - } - else - { - r->setf(r, "ikesas.%s.childsas.%s.%s=%s", - id, reqid, name, value); - } - } -} - -/** - * read XML of a ikesa element and fill template - */ -static void process_ikesa(private_status_controller_t *this, - enumerator_t *e, request_t *r) -{ - xml_t *xml; - enumerator_t *e1, *e2; - char *name, *value, *id = "", *section = ""; - - while (e->enumerate(e, &xml, &name, &value)) - { - if (streq(name, "id")) - { - id = value; - } - else if (streq(name, "local") || streq(name, "remote")) - { - section = name; - e1 = xml->children(xml); - while (e1->enumerate(e1, &xml, &name, &value)) - { - r->setf(r, "ikesas.%s.%s.%s=%s", id, section, name, value); - } - e1->destroy(e1); - } - else if (streq(name, "childsalist")) - { - e1 = xml->children(xml); - while (e1->enumerate(e1, &xml, &name, &value)) - { - if (streq(name, "childsa")) - { - e2 = xml->children(xml); - process_childsa(this, id, e2, r); - e2->destroy(e2); - } - } - e1->destroy(e1); - } - else - { - r->setf(r, "ikesas.%s.%s=%s", id, name, value); - } - } -} - -static void ikesalist(private_status_controller_t *this, request_t *r) -{ - gateway_t *gateway; - xml_t *xml; - enumerator_t *e1, *e2; - char *name, *value; - - gateway = this->manager->select_gateway(this->manager, 0); - e1 = gateway->query_ikesalist(gateway); - if (e1 == NULL) - { - r->set(r, "title", "Error"); - r->set(r, "error", "querying the gateway failed"); - r->render(r, "templates/error.cs"); - } - else - { - r->set(r, "title", "IKE SA overview"); - - while (e1->enumerate(e1, &xml, &name, &value)) - { - if (streq(name, "ikesa")) - { - e2 = xml->children(xml); - process_ikesa(this, e2, r); - e2->destroy(e2); - } - } - e1->destroy(e1); - - r->render(r, "templates/status/ikesalist.cs"); - } -} - -/** - * Implementation of controller_t.get_name - */ -static char* get_name(private_status_controller_t *this) -{ - return "status"; -} - -/** - * Implementation of controller_t.handle - */ -static void handle(private_status_controller_t *this, - request_t *request, char *action) -{ - if (!this->manager->logged_in(this->manager)) - { - return request->redirect(request, "auth/login"); - } - if (this->manager->select_gateway(this->manager, 0) == NULL) - { - return request->redirect(request, "gateway/list"); - } - if (action) - { - if (streq(action, "ikesalist")) - { - return ikesalist(this, request); - } - } - return request->redirect(request, "status/ikesalist"); -} - -/** - * Implementation of controller_t.destroy - */ -static void destroy(private_status_controller_t *this) -{ - free(this); -} - -/* - * see header file - */ -controller_t *status_controller_create(context_t *context, void *param) -{ - private_status_controller_t *this = malloc_thing(private_status_controller_t); - - this->public.controller.get_name = (char*(*)(controller_t*))get_name; - this->public.controller.handle = (void(*)(controller_t*,request_t*,char*,char*,char*,char*,char*))handle; - this->public.controller.destroy = (void(*)(controller_t*))destroy; - - this->manager = (manager_t*)context; - - return &this->public.controller; -} - diff --git a/src/manager/controller/status_controller.h b/src/manager/controller/status_controller.h deleted file mode 100644 index a736dda83..000000000 --- a/src/manager/controller/status_controller.h +++ /dev/null @@ -1,47 +0,0 @@ -/** - * @file status_controller.h - * - * @brief Interface of status_controller_t. - * - */ - -/* - * Copyright (C) 2007 Martin Willi - * Hochschule fuer Technik Rapperswil - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. See . - * - * This program is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY - * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - * for more details. - */ - -#ifndef STATUS_CONTROLLER_H_ -#define STATUS_CONTROLLER_H_ - - -#include - -typedef struct status_controller_t status_controller_t; - -/** - * @brief Status controller. - */ -struct status_controller_t { - - /** - * Implements controller_t interface. - */ - controller_t controller; -}; - -/** - * @brief Create a status_controller controller instance. - */ -controller_t *status_controller_create(context_t *context, void *param); - -#endif /* STATUS_CONTROLLER_H_ */ diff --git a/src/manager/gateway.c b/src/manager/gateway.c index 5f5a4b477..d4eb5279e 100644 --- a/src/manager/gateway.c +++ b/src/manager/gateway.c @@ -57,6 +57,11 @@ struct private_gateway_t { * socket file descriptor, > 0 if connected */ int fd; + + /** + * unique id assigned to each xml message + */ + int xmlid; }; struct sockaddr_un unix_addr = { AF_UNIX, IPSEC_PIDDIR "/charon.xml"}; @@ -103,7 +108,7 @@ static bool connect_(private_gateway_t *this) /** * Implementation of gateway_t.request. */ -static char* request(private_gateway_t *this, char *xml) +static char* request(private_gateway_t *this, char *xml, ...) { if (this->fd < 0) { @@ -116,18 +121,25 @@ static char* request(private_gateway_t *this, char *xml) { char buf[8096]; ssize_t len; + va_list args; - len = strlen(xml); - if (send(this->fd, xml, len, 0) != len) + va_start(args, xml); + len = vsnprintf(buf, sizeof(buf), xml, args); + va_end(args); + if (len < 0 || len >= sizeof(buf)) { return NULL; } - len = recv(this->fd, buf, sizeof(buf) - 1, 0); - if (len < 0) + if (send(this->fd, buf, len, 0) != len) { - return NULL; + if (!connect_(this)) + { + return NULL; + } + continue; } - if (len == 0) + len = recv(this->fd, buf, sizeof(buf) - 1, 0); + if (len <= 0) { if (!connect_(this)) { @@ -149,11 +161,11 @@ static enumerator_t* query_ikesalist(private_gateway_t *this) xml_t *xml; enumerator_t *e1, *e2, *e3, *e4 = NULL; - str = request(this, "" + str = request(this, "" "" "" "" - ""); + "", this->xmlid++); if (str == NULL) { return NULL; @@ -197,6 +209,152 @@ static enumerator_t* query_ikesalist(private_gateway_t *this) return NULL; } + +/** + * Implementation of gateway_t.query_configlist. + */ +static enumerator_t* query_configlist(private_gateway_t *this) +{ + char *str, *name, *value; + xml_t *xml; + enumerator_t *e1, *e2, *e3, *e4 = NULL; + + str = request(this, "" + "" + "" + "" + "", this->xmlid++); + if (str == NULL) + { + return NULL; + } + xml = xml_create(str); + if (xml == NULL) + { + return NULL; + } + + e1 = xml->children(xml); + free(str); + while (e1->enumerate(e1, &xml, &name, &value)) + { + if (streq(name, "message")) + { + e2 = xml->children(xml); + while (e2->enumerate(e2, &xml, &name, &value)) + { + if (streq(name, "query")) + { + e3 = xml->children(xml); + while (e3->enumerate(e3, &xml, &name, &value)) + { + if (streq(name, "configlist")) + { + e4 = xml->children(xml); + e1->destroy(e1); + e2->destroy(e2); + e3->destroy(e3); + return e4; + } + } + e3->destroy(e3); + } + } + e2->destroy(e2); + } + } + e1->destroy(e1); + return NULL; +} + +/** + * create enumerator over control elements children of a control response + */ +static enumerator_t* read_result(private_gateway_t *this, char *res) +{ + char *name, *value; + xml_t *xml; + enumerator_t *e1, *e2, *e3; + + if (res == NULL) + { + return NULL; + } + xml = xml_create(res); + if (xml == NULL) + { + return NULL; + } + e1 = xml->children(xml); + free(res); + while (e1->enumerate(e1, &xml, &name, &value)) + { + if (streq(name, "message")) + { + e2 = xml->children(xml); + while (e2->enumerate(e2, &xml, &name, &value)) + { + if (streq(name, "control")) + { + e3 = xml->children(xml); + e1->destroy(e1); + e2->destroy(e2); + return e3; + } + } + e2->destroy(e2); + } + } + e1->destroy(e1); + return NULL; +} + +/** + * Implementation of gateway_t.initiate. + */ +static enumerator_t* initiate(private_gateway_t *this, bool ike, char *name) +{ + char *str, *kind; + + if (ike) + { + kind = "ike"; + } + else + { + kind = "child"; + } + str = request(this, "" + "" + "<%ssainitiate>%s" + "" + "", this->xmlid++, kind, name, kind); + return read_result(this, str); +} + +/** + * Implementation of gateway_t.terminate. + */ +static enumerator_t* terminate(private_gateway_t *this, bool ike, u_int32_t id) +{ + char *str, *kind; + + if (ike) + { + kind = "ike"; + } + else + { + kind = "child"; + } + str = request(this, "" + "" + "<%ssaterminate>%d" + "" + "", this->xmlid++, kind, id, kind); + return read_result(this, str); +} + /** * Implementation of gateway_t.destroy */ @@ -220,11 +378,15 @@ static private_gateway_t *gateway_create(char *name) this->public.request = (char*(*)(gateway_t*, char *xml))request; this->public.query_ikesalist = (enumerator_t*(*)(gateway_t*))query_ikesalist; + this->public.query_configlist = (enumerator_t*(*)(gateway_t*))query_configlist; + this->public.initiate = (enumerator_t*(*)(gateway_t*, bool ike, char *name))initiate; + this->public.terminate = (enumerator_t*(*)(gateway_t*, bool ike, u_int32_t id))terminate; this->public.destroy = (void(*)(gateway_t*))destroy; this->name = strdup(name); this->host = NULL; this->fd = -1; + this->xmlid = 1; return this; } diff --git a/src/manager/gateway.h b/src/manager/gateway.h index 1fe2aef4b..81d8b9c3f 100644 --- a/src/manager/gateway.h +++ b/src/manager/gateway.h @@ -48,6 +48,31 @@ struct gateway_t { */ enumerator_t* (*query_ikesalist)(gateway_t *this); + /** + * @brief Query the list of peer configs and its subconfigs. + * + * @return enumerator over peerconfig XML elements + */ + enumerator_t* (*query_configlist)(gateway_t *this); + + /** + * @brief Terminate an IKE or a CHILD SA. + * + * @param ike TRUE for IKE-, FALSE for a CHILD-SA + * @param id ID of the SA to terminate + * @return enumerator over control response XML children + */ + enumerator_t* (*terminate)(gateway_t *this, bool ike, u_int32_t id); + + /** + * @brief Initiate an IKE or a CHILD SA. + * + * @param ike TRUE for IKE-, FALSE for CHILD-SA + * @param name name of the peer/child config + * @return enumerator over control response XML children + */ + enumerator_t* (*initiate)(gateway_t *this, bool ike, char *name); + /** * @brief Destroy a gateway instance. */ diff --git a/src/manager/lib/dispatcher.c b/src/manager/lib/dispatcher.c index df669ceb6..ce53d39ea 100644 --- a/src/manager/lib/dispatcher.c +++ b/src/manager/lib/dispatcher.c @@ -30,6 +30,7 @@ #include #include +#include #include typedef struct private_dispatcher_t private_dispatcher_t; @@ -122,8 +123,8 @@ typedef struct { session_t *session; /** condvar to wait for session */ pthread_cond_t cond; - /** number of threads waiting for session */ - int waiting; + /** TRUE if session is in use */ + bool in_use; /** last use of the session */ time_t used; } session_entry_t; @@ -164,7 +165,7 @@ static session_entry_t *session_entry_create(private_dispatcher_t *this) session_entry_t *entry; entry = malloc_thing(session_entry_t); - entry->waiting = 1; + entry->in_use = FALSE; pthread_cond_init(&entry->cond, NULL); entry->session = load_session(this); entry->used = time(NULL); @@ -228,11 +229,12 @@ static void dispatch(private_dispatcher_t *this) now = time(NULL); /* find session */ - iterator = this->sessions->create_iterator_locked(this->sessions, &this->mutex); + pthread_mutex_lock(&this->mutex); + iterator = this->sessions->create_iterator(this->sessions, TRUE); while (iterator->iterate(iterator, (void**)¤t)) { /* check all sessions for timeout */ - if (current->waiting == 0 && + if (!current->in_use && current->used < now - this->timeout) { iterator->remove(iterator); @@ -243,27 +245,24 @@ static void dispatch(private_dispatcher_t *this) streq(current->session->get_sid(current->session), sid)) { found = current; - found->waiting++; } } iterator->destroy(iterator); if (found) { /* wait until session is unused */ - pthread_mutex_lock(&this->mutex); - while (found->waiting > 1) + while (found->in_use) { pthread_cond_wait(&found->cond, &this->mutex); } - pthread_mutex_unlock(&this->mutex); } else { /* create a new session if not found */ found = session_entry_create(this); - pthread_mutex_lock(&this->mutex); this->sessions->insert_first(this->sessions, found); - pthread_mutex_unlock(&this->mutex); } + found->in_use = TRUE; + pthread_mutex_unlock(&this->mutex); /* start processing */ found->session->process(found->session, request); @@ -271,7 +270,7 @@ static void dispatch(private_dispatcher_t *this) /* release session */ pthread_mutex_lock(&this->mutex); - found->waiting--; + found->in_use = FALSE; pthread_cond_signal(&found->cond); pthread_mutex_unlock(&this->mutex); diff --git a/src/manager/lib/request.c b/src/manager/lib/request.c index 4623b3860..2e18bded5 100644 --- a/src/manager/lib/request.c +++ b/src/manager/lib/request.c @@ -179,12 +179,18 @@ static void add_cookie(private_request_t *this, char *name, char *value) /** * Implementation of request_t.redirect. */ -static void redirect(private_request_t *this, char *location) +static void redirect(private_request_t *this, char *fmt, ...) { + va_list args; + FCGX_FPrintF(this->req->out, "Status: 303 See Other\n"); - FCGX_FPrintF(this->req->out, "Location: %s%s%s\n\n", + FCGX_FPrintF(this->req->out, "Location: %s%s", FCGX_GetParam("SCRIPT_NAME", this->req->envp), - *location == '/' ? "" : "/", location); + *fmt == '/' ? "" : "/"); + va_start(args, fmt); + FCGX_VFPrintF(this->req->out, fmt, args); + va_end(args); + FCGX_FPrintF(this->req->out, "\n\n"); } /** @@ -195,6 +201,16 @@ static char* get_base(private_request_t *this) return FCGX_GetParam("SCRIPT_NAME", this->req->envp); } +/** + * Implementation of request_t.serve. + */ +static void serve(private_request_t *this, char *headers, chunk_t chunk) +{ + FCGX_FPrintF(this->req->out, "%s\n\n", headers); + + FCGX_PutStr(chunk.ptr, chunk.len, this->req->out); +} + /** * Implementation of request_t.render. */ @@ -254,8 +270,9 @@ request_t *request_create(FCGX_Request *request, bool debug) this->public.add_cookie = (void(*)(request_t*, char *name, char *value))add_cookie; this->public.get_cookie = (char*(*)(request_t*,char*))get_cookie; this->public.get_query_data = (char*(*)(request_t*, char *name))get_query_data; - this->public.redirect = (void(*)(request_t*, char *location))redirect; + this->public.redirect = (void(*)(request_t*, char *fmt,...))redirect; this->public.render = (void(*)(request_t*,char*))render; + this->public.serve = (void(*)(request_t*,char*,chunk_t))serve; this->public.set = (void(*)(request_t*, char *, char*))set; this->public.setf = (void(*)(request_t*, char *format, ...))setf; this->public.destroy = (void(*)(request_t*))destroy; diff --git a/src/manager/lib/request.h b/src/manager/lib/request.h index e6fd71e71..f78741d37 100644 --- a/src/manager/lib/request.h +++ b/src/manager/lib/request.h @@ -75,9 +75,10 @@ struct request_t { /** * @brief Redirect the client to another location. * - * @param location location to redirect to + * @param fmt location format string + * @param ... variable argument for fmt */ - void (*redirect)(request_t *this, char *location); + void (*redirect)(request_t *this, char *fmt, ...); /** * @brief Set a template value. @@ -106,10 +107,17 @@ struct request_t { * other targets without to worry about path location. * * @param template clearsilver template file location - * @return rendered template string */ void (*render)(request_t *this, char *template); + /** + * @brief Serve a request with headers and a body. + * + * @param headers HTTP headers, \n separated + * @param chunk body to write to output + */ + void (*serve)(request_t *this, char *headers, chunk_t chunk); + /** * @brief Destroy the request_t. */ diff --git a/src/manager/main.c b/src/manager/main.c index bbe07cbf3..eb4654ced 100644 --- a/src/manager/main.c +++ b/src/manager/main.c @@ -26,11 +26,13 @@ #include "manager.h" #include "database.h" #include "controller/auth_controller.h" -#include "controller/status_controller.h" +#include "controller/ikesa_controller.h" #include "controller/gateway_controller.h" +#include "controller/control_controller.h" +#include "controller/config_controller.h" #define DBFILE IPSECDIR "/manager.db" -#define SESSION_TIMEOUT 180 +#define SESSION_TIMEOUT 900 #define THREADS 10 int main (int arc, char *argv[]) @@ -52,9 +54,11 @@ int main (int arc, char *argv[]) dispatcher = dispatcher_create(socket, SESSION_TIMEOUT, (context_constructor_t)manager_create, database); - dispatcher->add_controller(dispatcher, status_controller_create, NULL); + dispatcher->add_controller(dispatcher, ikesa_controller_create, NULL); dispatcher->add_controller(dispatcher, gateway_controller_create, NULL); dispatcher->add_controller(dispatcher, auth_controller_create, NULL); + dispatcher->add_controller(dispatcher, control_controller_create, NULL); + dispatcher->add_controller(dispatcher, config_controller_create, NULL); dispatcher->run(dispatcher, THREADS, NULL, NULL, NULL, NULL); diff --git a/src/manager/templates/config/list.cs b/src/manager/templates/config/list.cs new file mode 100644 index 000000000..e71830d4d --- /dev/null +++ b/src/manager/templates/config/list.cs @@ -0,0 +1,104 @@ + + +
+

: + <-> + +

+
+ + + + + +   + +
+
+
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+ + + + +
+ + + + + + + 0123456789abdcef


+ +
+ + + + + + + 0123456789abcdef


+ +
+ + + + + +
+

:

+
+ + + + + +

+ +

+ +
+


+
+ +


+
+ +

+ +
+
+
+ + diff --git a/src/manager/templates/control/result.cs b/src/manager/templates/control/result.cs new file mode 100644 index 000000000..1d59df65f --- /dev/null +++ b/src/manager/templates/control/result.cs @@ -0,0 +1,14 @@ + +
+

+
 
+
+
+
    + +
  • + +
+
+
+ diff --git a/src/manager/templates/header.cs b/src/manager/templates/header.cs index 64a859a9a..bacd833e0 100644 --- a/src/manager/templates/header.cs +++ b/src/manager/templates/header.cs @@ -9,13 +9,15 @@
- +

strongSwan Manager

diff --git a/src/manager/templates/ikesa/list.cs b/src/manager/templates/ikesa/list.cs new file mode 100644 index 000000000..f9a8e5c68 --- /dev/null +++ b/src/manager/templates/ikesa/list.cs @@ -0,0 +1,111 @@ + + +
+

+ [IKE #]: + <-> + +

+
+ + + +
+
+
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+ + + + +
+ + + + + + +


+ +
+ + + + + + + + + + + + + + + + + + +


+ +
+ + + + + +
+

[IPsec #]:

+
+ + + +

+ +

+ +
+ <-


+
+ + ->


+
+ +

+ +
+
+
+ + diff --git a/src/manager/templates/static/close.png b/src/manager/templates/static/close.png new file mode 100644 index 000000000..7cb058d69 Binary files /dev/null and b/src/manager/templates/static/close.png differ diff --git a/src/manager/templates/static/initiate.png b/src/manager/templates/static/initiate.png new file mode 100644 index 000000000..4463e3b7a Binary files /dev/null and b/src/manager/templates/static/initiate.png differ diff --git a/src/manager/templates/static/pipe-thin-green.png b/src/manager/templates/static/pipe-thin-green.png new file mode 100644 index 000000000..df3026ec5 Binary files /dev/null and b/src/manager/templates/static/pipe-thin-green.png differ diff --git a/src/manager/templates/static/pipe-thin-left-green.png b/src/manager/templates/static/pipe-thin-left-green.png new file mode 100644 index 000000000..b76432a94 Binary files /dev/null and b/src/manager/templates/static/pipe-thin-left-green.png differ diff --git a/src/manager/templates/static/pipe-thin-right-green.png b/src/manager/templates/static/pipe-thin-right-green.png new file mode 100644 index 000000000..f193af9cc Binary files /dev/null and b/src/manager/templates/static/pipe-thin-right-green.png differ diff --git a/src/manager/templates/static/script.js b/src/manager/templates/static/script.js index 7b2a5823c..c9105c372 100644 --- a/src/manager/templates/static/script.js +++ b/src/manager/templates/static/script.js @@ -1,8 +1,7 @@ $(function(){ - $(".expand > div").hide(); $(".expand > h1").toggle( - function(){$(this).parent(".expand").find("div").slideDown('fast');}, - function(){$(this).parent(".expand").find("div").slideUp('fast');} + function(){$(this).parent(".expand").find(".expander").slideUp('fast');}, + function(){$(this).parent(".expand").find(".expander").slideDown('fast');} ); }); diff --git a/src/manager/templates/static/style.css b/src/manager/templates/static/style.css index 8a7f4960d..9550b8291 100644 --- a/src/manager/templates/static/style.css +++ b/src/manager/templates/static/style.css @@ -57,6 +57,8 @@ a img { font-size: 1em; cursor: pointer; margin: 0; + float: left; + padding-top: 3px; } .expand h1 span { @@ -64,6 +66,15 @@ a img { margin-right: 2em; } +.expander { + clear:left; +} + +.controls { + margin-top: 3px; + text-align: right; +} + .center { text-align: center; } diff --git a/src/manager/templates/status/ikesalist.cs b/src/manager/templates/status/ikesalist.cs deleted file mode 100644 index 2238aafd3..000000000 --- a/src/manager/templates/status/ikesalist.cs +++ /dev/null @@ -1,101 +0,0 @@ - - -
-

- IKE # []: - <-> - -

-
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
- - - - -
- - - - - - -


- -
- - - - - - - - - - - - - - - - - - -


- -
- - - - - -
-

IPsec # []:

-

- -

- -
- <-


-
- - ->


-
- -

- -
-
-
- - diff --git a/src/pluto/Makefile.am b/src/pluto/Makefile.am index 4519ef7bb..69902ad8f 100644 --- a/src/pluto/Makefile.am +++ b/src/pluto/Makefile.am @@ -132,15 +132,3 @@ if USE_LIBLDAP pluto_LDADD += -lldap -llber endif -install-exec-local : - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/cacerts - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/ocspcerts - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/certs - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/acerts - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/aacerts - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/crls - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/reqs - mkdir -p -m 700 $(DESTDIR)$(confdir)/ipsec.d/private - chown -R $(ipsecuid):$(ipsecgid) $(DESTDIR)$(confdir)/ipsec.d - diff --git a/src/pluto/Makefile.in b/src/pluto/Makefile.in index 8f7a7f31b..77a0a7548 100644 --- a/src/pluto/Makefile.in +++ b/src/pluto/Makefile.in @@ -804,7 +804,7 @@ install-data-am: install-ipsecPROGRAMS install-man install-dvi: install-dvi-am -install-exec-am: install-exec-local +install-exec-am: install-html: install-html-am @@ -847,8 +847,8 @@ uninstall-man: uninstall-man5 uninstall-man8 distclean-compile distclean-generic distclean-libtool \ distclean-tags distdir dvi dvi-am html html-am info info-am \ install install-am install-data install-data-am install-dvi \ - install-dvi-am install-exec install-exec-am install-exec-local \ - install-html install-html-am install-info install-info-am \ + install-dvi-am install-exec install-exec-am install-html \ + install-html-am install-info install-info-am \ install-ipsecPROGRAMS install-man install-man5 install-man8 \ install-pdf install-pdf-am install-ps install-ps-am \ install-strip installcheck installcheck-am installdirs \ @@ -861,18 +861,6 @@ uninstall-man: uninstall-man5 uninstall-man8 oid.o : $(LIBSTRONGSWANDIR)/asn1/oid.c $(LIBSTRONGSWANDIR)/asn1/oid.h $(COMPILE) -c -o $@ $< - -install-exec-local : - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/cacerts - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/ocspcerts - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/certs - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/acerts - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/aacerts - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/crls - mkdir -p -m 755 $(DESTDIR)$(confdir)/ipsec.d/reqs - mkdir -p -m 700 $(DESTDIR)$(confdir)/ipsec.d/private - chown -R $(ipsecuid):$(ipsecgid) $(DESTDIR)$(confdir)/ipsec.d # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. .NOEXPORT: diff --git a/src/pluto/connections.c b/src/pluto/connections.c index 952e722d2..8fbf969b6 100644 --- a/src/pluto/connections.c +++ b/src/pluto/connections.c @@ -11,7 +11,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: connections.c 3252 2007-10-06 21:24:50Z andreas $ + * RCSID $Id: connections.c 3361 2007-11-21 23:42:27Z andreas $ */ #include @@ -955,6 +955,7 @@ gen_reqid(void) } while (reqid != start); exit_log("unable to allocate reqid"); + return 0; /* never reached ... */ } void diff --git a/src/pluto/vendor.c b/src/pluto/vendor.c index b54f574f2..0e6e3d9b7 100644 --- a/src/pluto/vendor.c +++ b/src/pluto/vendor.c @@ -11,7 +11,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: vendor.c 3252 2007-10-06 21:24:50Z andreas $ + * RCSID $Id: vendor.c 3380 2007-12-04 23:54:32Z andreas $ */ #include @@ -206,7 +206,9 @@ static struct vid_struct _vid_tab[] = { /* * strongSwan */ - DEC_MD5_VID(STRONGSWAN, "strongSwan 4.1.8") + DEC_MD5_VID(STRONGSWAN, "strongSwan 4.1.10") + DEC_MD5_VID(STRONGSWAN_4_1_9, "strongSwan 4.1.9") + DEC_MD5_VID(STRONGSWAN_4_1_8, "strongSwan 4.1.8") DEC_MD5_VID(STRONGSWAN_4_1_7, "strongSwan 4.1.7") DEC_MD5_VID(STRONGSWAN_4_1_6, "strongSwan 4.1.6") DEC_MD5_VID(STRONGSWAN_4_1_5, "strongSwan 4.1.5") diff --git a/src/pluto/vendor.h b/src/pluto/vendor.h index 4f480df30..d0853b08c 100644 --- a/src/pluto/vendor.h +++ b/src/pluto/vendor.h @@ -11,7 +11,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: vendor.h 3252 2007-10-06 21:24:50Z andreas $ + * RCSID $Id: vendor.h 3380 2007-12-04 23:54:32Z andreas $ */ #ifndef _VENDOR_H_ @@ -111,6 +111,8 @@ enum known_vendorid { VID_STRONGSWAN_4_1_5 = 93, VID_STRONGSWAN_4_1_6 = 94, VID_STRONGSWAN_4_1_7 = 95, + VID_STRONGSWAN_4_1_8 = 96, + VID_STRONGSWAN_4_1_9 = 97, /* 101 - 200 : NAT-Traversal */ VID_NATT_STENBERG_01 =101, diff --git a/src/starter/confread.c b/src/starter/confread.c index e481ff7cf..7a312d893 100644 --- a/src/starter/confread.c +++ b/src/starter/confread.c @@ -11,7 +11,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: confread.c 3267 2007-10-08 19:57:54Z andreas $ + * RCSID $Id: confread.c 3405 2007-12-19 00:49:32Z andreas $ */ #include @@ -173,7 +173,7 @@ kw_end(starter_conn_t *conn, starter_end_t *end, kw_token_t token goto err; } } - else if (streq(value, "%any")) + else if (streq(value, "%any") || streq(value, "%any4")) { anyaddr(conn->addr_family, &end->addr); } @@ -509,25 +509,46 @@ load_conn(starter_conn_t *conn, kw_list_t *kw, starter_config_t *cfg) } break; case KW_EAP: - /* TODO: a gperf function for all EAP types */ + { + char *sep; + + /* check for vendor-type format */ + sep = strchr(kw->value, '-'); + if (sep) + { + *(sep++) = '\0'; + conn->eap_type = atoi(kw->value); + conn->eap_vendor = atoi(sep); + if (conn->eap_type == 0 || conn->eap_vendor == 0) + { + plog("# invalid EAP type: %s=%s", kw->entry->name, kw->value); + cfg->err++; + } + break; + } if (streq(kw->value, "aka")) { - conn->eap = 23; + conn->eap_type = 23; } else if (streq(kw->value, "sim")) { - conn->eap = 18; + conn->eap_type = 18; + } + else if (streq(kw->value, "md5")) + { + conn->eap_type = 4; } else { - conn->eap = atoi(kw->value); - if (conn->eap == 0) + conn->eap_type = atoi(kw->value); + if (conn->eap_type == 0) { plog("# unknown EAP type: %s=%s", kw->entry->name, kw->value); cfg->err++; } } break; + } case KW_KEYINGTRIES: if (streq(kw->value, "%forever")) { diff --git a/src/starter/confread.h b/src/starter/confread.h index 839f73e99..a32e7116d 100644 --- a/src/starter/confread.h +++ b/src/starter/confread.h @@ -14,7 +14,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: confread.h 3267 2007-10-08 19:57:54Z andreas $ + * RCSID $Id: confread.h 3394 2007-12-13 17:31:21Z martin $ */ #ifndef _IPSEC_CONFREAD_H_ @@ -106,7 +106,8 @@ struct starter_conn { starter_state_t state; keyexchange_t keyexchange; - int eap; + u_int32_t eap_type; + u_int32_t eap_vendor; lset_t policy; time_t sa_ike_life_seconds; time_t sa_ipsec_life_seconds; diff --git a/src/starter/invokecharon.c b/src/starter/invokecharon.c index 1cb0dfb63..111bb9c6f 100644 --- a/src/starter/invokecharon.c +++ b/src/starter/invokecharon.c @@ -14,7 +14,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: invokecharon.c 3267 2007-10-08 19:57:54Z andreas $ + * RCSID $Id: invokecharon.c 3344 2007-11-15 18:34:05Z martin $ */ #include @@ -78,9 +78,14 @@ starter_stop_charon (void) kill(pid, SIGINT); else if (i < 10) kill(pid, SIGTERM); + else if (i == 10) + { + kill(pid, SIGKILL); + plog("starter_stop_charon(): charon does not respond, sending KILL"); + } else kill(pid, SIGKILL); - usleep(20000); + usleep(200000); } if (_charon_pid == 0) return 0; diff --git a/src/starter/ipsec.conf.5 b/src/starter/ipsec.conf.5 index 1f581bce8..d542af555 100644 --- a/src/starter/ipsec.conf.5 +++ b/src/starter/ipsec.conf.5 @@ -1,5 +1,5 @@ .TH IPSEC.CONF 5 "27 Jun 2007" -.\" RCSID $Id: ipsec.conf.5 3267 2007-10-08 19:57:54Z andreas $ +.\" RCSID $Id: ipsec.conf.5 3394 2007-12-13 17:31:21Z martin $ .SH NAME ipsec.conf \- IPsec configuration and connections .SH DESCRIPTION @@ -350,13 +350,21 @@ in case of inactivity. This only applies to IKEv1, in IKEv2 the default retransmission timeout applies, as every exchange is used to detect dead peers. .TP .B eap -defines the EAP type to be used if +defines the EAP type to propose as server if the client has .B authby=eap -is selected. Acceptable values are +selected. Acceptable values are .B aka -for EAP-AKA and +for EAP-AKA, .B sim -for EAP-SIM. +for EAP-SIM and +.B md5 +for EAP-MD5. +Additionally, IANA assigned EAP method numbers are accepted, or a definition +in the form +.B eap=type-vendor +(e.g. +.B eap=7-12345 +) can be used to specify vendor specific EAP types. .TP .B esp ESP encryption/authentication algorithm to be used diff --git a/src/starter/starter.c b/src/starter/starter.c index cc591dc61..bc2e8f1df 100644 --- a/src/starter/starter.c +++ b/src/starter/starter.c @@ -11,7 +11,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: starter.c 3267 2007-10-08 19:57:54Z andreas $ + * RCSID $Id: starter.c 3369 2007-11-28 17:02:12Z andreas $ */ #include @@ -43,6 +43,19 @@ #include "cmp.h" #include "interfaces.h" +/** + * Return codes defined by Linux Standard Base Core Specification 3.1 + * in section 20.2. Init Script Actions + */ +#define LSB_RC_SUCCESS 0 /* success */ +#define LSB_RC_FAILURE 1 /* generic or unspecified error */ +#define LSB_RC_INVALID_ARGUMENT 2 /* invalid or excess argument(s) */ +#define LSB_RC_NOT_IMPLEMENTED 3 /* unimplemented feature (reload) */ +#define LSB_RC_NOT_ALLOWED 4 /* user had insufficient privilege */ +#define LSB_RC_NOT_INSTALLED 5 /* program is not installed */ +#define LSB_RC_NOT_CONFIGURED 6 /* program is not configured */ +#define LSB_RC_NOT_RUNNING 7 /* program is not running */ + #define FLAG_ACTION_START_PLUTO 0x01 #define FLAG_ACTION_UPDATE 0x02 #define FLAG_ACTION_RELOAD 0x04 @@ -131,7 +144,7 @@ usage(char *name) { fprintf(stderr, "Usage: starter [--nofork] [--auto-update ] " "[--debug|--debug-more|--debug-all]\n"); - exit(1); + exit(LSB_RC_INVALID_ARGUMENT); } int main (int argc, char **argv) @@ -205,7 +218,7 @@ int main (int argc, char **argv) if (getuid() != 0) { plog("permission denied (must be superuser)"); - exit(1); + exit(LSB_RC_NOT_ALLOWED); } if (stat(PLUTO_PID_FILE, &stb) == 0) @@ -227,13 +240,13 @@ int main (int argc, char **argv) if (stat(DEV_RANDOM, &stb) != 0) { plog("unable to start strongSwan IPsec -- no %s!", DEV_RANDOM); - exit(1); + exit(LSB_RC_FAILURE); } if (stat(DEV_URANDOM, &stb)!= 0) { plog("unable to start strongSwan IPsec -- no %s!", DEV_URANDOM); - exit(1); + exit(LSB_RC_FAILURE); } cfg = confread_load(CONFIG_FILE); @@ -244,14 +257,14 @@ int main (int argc, char **argv) { confread_free(cfg); } - exit(1); + exit(LSB_RC_INVALID_ARGUMENT); } /* determine if we have a native netkey IPsec stack */ if (!starter_netkey_init()) { plog("no netkey IPSec stack detected"); - exit(1); + exit(LSB_RC_FAILURE); } last_reload = time(NULL); @@ -259,7 +272,7 @@ int main (int argc, char **argv) if (stat(STARTER_PID_FILE, &stb) == 0) { plog("starter is already running (%s exists) -- no fork done", STARTER_PID_FILE); - exit(0); + exit(LSB_RC_SUCCESS); } /* fork if we're not debugging stuff */ @@ -287,7 +300,7 @@ int main (int argc, char **argv) plog("can't fork: %s", strerror(errno)); break; default: - exit(0); + exit(LSB_RC_SUCCESS); } } @@ -322,7 +335,7 @@ int main (int argc, char **argv) #endif /* LEAK_DETECTIVE */ close_log(); plog("ipsec starter stopped"); - exit(0); + exit(LSB_RC_SUCCESS); } /* @@ -643,7 +656,6 @@ int main (int argc, char **argv) _action_ |= FLAG_ACTION_UPDATE; } } - - return 0; + exit(LSB_RC_SUCCESS); } diff --git a/src/starter/starterstroke.c b/src/starter/starterstroke.c index eb5d20628..fae895ba0 100644 --- a/src/starter/starterstroke.c +++ b/src/starter/starterstroke.c @@ -13,7 +13,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: starterstroke.c 3267 2007-10-08 19:57:54Z andreas $ + * RCSID $Id: starterstroke.c 3394 2007-12-13 17:31:21Z martin $ */ #include @@ -197,7 +197,8 @@ int starter_stroke_add_conn(starter_conn_t *conn) { msg.add_conn.auth_method = AUTH_EAP; } - msg.add_conn.eap_type = conn->eap; + msg.add_conn.eap_type = conn->eap_type; + msg.add_conn.eap_vendor = conn->eap_vendor; if (conn->policy & POLICY_TUNNEL) { diff --git a/src/starter/starterwhack.c b/src/starter/starterwhack.c index 19fa9558f..d29b87873 100644 --- a/src/starter/starterwhack.c +++ b/src/starter/starterwhack.c @@ -11,7 +11,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: starterwhack.c 3267 2007-10-08 19:57:54Z andreas $ + * RCSID $Id: starterwhack.c 3405 2007-12-19 00:49:32Z andreas $ */ #include @@ -148,17 +148,22 @@ connection_name(starter_conn_t *conn) } static void -set_whack_end(whack_end_t *w, starter_end_t *end) +set_whack_end(whack_end_t *w, starter_end_t *end, sa_family_t family) { w->id = end->id; w->cert = end->cert; w->ca = end->ca; w->groups = end->groups; w->host_addr = end->addr; - w->host_nexthop = end->nexthop; w->host_srcip = end->srcip; w->has_client = end->has_client; + if (family == AF_INET6 && isanyaddr(&end->nexthop)) + { + anyaddr(AF_INET6, &end->nexthop); + } + w->host_nexthop = end->nexthop; + if (w->has_client) w->client = end->subnet; else @@ -246,8 +251,8 @@ starter_whack_add_conn(starter_conn_t *conn) msg.sa_keying_tries = conn->sa_keying_tries; msg.policy = conn->policy; - set_whack_end(&msg.left, &conn->left); - set_whack_end(&msg.right, &conn->right); + set_whack_end(&msg.left, &conn->left, conn->addr_family); + set_whack_end(&msg.right, &conn->right, conn->addr_family); msg.esp = conn->esp; msg.ike = conn->ike; diff --git a/src/stroke/stroke.h b/src/stroke/stroke.h index 18db5a894..ca4e397e4 100644 --- a/src/stroke/stroke.h +++ b/src/stroke/stroke.h @@ -19,7 +19,7 @@ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * - * RCSID $Id: stroke.h 3271 2007-10-08 20:12:25Z andreas $ + * RCSID $Id: stroke.h 3394 2007-12-13 17:31:21Z martin $ */ #ifndef STROKE_H_ @@ -182,7 +182,8 @@ struct stroke_msg_t { char *name; int ikev2; int auth_method; - int eap_type; + u_int32_t eap_type; + u_int32_t eap_vendor; int mode; int mobike; int force_encap; diff --git a/testing/INSTALL b/testing/INSTALL index 4e55ab633..079bf7f41 100644 --- a/testing/INSTALL +++ b/testing/INSTALL @@ -53,7 +53,7 @@ are required for the strongSwan testing environment: * A vanilla Linux kernel on which the UML kernel will be based on. We recommend the use of - http://www.kernel.org/pub/linux/kernel/v2.6/linux-2.6.23.1.tar.bz2 + http://www.kernel.org/pub/linux/kernel/v2.6/linux-2.6.23.11.tar.bz2 * Starting with Linux kernel 2.6.9 no patch must be applied any more in order to make the vanilla kernel UML-capable. For older kernels you'll find @@ -67,11 +67,11 @@ are required for the strongSwan testing environment: * A gentoo-based UML file system (compressed size 130 MBytes) found at - http://download.strongswan.org/uml/gentoo-fs-20070702.tar.bz2 + http://download.strongswan.org/uml/gentoo-fs-20071108.tar.bz2 * The latest strongSwan distribution - http://download.strongswan.org/strongswan-4.1.8.tar.gz + http://download.strongswan.org/strongswan-4.1.10.tar.gz 3. Creating the environment @@ -146,5 +146,5 @@ README document. ----------------------------------------------------------------------------- -This file is RCSID $Id: INSTALL 3308 2007-10-17 03:39:16Z andreas $ +This file is RCSID $Id: INSTALL 3410 2007-12-19 21:01:19Z andreas $ diff --git a/testing/do-tests.in b/testing/do-tests.in index 2b26d4517..7aadafd6a 100755 --- a/testing/do-tests.in +++ b/testing/do-tests.in @@ -14,7 +14,7 @@ # or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License # for more details. # -# RCSID $Id: do-tests.in 3273 2007-10-08 20:18:34Z andreas $ +# RCSID $Id: do-tests.in 3323 2007-11-07 12:22:44Z andreas $ DIR=`dirname $0` @@ -233,6 +233,13 @@ do @EOF fi + if [ $SUBDIR = "ipv6" ] + then + IPTABLES="ip6tables" + else + IPTABLES="iptables" + fi + for name in $SUBTESTS do let "testnumber += 1" @@ -464,7 +471,7 @@ do ssh $HOSTLOGIN ip route list table $SOURCEIP_ROUTING_TABLE \ > $TESTRESULTDIR/${host}.iproute 2>/dev/null - ssh $HOSTLOGIN iptables -v -n -L \ + ssh $HOSTLOGIN $IPTABLES -v -n -L \ > $TESTRESULTDIR/${host}.iptables 2>/dev/null cat >> $TESTRESULTDIR/index.html <<@EOF

$host

@@ -483,7 +490,7 @@ do
  • auth.log
  • daemon.log
  • ip route list table $SOURCEIP_ROUTING_TABLE
  • -
  • iptables -L
  • +
  • $IPTABLES -L
  • diff --git a/testing/hosts/winnetou/etc/apache2/httpd.conf b/testing/hosts/winnetou/etc/apache2/httpd.conf deleted file mode 100644 index 41c74453a..000000000 --- a/testing/hosts/winnetou/etc/apache2/httpd.conf +++ /dev/null @@ -1,1103 +0,0 @@ -# -# This is a modification of the default Apache 2 configuration -# file by Gentoo Linux. .... [insert more] -# -# Support: -# http://www.gentoo.org/main/en/lists.xml [mailing lists] -# http://forums.gentoo.org/ [web forums] -# -# Bug Reports: -# http://bugs.gentoo.org/ [gentoo related bugs] -# http://bugs.apache.org/ [apache httpd related bugs] - -# -# -# -# Based upon the NCSA server configuration files originally by Rob McCool. -# -# This is the main Apache server configuration file. It contains the -# configuration directives that give the server its instructions. -# See for detailed information about -# the directives. -# -# Do NOT simply read the instructions in here without understanding -# what they do. They're here only as hints or reminders. If you are unsure -# consult the online docs. You have been warned. -# -# The configuration directives are grouped into three basic sections: -# 1. Directives that control the operation of the Apache server process as a -# whole (the 'global environment'). -# 2. Directives that define the parameters of the 'main' or 'default' server, -# which responds to requests that aren't handled by a virtual host. -# These directives also provide default values for the settings -# of all virtual hosts. -# 3. Settings for virtual hosts, which allow Web requests to be sent to -# different IP addresses or hostnames and have them handled by the -# same Apache server process. -# -# Configuration and logfile names: If the filenames you specify for many -# of the server's control files begin with "/" (or "drive:/" for Win32), the -# server will use that explicit path. If the filenames do *not* begin -# with "/", the value of ServerRoot is prepended -- so "logs/foo.log" -# with ServerRoot set to "/usr/lib/apache2" will be interpreted by the -# server as "/usr/lib/apache2/logs/foo.log". -# - -### Section 1: Global Environment -# -# The directives in this section affect the overall operation of Apache, -# such as the number of concurrent requests it can handle or where it -# can find its configuration files. -# - -# -# ServerRoot: The top of the directory tree under which the server's -# configuration, error, and log files are kept. -# -# NOTE! If you intend to place this on an NFS (or otherwise network) -# mounted filesystem then please read the LockFile documentation (available -# at ); -# you will save yourself a lot of trouble. -# -# Do NOT add a slash at the end of the directory path. -# -ServerRoot "/usr/lib/apache2" - -# -# The accept serialization lock file MUST BE STORED ON A LOCAL DISK. -# -#LockFile "/var/run/apache2.lock" - -# -# ScoreBoardFile: File used to store internal server process information. -# If unspecified (the default), the scoreboard will be stored in an -# anonymous shared memory segment, and will be unavailable to third-party -# applications. -# If specified, ensure that no two invocations of Apache share the same -# scoreboard file. The scoreboard file MUST BE STORED ON A LOCAL DISK. -# - - #ScoreBoardFile /var/run/apache2_runtime_status - - - -# -# PidFile: The file in which the server should record its process -# identification number when it starts. -# -PidFile "/var/run/apache2.pid" - -# -# Timeout: The number of seconds before receives and sends time out. -# -Timeout 300 - -# -# KeepAlive: Whether or not to allow persistent connections (more than -# one request per connection). Set to "Off" to deactivate. -# -KeepAlive On - -# -# MaxKeepAliveRequests: The maximum number of requests to allow -# during a persistent connection. Set to 0 to allow an unlimited amount. -# We recommend you leave this number high, for maximum performance. -# -MaxKeepAliveRequests 100 - -# -# KeepAliveTimeout: Number of seconds to wait for the next request from the -# same client on the same connection. -# -KeepAliveTimeout 15 - -## -## Server-Pool Size Regulation (MPM specific) -## - -# prefork MPM [DEFAULT IF USE=-threads] -# StartServers: number of server processes to start -# MinSpareServers: minimum number of server processes which are kept spare -# MaxSpareServers: maximum number of server processes which are kept spare -# MaxClients: maximum number of server processes allowed to start -# MaxRequestsPerChild: maximum number of requests a server process serves - - StartServers 5 - MinSpareServers 5 - MaxSpareServers 10 - MaxClients 150 - MaxRequestsPerChild 0 - - -# worker MPM [DEFAULT IF USE=threads] -# StartServers: initial number of server processes to start -# MaxClients: maximum number of simultaneous client connections -# MinSpareThreads: minimum number of worker threads which are kept spare -# MaxSpareThreads: maximum number of worker threads which are kept spare -# ThreadsPerChild: constant number of worker threads in each server process -# MaxRequestsPerChild: maximum number of requests a server process serves - - StartServers 2 - MaxClients 150 - MinSpareThreads 25 - MaxSpareThreads 75 - ThreadsPerChild 25 - MaxRequestsPerChild 0 - - -# perchild MPM [THIS MPM IS NOT SUPPORTED] -# NumServers: constant number of server processes -# StartThreads: initial number of worker threads in each server process -# MinSpareThreads: minimum number of worker threads which are kept spare -# MaxSpareThreads: maximum number of worker threads which are kept spare -# MaxThreadsPerChild: maximum number of worker threads in each server process -# MaxRequestsPerChild: maximum number of connections per server process - - NumServers 5 - StartThreads 5 - MinSpareThreads 5 - MaxSpareThreads 10 - MaxThreadsPerChild 20 - MaxRequestsPerChild 0 - - -# peruser MPM [THIS MPM IS NOT SUPPORTED] -# MinSpareServers - Minimum number of idle children, to handle request spikes -# MaxClients - Maximum number of children alive at the same time -# MaxProcessors - Maximum number of processors per vhost -# Multiplexer - Specify an Multiplexer Child configuration. -# Processor - Specify a User and Group for a specific child process. -# ServerEnvironment - Specify the server environment for this virtual host. - - ServerLimit 256 - MaxClients 256 - MinSpareProcessors 2 - MaxProcessors 10 - MaxRequestsPerChild 1000 - - # kill off idle processors after this many seconds - # set to 0 to disable - ExpireTimeout 1800 - - Multiplexer nobody nobody - - Processor apache apache - - # chroot dir is optional: - # Processor user group /path/to/chroot - - -# itk MPM [THIS MPM IS NOT SUPPORTED] -# StartServers: number of server processes to start -# MinSpareServers: minimum number of server processes which are kept spare -# MaxSpareServers: maximum number of server processes which are kept spare -# MaxClients: maximum number of server processes allowed to start -# MaxRequestsPerChild: maximum number of requests a server process serves - - StartServers 5 - MinSpareServers 2 - MaxSpareServers 10 - MaxClients 150 - MaxRequestsPerChild 1000 - - -# -# Listen: Allows you to bind Apache to specific IP addresses and/or -# ports, instead of the default. See also the -# directive. -# -# Change this to Listen on specific IP addresses as shown below to -# prevent Apache from glomming onto all bound IP addresses (0.0.0.0) -# -#Listen 12.34.56.78:80 -Listen 80 -Listen 8880 -Listen 8881 -Listen 8882 - -# -# Dynamic Shared Object (DSO) Support -# -# To be able to use the functionality of a module which was built as a DSO you -# have to place corresponding `LoadModule' lines at this location so the -# directives contained in it are actually available _before_ they are used. -# Statically compiled modules (those listed by `httpd -l') do not need -# to be loaded here. -# -# The following modules are considered as the default configuration. -# If you wish to disable one of them, you may have to alter other -# configuration directives. -# -# You should always leave these three, as they are needed for normal use. -# mod_access (Order, Allow, etc..) -# mod_log_config (Transferlog, etc..) -# mod_mime (AddType, etc...) -# -# Example: -# LoadModule foo_module modules/mod_foo.so - - -# Authentication Modules -# -# These modules provide authentication and authorization for -# clients. They should not normally be disabled. -# -LoadModule access_module modules/mod_access.so -LoadModule auth_module modules/mod_auth.so -LoadModule auth_anon_module modules/mod_auth_anon.so -LoadModule auth_dbm_module modules/mod_auth_dbm.so -LoadModule auth_digest_module modules/mod_auth_digest.so - -# -# Metadata Modules -# -# These modules provide extra data to clients about -# a file, such as the mime-type or charset. -# -LoadModule charset_lite_module modules/mod_charset_lite.so -LoadModule env_module modules/mod_env.so -LoadModule expires_module modules/mod_expires.so -LoadModule headers_module modules/mod_headers.so -LoadModule mime_module modules/mod_mime.so -LoadModule negotiation_module modules/mod_negotiation.so -LoadModule setenvif_module modules/mod_setenvif.so - -# -# Logging Modules -# -# These modules provide logging services for Apache -# -LoadModule log_config_module modules/mod_log_config.so -LoadModule logio_module modules/mod_logio.so - - -# -# CGI Modules -# -# These modules provide the ability to execute CGI Scripts. -# -LoadModule cgi_module modules/mod_cgi.so -LoadModule cgid_module modules/mod_cgid.so - - -# -# This `suexec` module provides the ability to exeucte CGI scripts under -# a different user than apache is run. -# -LoadModule suexec_module modules/mod_suexec.so - - -# -# Mappers -# -# These Modules provide URL mappings or translations. -LoadModule alias_module modules/mod_alias.so -LoadModule rewrite_module modules/mod_rewrite.so - - LoadModule userdir_module modules/mod_userdir.so - - - -# -# Handlers -# -# These modules create content for a client. -# - - LoadModule info_module modules/mod_info.so - LoadModule status_module modules/mod_status.so - -LoadModule actions_module modules/mod_actions.so -LoadModule autoindex_module modules/mod_autoindex.so -LoadModule dir_module modules/mod_dir.so - -# -# Filters -# -# These modules provide filters for Apache. -# They preform common tasks like gzip encoding or SSI -# -# -LoadModule ext_filter_module modules/mod_ext_filter.so -LoadModule deflate_module modules/mod_deflate.so -LoadModule include_module modules/mod_include.so - - -# -# Cache Modules -# -# The following modules are used for storing a cache of -# generated or proxied content. -# -#LoadModule cache_module modules/mod_cache.so -#LoadModule disk_cache_module modules/mod_disk_cache.so -#LoadModule mem_cache_module modules/mod_mem_cache.so -#LoadModule file_cache_module modules/mod_file_cache.so - -# -# Proxy Modules -# -# The following modules are only needed if you are running -# Apache as a Forward or Reverse Proxy. -# -# WARNING: Enabling these modules can be dangerous! -# READ THE DOCUMENTATION FIRST: -# http://httpd.apache.org/docs/2.0/mod/mod_proxy.html - - LoadModule proxy_module modules/mod_proxy.so - LoadModule proxy_connect_module modules/mod_proxy_connect.so - LoadModule proxy_ftp_module modules/mod_proxy_ftp.so - LoadModule proxy_http_module modules/mod_proxy_http.so - - -# -# Uncommon Modules -# -# The following Modules are not commonly loaded for Apache -# -#LoadModule case_filter_module modules/mod_case_filter.so -#LoadModule case_filter_in_module modules/mod_case_filter_in.so -#LoadModule echo_module modules/mod_echo.so -#LoadModule mime_magic_module modules/mod_mime_magic.so -#LoadModule speling_module modules/mod_speling.so -#LoadModule unique_id_module modules/mod_unique_id.so -#LoadModule vhost_alias_module modules/mod_vhost_alias.so - -# -# Obsolete Modules -# -# The Following modules are not commonly needed and use -# obsolete technologies. -# -#LoadModule cern_meta_module modules/mod_cern_meta.so -#LoadModule imap_module modules/mod_imap.so -#LoadModule usertrack_module modules/mod_usertrack.so -#LoadModule asis_module modules/mod_asis.so - - -# -# Extra Modules -# -# We Include extra .conf files from /etc/apache2/modules.d -# This is used to load things like PHP and mod_ssl. -# -Include /etc/apache2/modules.d/*.conf - -### Section 2: 'Main' server configuration -# -# The directives in this section set up the values used by the 'main' -# server, which responds to any requests that aren't handled by a -# definition. These values also provide defaults for -# any containers you may define later in the file. -# -# All of these directives may appear inside containers, -# in which case these default settings will be overridden for the -# virtual host being defined. -# - -# -# If you wish httpd to run as a different user or group, you must run -# httpd as root initially and it will switch. -# -# User/Group: The name (or #number) of the user/group to run httpd as. -# . On SCO (ODT 3) use "User nouser" and "Group nogroup". -# . On HPUX you may not be able to use shared memory as nobody, and the -# suggested workaround is to create a user www and use that user. -# NOTE that some kernels refuse to setgid(Group) or semctl(IPC_SET) -# when the value of (unsigned)Group is above 60000; -# don't use Group #-1 on these systems! -# -User apache -Group apache - -# -# ServerAdmin: Your address, where problems with the server should be -# e-mailed. This address appears on some server-generated pages, such -# as error documents. e.g. admin@your-domain.com -# -ServerAdmin root@localhost - -# -# ServerName gives the name and port that the server uses to identify itself. -# This can often be determined automatically, but we recommend you specify -# it explicitly to prevent problems during startup. -# -# If this is not set to valid DNS name for your host, server-generated -# redirections will not work. See also the UseCanonicalName directive. -# -# If your host doesn't have a registered DNS name, enter its IP address here. -# You will have to access it by its address anyway, and this will make -# redirections work in a sensible way. -# -#ServerName localhost - -# -# UseCanonicalName: Determines how Apache constructs self-referencing -# URLs and the SERVER_NAME and SERVER_PORT variables. -# When set "Off", Apache will use the Hostname and Port supplied -# by the client. When set "On", Apache will use the value of the -# ServerName directive. -# -UseCanonicalName Off - - -# -# Each directory to which Apache has access can be configured with respect -# to which services and features are allowed and/or disabled in that -# directory (and its subdirectories). -# -# First, we configure the "default" to be a very restrictive set of -# features. -# - - Options FollowSymLinks - AllowOverride None - - -# -# Note that from this point forward you must specifically allow -# particular features to be enabled - so if something's not working as -# you might expect, make sure that you have specifically enabled it -# below. -# - -# -# UserDir: The name of the directory that is appended onto a user's home -# directory if a ~user request is received. -# enable by adding -D USERDIR to /etc/conf.d/apache2 -# - - UserDir public_html - -# -# Control access to UserDir directories. The following is an example -# for a site where these directories are restricted to read-only. -# - - AllowOverride FileInfo AuthConfig Limit Indexes - Options MultiViews Indexes SymLinksIfOwnerMatch IncludesNoExec - - Order allow,deny - Allow from all - - - Order deny,allow - Deny from all - - - - -# Enable this additional section if you would like to make use of a -# suexec-enabled cgi-bin directory on a per-user basis. -# -# -# Options ExecCGI -# SetHandler cgi-script -# - - - - -# -# DirectoryIndex: sets the file that Apache will serve if a directory -# is requested. -# -# The index.html.var file (a type-map) is used to deliver content- -# negotiated documents. The MultiViews Option can be used for the -# same purpose, but it is much slower. -# -DirectoryIndex index.html ocsp.cgi - -# -# AccessFileName: The name of the file to look for in each directory -# for additional configuration directives. See also the AllowOverride -# directive. -# -AccessFileName .htaccess - -# -# The following lines prevent .htaccess and .htpasswd files from being -# viewed by Web clients. -# - - Order allow,deny - Deny from all - - -# -# TypesConfig describes where the mime.types file (or equivalent) is -# to be found. -# -TypesConfig /etc/mime.types - -# -# DefaultType is the default MIME type the server will use for a document -# if it cannot otherwise determine one, such as from filename extensions. -# If your server contains mostly text or HTML documents, "text/plain" is -# a good value. If most of your content is binary, such as applications -# or images, you may want to use "application/octet-stream" instead to -# keep browsers from trying to display binary files as though they are -# text. -# -DefaultType text/plain - -# -# The mod_mime_magic module allows the server to use various hints from the -# contents of the file itself to determine its type. The MIMEMagicFile -# directive tells the module where the hint definitions are located. -# - - MIMEMagicFile /etc/apache2/magic - - -# -# HostnameLookups: Log the names of clients or just their IP addresses -# e.g., www.apache.org (on) or 204.62.129.132 (off). -# The default is off because it'd be overall better for the net if people -# had to knowingly turn this feature on, since enabling it means that -# each client request will result in AT LEAST one lookup request to the -# nameserver. -# -HostnameLookups Off - -# -# EnableMMAP: Control whether memory-mapping is used to deliver -# files (assuming that the underlying OS supports it). -# The default is on; turn this off if you serve from NFS-mounted -# filesystems. On some systems, turning it off (regardless of -# filesystem) can improve performance; for details, please see -# http://httpd.apache.org/docs/2.0/mod/core.html#enablemmap -# -#EnableMMAP off - -# -# EnableSendfile: Control whether the sendfile kernel support is -# used to deliver files (assuming that the OS supports it). -# The default is on; turn this off if you serve from NFS-mounted -# filesystems. Please see -# http://httpd.apache.org/docs/2.0/mod/core.html#enablesendfile -# -#EnableSendfile off - -# -# ErrorLog: The location of the error log file. -# If you do not specify an ErrorLog directive within a -# container, error messages relating to that virtual host will be -# logged here. If you *do* define an error logfile for a -# container, that host's errors will be logged there and not here. -# -ErrorLog logs/error_log - -# -# LogLevel: Control the number of messages logged to the error_log. -# Possible values include: debug, info, notice, warn, error, crit, -# alert, emerg. -# -LogLevel warn - -# -# The following directives define some format nicknames for use with -# a CustomLog directive (see below). -# -LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"" combined -LogFormat "%h %l %u %t \"%r\" %>s %b" common -LogFormat "%{Referer}i -> %U" referer -LogFormat "%{User-agent}i" agent -LogFormat "%v %h %l %u %t \"%r\" %>s %b %T" script -LogFormat "%v %h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\" VLOG=%{VLOG}e" vhost - -# You need to enable mod_logio.c to use %I and %O -#LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\" %I %O" combinedio - -# -# The location and format of the access logfile (Common Logfile Format). -# If you do not define any access logfiles within a -# container, they will be logged here. Contrariwise, if you *do* -# define per- access logfiles, transactions will be -# logged therein and *not* in this file. -# -CustomLog logs/access_log common - -# -# If you would like to have agent and referer logfiles, uncomment the -# following directives. -# -#CustomLog logs/referer_log referer -#CustomLog logs/agent_log agent - -# -# If you prefer a single logfile with access, agent, and referer information -# (Combined Logfile Format) you can use the following directive. -# -#CustomLog logs/access_log combined - -# -# ServerTokens -# This directive configures what you return as the Server HTTP response -# Header. The default is 'Full' which sends information about the OS-Type -# and compiled in modules. -# Set to one of: Full | OS | Minor | Minimal | Major | Prod -# where Full conveys the most information, and Prod the least. -# -ServerTokens Prod - -# -# Optionally add a line containing the server version and virtual host -# name to server-generated pages (internal error documents, FTP directory -# listings, mod_status and mod_info output etc., but not CGI generated -# documents or custom error documents). -# Set to "EMail" to also include a mailto: link to the ServerAdmin. -# Set to one of: On | Off | EMail -# -ServerSignature On - -# -# Aliases: Add here as many aliases as you need (with no limit). The format is -# Alias fakename realname -# -# Note that if you include a trailing / on fakename then the server will -# require it to be present in the URL. So "/icons" isn't aliased in this -# example, only "/icons/". If the fakename is slash-terminated, then the -# realname must also be slash terminated, and if the fakename omits the -# trailing slash, the realname must also omit it. -# -# We include the /icons/ alias for FancyIndexed directory listings. If you -# do not use FancyIndexing, you may comment this out. -# -Alias /icons/ "/var/www/localhost/icons/" - - - Options Indexes MultiViews - AllowOverride None - Order allow,deny - Allow from all - - -# -# ScriptAlias: This controls which directories contain server scripts. -# ScriptAliases are essentially the same as Aliases, except that -# documents in the realname directory are treated as applications and -# run by the server when requested rather than as documents sent to the client. -# The same rules about trailing "/" apply to ScriptAlias directives as to -# Alias. -# -ScriptAlias /cgi-bin/ /var/www/localhost/cgi-bin/ - - - # - # Additional to mod_cgid.c settings, mod_cgid has Scriptsock - # for setting UNIX socket for communicating with cgid. - # - #Scriptsock /var/run/cgisock - - -# -# "/var/www/localhost/cgi-bin/" should be changed to whatever your ScriptAliased -# CGI directory exists, if you have that configured. -# - - AllowOverride None - Options None - Order allow,deny - Allow from all - - -# -# Redirect allows you to tell clients about documents which used to exist in -# your server's namespace, but do not anymore. This allows you to tell the -# clients where to look for the relocated document. -# Example: -# Redirect permanent /foo http://www.example.com/bar - -# -# Directives controlling the display of server-generated directory listings. -# - - # - # IndexOptions: Controls the appearance of server-generated directory - # listings. - # - IndexOptions FancyIndexing VersionSort - - # - # AddIcon* directives tell the server which icon to show for different - # files or filename extensions. These are only displayed for - # FancyIndexed directories. - # - AddIconByEncoding (CMP,/icons/compressed.gif) x-compress x-gzip - - AddIconByType (TXT,/icons/text.gif) text/* - AddIconByType (IMG,/icons/image2.gif) image/* - AddIconByType (SND,/icons/sound2.gif) audio/* - AddIconByType (VID,/icons/movie.gif) video/* - - AddIcon /icons/binary.gif .bin .exe - AddIcon /icons/binhex.gif .hqx - AddIcon /icons/tar.gif .tar - AddIcon /icons/world2.gif .wrl .wrl.gz .vrml .vrm .iv - AddIcon /icons/compressed.gif .Z .z .tgz .gz .zip - AddIcon /icons/a.gif .ps .ai .eps - AddIcon /icons/layout.gif .html .shtml .htm .pdf - AddIcon /icons/text.gif .txt - AddIcon /icons/c.gif .c - AddIcon /icons/p.gif .pl .py - AddIcon /icons/f.gif .for - AddIcon /icons/dvi.gif .dvi - AddIcon /icons/uuencoded.gif .uu - AddIcon /icons/script.gif .conf .sh .shar .csh .ksh .tcl - AddIcon /icons/tex.gif .tex - AddIcon /icons/bomb.gif core - - AddIcon /icons/back.gif .. - AddIcon /icons/hand.right.gif README - AddIcon /icons/folder.gif ^^DIRECTORY^^ - AddIcon /icons/blank.gif ^^BLANKICON^^ - - # - # DefaultIcon is which icon to show for files which do not have an icon - # explicitly set. - # - DefaultIcon /icons/unknown.gif - - # - # AddDescription allows you to place a short description after a file in - # server-generated indexes. These are only displayed for FancyIndexed - # directories. - # Format: AddDescription "description" filename - # - #AddDescription "GZIP compressed document" .gz - #AddDescription "tar archive" .tar - #AddDescription "GZIP compressed tar archive" .tgz - - # - # ReadmeName is the name of the README file the server will look for by - # default, and append to directory listings. - # - # HeaderName is the name of a file which should be prepended to - # directory indexes. - ReadmeName README.html - HeaderName HEADER.html - - # - # IndexIgnore is a set of filenames which directory indexing should ignore - # and not include in the listing. Shell-style wildcarding is permitted. - # - IndexIgnore .??* *~ *# HEADER* README* RCS CVS *,v *,t .svn - - -# -# DefaultLanguage and AddLanguage allows you to specify the language of -# a document. You can then use content negotiation to give a browser a -# file in a language the user can understand. -# -# Specify a default language. This means that all data -# going out without a specific language tag (see below) will -# be marked with this one. You probably do NOT want to set -# this unless you are sure it is correct for all cases. -# -# * It is generally better to not mark a page as -# * being a certain language than marking it with the wrong -# * language! -# -# DefaultLanguage nl -# -# Note 1: The suffix does not have to be the same as the language -# keyword --- those with documents in Polish (whose net-standard -# language code is pl) may wish to use "AddLanguage pl .po" to -# avoid the ambiguity with the common suffix for perl scripts. -# -# Note 2: The example entries below illustrate that in some cases -# the two character 'Language' abbreviation is not identical to -# the two character 'Country' code for its country, -# E.g. 'Danmark/dk' versus 'Danish/da'. -# -# Note 3: In the case of 'ltz' we violate the RFC by using a three char -# specifier. There is 'work in progress' to fix this and get -# the reference data for rfc1766 cleaned up. -# -# Catalan (ca) - Croatian (hr) - Czech (cs) - Danish (da) - Dutch (nl) -# English (en) - Esperanto (eo) - Estonian (et) - French (fr) - German (de) -# Greek-Modern (el) - Hebrew (he) - Italian (it) - Japanese (ja) -# Korean (ko) - Luxembourgeois* (ltz) - Norwegian Nynorsk (nn) -# Norwegian (no) - Polish (pl) - Portugese (pt) -# Brazilian Portuguese (pt-BR) - Russian (ru) - Swedish (sv) -# Simplified Chinese (zh-CN) - Spanish (es) - Traditional Chinese (zh-TW) -# -AddLanguage ca .ca -AddLanguage cs .cz .cs -AddLanguage da .dk -AddLanguage de .de -AddLanguage el .el -AddLanguage en .en -AddLanguage eo .eo -AddLanguage es .es -AddLanguage et .et -AddLanguage fr .fr -AddLanguage he .he -AddLanguage hr .hr -AddLanguage it .it -AddLanguage ja .ja -AddLanguage ko .ko -AddLanguage ltz .ltz -AddLanguage nl .nl -AddLanguage nn .nn -AddLanguage no .no -AddLanguage pl .po -AddLanguage pt .pt -AddLanguage pt-BR .pt-br -AddLanguage ru .ru -AddLanguage sv .sv -AddLanguage zh-CN .zh-cn -AddLanguage zh-TW .zh-tw - -# -# LanguagePriority allows you to give precedence to some languages -# in case of a tie during content negotiation. -# -# Just list the languages in decreasing order of preference. We have -# more or less alphabetized them here. You probably want to change this. -# -LanguagePriority en ca cs da de el eo es et fr he hr it ja ko ltz nl nn no pl pt pt-BR ru sv zh-CN zh-TW - -# -# ForceLanguagePriority allows you to serve a result page rather than -# MULTIPLE CHOICES (Prefer) [in case of a tie] or NOT ACCEPTABLE (Fallback) -# [in case no accepted languages matched the available variants] -# -ForceLanguagePriority Prefer Fallback - -# -# Commonly used filename extensions to character sets. You probably -# want to avoid clashes with the language extensions, unless you -# are good at carefully testing your setup after each change. -# See http://www.iana.org/assignments/character-sets for the -# official list of charset names and their respective RFCs. -# -AddCharset ISO-8859-1 .iso8859-1 .latin1 -AddCharset ISO-8859-2 .iso8859-2 .latin2 .cen -AddCharset ISO-8859-3 .iso8859-3 .latin3 -AddCharset ISO-8859-4 .iso8859-4 .latin4 -AddCharset ISO-8859-5 .iso8859-5 .latin5 .cyr .iso-ru -AddCharset ISO-8859-6 .iso8859-6 .latin6 .arb -AddCharset ISO-8859-7 .iso8859-7 .latin7 .grk -AddCharset ISO-8859-8 .iso8859-8 .latin8 .heb -AddCharset ISO-8859-9 .iso8859-9 .latin9 .trk -AddCharset ISO-2022-JP .iso2022-jp .jis -AddCharset ISO-2022-KR .iso2022-kr .kis -AddCharset ISO-2022-CN .iso2022-cn .cis -AddCharset Big5 .Big5 .big5 -# For russian, more than one charset is used (depends on client, mostly): -AddCharset WINDOWS-1251 .cp-1251 .win-1251 -AddCharset CP866 .cp866 -AddCharset KOI8-r .koi8-r .koi8-ru -AddCharset KOI8-ru .koi8-uk .ua -AddCharset ISO-10646-UCS-2 .ucs2 -AddCharset ISO-10646-UCS-4 .ucs4 -AddCharset UTF-8 .utf8 - -# The set below does not map to a specific (iso) standard -# but works on a fairly wide range of browsers. Note that -# capitalization actually matters (it should not, but it -# does for some browsers). -# -# See http://www.iana.org/assignments/character-sets -# for a list of sorts. But browsers support few. -# -AddCharset GB2312 .gb2312 .gb -AddCharset utf-7 .utf7 -AddCharset utf-8 .utf8 -AddCharset big5 .big5 .b5 -AddCharset EUC-TW .euc-tw -AddCharset EUC-JP .euc-jp -AddCharset EUC-KR .euc-kr -AddCharset shift_jis .sjis - -# -# AddType allows you to add to or override the MIME configuration -# file mime.types for specific file types. -# -#AddType application/x-tar .tgz -# -# AddEncoding allows you to have certain browsers uncompress -# information on the fly. Note: Not all browsers support this. -# Despite the name similarity, the following Add* directives have nothing -# to do with the FancyIndexing customization directives above. -# -#AddEncoding x-compress .Z -#AddEncoding x-gzip .gz .tgz -# -# If the AddEncoding directives above are commented-out, then you -# probably should define those extensions to indicate media types: -# -AddType application/x-compress .Z -AddType application/x-gzip .gz .tgz - -# -# AddHandler allows you to map certain file extensions to "handlers": -# actions unrelated to filetype. These can be either built into the server -# or added with the Action directive (see below) -# -# To use CGI scripts outside of ScriptAliased directories: -# (You will also need to add "ExecCGI" to the "Options" directive.) -# -AddHandler cgi-script .cgi - -# -# For files that include their own HTTP headers: -# -#AddHandler send-as-is asis - -# -# For server-parsed imagemap files: -# -#AddHandler imap-file map - -# -# For type maps (negotiated resources): -# (This is enabled by default to allow the Apache "It Worked" page -# to be distributed in multiple languages.) -# -AddHandler type-map var - -# -# Filters allow you to process content before it is sent to the client. -# -# To parse .shtml files for server-side includes (SSI): -# (You will also need to add "Includes" to the "Options" directive.) -# -#AddType text/html .shtml -#AddOutputFilter INCLUDES .shtml - -# -# Action lets you define media types that will execute a script whenever -# a matching file is called. This eliminates the need for repeated URL -# pathnames for oft-used CGI file processors. -# Format: Action media/type /cgi-script/location -# Format: Action handler-name /cgi-script/location -# - -# -# Customizable error responses come in three flavors: -# 1) plain text 2) local redirects 3) external redirects -# -# Some examples: -#ErrorDocument 500 "The server made a boo boo." -#ErrorDocument 404 /missing.html -#ErrorDocument 404 "/cgi-bin/missing_handler.pl" -#ErrorDocument 402 http://www.example.com/subscription_info.html -# - -# -# Putting this all together, we can internationalize error responses. -# -# We use Alias to redirect any /error/HTTP_.html.var response to -# our collection of by-error message multi-language collections. We use -# includes to substitute the appropriate text. -# -# You can modify the messages' appearance without changing any of the -# default HTTP_.html.var files by adding the line: -# -# Alias /error/include/ "/your/include/path/" -# -# which allows you to create your own set of files by starting with the -# /var/www/localhost/error/include files and copying them to /your/includepath/ -# even on a per-VirtualHost basis. The default include files will display -# your Apache version number and your ServerAdmin email address regardless -# of the setting of ServerSignature. -# -# The internationalized error documents require mod_alias, mod_include -# and mod_negotiation. To activate them, uncomment the following 30 lines. - -# Alias /error/ "/var/www/localhost/error/" -# -# -# AllowOverride None -# Options IncludesNoExec -# AddOutputFilter Includes html -# AddHandler type-map var -# Order allow,deny -# Allow from all -# LanguagePriority en cs de es fr it nl sv pt-br ro -# ForceLanguagePriority Prefer Fallback -# -# -# ErrorDocument 400 /error/HTTP_BAD_REQUEST.html.var -# ErrorDocument 401 /error/HTTP_UNAUTHORIZED.html.var -# ErrorDocument 403 /error/HTTP_FORBIDDEN.html.var -# ErrorDocument 404 /error/HTTP_NOT_FOUND.html.var -# ErrorDocument 405 /error/HTTP_METHOD_NOT_ALLOWED.html.var -# ErrorDocument 408 /error/HTTP_REQUEST_TIME_OUT.html.var -# ErrorDocument 410 /error/HTTP_GONE.html.var -# ErrorDocument 411 /error/HTTP_LENGTH_REQUIRED.html.var -# ErrorDocument 412 /error/HTTP_PRECONDITION_FAILED.html.var -# ErrorDocument 413 /error/HTTP_REQUEST_ENTITY_TOO_LARGE.html.var -# ErrorDocument 414 /error/HTTP_REQUEST_URI_TOO_LARGE.html.var -# ErrorDocument 415 /error/HTTP_UNSUPPORTED_MEDIA_TYPE.html.var -# ErrorDocument 500 /error/HTTP_INTERNAL_SERVER_ERROR.html.var -# ErrorDocument 501 /error/HTTP_NOT_IMPLEMENTED.html.var -# ErrorDocument 502 /error/HTTP_BAD_GATEWAY.html.var -# ErrorDocument 503 /error/HTTP_SERVICE_UNAVAILABLE.html.var -# ErrorDocument 506 /error/HTTP_VARIANT_ALSO_VARIES.html.var - - -# -# The following directives modify normal HTTP response behavior to -# handle known problems with browser implementations. -# -BrowserMatch "Mozilla/2" nokeepalive -BrowserMatch "MSIE 4\.0b2;" nokeepalive downgrade-1.0 force-response-1.0 -BrowserMatch "RealPlayer 4\.0" force-response-1.0 -BrowserMatch "Java/1\.0" force-response-1.0 -BrowserMatch "JDK/1\.0" force-response-1.0 - -# -# The following directive disables redirects on non-GET requests for -# a directory that does not include the trailing slash. This fixes a -# problem with Microsoft WebFolders which does not appropriately handle -# redirects for folders with DAV methods. -# Same deal with Apple's DAV filesystem and Gnome VFS support for DAV. -# -BrowserMatch "Microsoft Data Access Internet Publishing Provider" redirect-carefully -BrowserMatch "MS FrontPage" redirect-carefully -BrowserMatch "^WebDrive" redirect-carefully -BrowserMatch "^WebDAVFS/1.[0123]" redirect-carefully -BrowserMatch "^gnome-vfs" redirect-carefully -BrowserMatch "^XML Spy" redirect-carefully -BrowserMatch "^Dreamweaver-WebDAV-SCM1" redirect-carefully - -# -# Allow server status reports generated by mod_status, -# with the URL of http://servername/server-status -# Change the ".example.com" to match your domain to enable. -# - - ExtendedStatus On - - SetHandler server-status - Order deny,allow - Deny from all - Allow from localhost - - - -# -# Allow remote server configuration reports, with the URL of -# http://localhost/server-info (This is useful for debugging) -# - - - SetHandler server-info - Order deny,allow - Deny from all - Allow from localhost - - - - -# -# Gentoo VHosts -# -# For Gentoo we include External Virtual Hosts Files. -# Please see vhosts.d/00_default_vhost.conf for the default virtual host. -# -Include /etc/apache2/vhosts.d/*.conf diff --git a/testing/hosts/winnetou/etc/apache2/modules.d/00_mod_mime.conf b/testing/hosts/winnetou/etc/apache2/modules.d/00_mod_mime.conf new file mode 100644 index 000000000..72b7e0ea4 --- /dev/null +++ b/testing/hosts/winnetou/etc/apache2/modules.d/00_mod_mime.conf @@ -0,0 +1,61 @@ +# DefaultType: the default MIME type the server will use for a document +# if it cannot otherwise determine one, such as from filename extensions. +# If your server contains mostly text or HTML documents, "text/plain" is +# a good value. If most of your content is binary, such as applications +# or images, you may want to use "application/octet-stream" instead to +# keep browsers from trying to display binary files as though they are +# text. +DefaultType text/plain + + +# TypesConfig points to the file containing the list of mappings from +# filename extension to MIME-type. +TypesConfig /etc/mime.types + +# AddType allows you to add to or override the MIME configuration +# file specified in TypesConfig for specific file types. +#AddType application/x-gzip .tgz + +# AddEncoding allows you to have certain browsers uncompress +# information on the fly. Note: Not all browsers support this. +#AddEncoding x-compress .Z +#AddEncoding x-gzip .gz .tgz + +# If the AddEncoding directives above are commented-out, then you +# probably should define those extensions to indicate media types: +AddType application/x-compress .Z +AddType application/x-gzip .gz .tgz + +# AddHandler allows you to map certain file extensions to "handlers": +# actions unrelated to filetype. These can be either built into the server +# or added with the Action directive (see below) + +# To use CGI scripts outside of ScriptAliased directories: +# (You will also need to add "ExecCGI" to the "Options" directive.) +AddHandler cgi-script .cgi + +# For files that include their own HTTP headers: +#AddHandler send-as-is asis + +# For server-parsed imagemap files: +#AddHandler imap-file map + +# For type maps (negotiated resources): +AddHandler type-map var + +# Filters allow you to process content before it is sent to the client. +# +# To parse .shtml files for server-side includes (SSI): +# (You will also need to add "Includes" to the "Options" directive.) +#AddType text/html .shtml +#AddOutputFilter INCLUDES .shtml + + + +# The mod_mime_magic module allows the server to use various hints from the +# contents of the file itself to determine its type. The MIMEMagicFile +# directive tells the module where the hint definitions are located. +MIMEMagicFile /etc/apache2/magic + + +# vim: ts=4 filetype=apache diff --git a/testing/hosts/winnetou/etc/apache2/vhosts.d/01_ocsp_vhost.conf b/testing/hosts/winnetou/etc/apache2/vhosts.d/01_ocsp_vhost.conf index c97c30936..9a32412db 100644 --- a/testing/hosts/winnetou/etc/apache2/vhosts.d/01_ocsp_vhost.conf +++ b/testing/hosts/winnetou/etc/apache2/vhosts.d/01_ocsp_vhost.conf @@ -1,36 +1,51 @@ # OCSP Server +Listen 8880 + ServerAdmin root@strongswan.org DocumentRoot /etc/openssl/ocsp ServerName ocsp.strongswan.org ServerAlias 192.168.0.150 + DirectoryIndex ocsp.cgi - Options +ExecCGI + Options +ExecCGI + Order allow,deny + Allow from all ErrorLog /var/log/apache2/ocsp/error_log CustomLog /var/log/apache2/ocsp/access_log combined +Listen 8881 + ServerAdmin root@research.strongswan.org DocumentRoot /etc/openssl/research/ocsp ServerName ocsp.research.strongswan.org ServerAlias ocsp.strongswan.org 192.168.0.150 + DirectoryIndex ocsp.cgi - Options +ExecCGI + Options +ExecCGI + Order allow,deny + Allow from all ErrorLog /var/log/apache2/ocsp/error_log CustomLog /var/log/apache2/ocsp/access_log combined +Listen 8882 + ServerAdmin root@sales.strongswan.org DocumentRoot /etc/openssl/sales/ocsp ServerName ocsp.sales.strongswan.org ServerAlias ocsp.strongswan.org 192.168.0.150 + DirectoryIndex ocsp.cgi - Options +ExecCGI + Options +ExecCGI + Order allow,deny + Allow from all ErrorLog /var/log/apache2/ocsp/error_log CustomLog /var/log/apache2/ocsp/access_log combined diff --git a/testing/hosts/winnetou/etc/conf.d/apache2 b/testing/hosts/winnetou/etc/conf.d/apache2 deleted file mode 100644 index cfb80a7d9..000000000 --- a/testing/hosts/winnetou/etc/conf.d/apache2 +++ /dev/null @@ -1,52 +0,0 @@ -# Copyright 1999-2004 Gentoo Foundation -# Distributed under the terms of the GNU General Public License v2 -# $Header: /var/cvsroot/strongswan/testing/hosts/winnetou/etc/conf.d/apache2,v 1.2 2006/01/06 12:21:21 as Exp $ - -# Config file for /etc/init.d/apache2 - -# An example from /etc/apache2/conf/modules.d/40_mod_ssl.conf: -# -# -# -# LoadModule ssl_module extramodules/mod_ssl.so -# -# -# -# This means that the mod_ssl.so DSO module is only loaded -# into the server when you pass "-D SSL" at startup. To -# enable WebDAV, add "-D DAV -D DAV_FS". If you installed -# mod_php then add "-D PHP4". For more options, please -# read the files in the /etc/apache2/conf/modules.d directory. - -APACHE2_OPTS="-D SSL -D DEFAULT_VHOST" - -# Extended options for advanced uses of Apache ONLY -# You don't need to edit these unless you are doing crazy Apache stuff -# As not having them set correctly, or feeding in an incorrect configuration -# via them will result in Apache failing to start -# YOU HAVE BEEN WARNED. - -# ServerRoot setting -#SERVERROOT=/etc/apache2 - -# Configuration file location -# - If this does NOT start with a '/', then it is treated relative to -# $SERVERROOT by Apache -#CONFIGFILE=conf/apache2.conf - -# Location to log startup errors to -# They are normally dumped to your terminal. -#STARTUPERRORLOG="/var/log/apache2/startuperror.log" - -# PID file location -# Note that this MUST match the setting in your configuration file! -PIDFILE=/var/run/apache2.pid - -# Restart style -# see http://httpd.apache.org/docs-2.0/stopping.html for more details -# the default is 'graceful', the other possible value is 'restart' -# If you use 'graceful', completion of the command does NOT imply that the system -# has finished restarting. Restart is finished only when all child processes -# have finished serving their current request sets. Read the URL for details. -#RESTARTSTYLE="restart" -RESTARTSTYLE="graceful" diff --git a/testing/hosts/winnetou/etc/init.d/apache2 b/testing/hosts/winnetou/etc/init.d/apache2 index f54f3444a..5f72d3090 100755 --- a/testing/hosts/winnetou/etc/init.d/apache2 +++ b/testing/hosts/winnetou/etc/init.d/apache2 @@ -1,78 +1,121 @@ #!/sbin/runscript -# Copyright 1999-2004 Gentoo Foundation +# Copyright 1999-2007 Gentoo Foundation # Distributed under the terms of the GNU General Public License v2 -opts="${opts} reload" +opts="configtest fullstatus graceful gracefulstop modules reload" -[ "x${SERVERROOT}" != "x" ] && APACHE2_OPTS="${APACHE2_OPTS} -d ${SERVERROOT}" -[ "x${CONFIGFILE}" != "x" ] && APACHE2_OPTS="${APACHE2_OPTS} -f ${CONFIGFILE}" -[ "x${STARTUPERRORLOG}" != "x" ] && APACHE2_OPTS="${APACHE2_OPTS} -E ${STARTUPERRORLOG}" -# set a default for PIDFILE/RESTARTSTYLE for those that FAILED to follow -# instructiosn and update the conf.d/apache2 file. -# (bug #38787) -[ -z "${PIDFILE}" ] && PIDFILE=/var/run/apache2.pid -[ -z "${RESTARTSTYLE}" ] && RESTARTSTYLE="graceful" +depend() { + need net + use mysql dns logger netmount postgresql + after sshd +} + +configtest() { + ebegin "Checking Apache Configuration" + checkconfig + eend $? +} checkconfig() { - local myconf="/etc/apache2/conf/apache2.conf" - if [ "x${CONFIGFILE}" != "x" ]; then - if [ ${CONFIGFILE:0:1} = "/" ]; then - myconf="${CONFIGFILE}" - else - myconf="${SERVERROOT:-/usr/lib/apache2}/${CONFIGFILE}" - fi + SERVERROOT="${SERVERROOT:-/usr/lib/apache2}" + if [ ! -d ${SERVERROOT} ]; then + eerror "SERVERROOT does not exist: ${SERVERROOT}" + return 1 fi - if [ ! -r "${myconf}" ]; then - eerror "Unable to read configuration file: ${myconf}" + + CONFIGFILE="${CONFIGFILE:-/etc/apache2/httpd.conf}" + [ "${CONFIGFILE#/}" = "${CONFIGFILE}" ] && CONFIGFILE="${SERVERROOT}/${CONFIGFILE}" + if [ ! -r "${CONFIGFILE}" ]; then + eerror "Unable to read configuration file: ${CONFIGFILE}" return 1 fi - if [ -z "${PIDFILE}" ]; then - eerror "\$PIDFILE is not set!" - eerror "Did you etc-update /etc/conf.d/apache2?" - return 1 - fi - if [ -z "${RESTARTSTYLE}" ]; then - eerror "\$RESTARTSTYLE is not set!" - eerror "Did you etc-update /etc/conf.d/apache2?" - return 1 - fi - /usr/sbin/apache2 -t ${APACHE2_OPTS} 1>/dev/null 2>&1 + + APACHE2_OPTS="${APACHE2_OPTS} -d ${SERVERROOT}" + APACHE2_OPTS="${APACHE2_OPTS} -f ${CONFIGFILE}" + [ -n "${STARTUPERRORLOG}" ] && APACHE2_OPTS="${APACHE2_OPTS} -E ${STARTUPERRORLOG}" + + APACHE2="/usr/sbin/apache2" + + ${APACHE2} ${APACHE2_OPTS} -t 1>/dev/null 2>&1 ret=$? if [ $ret -ne 0 ]; then eerror "Apache2 has detected a syntax error in your configuration files:" - /usr/sbin/apache2 -t ${APACHE2_OPTS} + ${APACHE2} ${APACHE2_OPTS} -t fi - return $ret -} -depend() { - need net - use mysql dns logger netmount postgres - after sshd + return $ret } start() { checkconfig || return 1 ebegin "Starting apache2" [ -f /var/log/apache2/ssl_scache ] && rm /var/log/apache2/ssl_scache - [ -f /usr/lib/apache2/build/envvars ] && . /usr/lib/apache2/build/envvars - env -i PATH=$PATH /sbin/start-stop-daemon --quiet \ - --start --startas /usr/sbin/apache2 \ - --pidfile ${PIDFILE} -- -k start ${APACHE2_OPTS} + + start-stop-daemon --start --exec ${APACHE2} -- ${APACHE2_OPTS} -k start eend $? } stop() { + checkconfig || return 1 ebegin "Stopping apache2" - /usr/sbin/apache2ctl stop >/dev/null - start-stop-daemon -o --quiet --stop --pidfile ${PIDFILE} + start-stop-daemon --stop --retry -TERM/5/-KILL/5 --exec ${APACHE2} --pidfile /var/run/apache2.pid eend $? } reload() { - # restarting apache2 is much easier than apache1. The server handles most of the work for us. - # see http://httpd.apache.org/docs-2.0/stopping.html for more details - ebegin "Restarting apache2" - /usr/sbin/apache2 ${APACHE2_OPTS} -k ${RESTARTSTYLE} + RELOAD_TYPE="${RELOAD_TYPE:-graceful}" + + checkconfig || return 1 + if [ "${RELOAD_TYPE}" = "restart" ]; then + ebegin "Restarting apache2" + start-stop-daemon --stop --oknodo --signal HUP --exec ${APACHE2} --pidfile /var/run/apache2.pid + eend $? + elif [ "${RELOAD_TYPE}" = "graceful" ]; then + ebegin "Gracefully restarting apache2" + start-stop-daemon --stop --oknodo --signal USR1 --exec ${APACHE2} --pidfile /var/run/apache2.pid + eend $? + else + eerror "${RELOAD_TYPE} is not a valid RELOAD_TYPE. Please edit /etc/conf.d/apache2" + fi +} + +graceful() { + checkconfig || return 1 + ebegin "Gracefully restarting apache2" + start-stop-daemon --stop --signal USR1 --exec ${APACHE2} --pidfile /var/run/apache2.pid + eend $? +} + +gracefulstop() { + checkconfig || return 1 + + # zap! + if service_started "${myservice}"; then + mark_service_stopped "${myservice}" + fi + + ebegin "Gracefully stopping apache2" + # 28 is SIGWINCH + start-stop-daemon --stop --signal 28 --exec ${APACHE2} --pidfile /var/run/apache2.pid eend $? } + +modules() { + checkconfig || return 1 + + ${APACHE2} ${APACHE2_OPTS} -M 2>&1 +} + +status() { + LYNX="${LYNX:-lynx -dump}" + STATUSURL="${STATUSURL:-http://localhost/server-status}" + + ${LYNX} ${STATUSURL} | awk ' /process$/ { print; exit } { print } ' +} + +fullstatus() { + LYNX="${LYNX:-lynx -dump}" + STATUSURL="${STATUSURL:-http://localhost/server-status}" + + ${LYNX} ${STATUSURL} +} diff --git a/testing/hosts/winnetou/etc/runlevels/default/apache2 b/testing/hosts/winnetou/etc/runlevels/default/apache2 index f54f3444a..5f72d3090 100755 --- a/testing/hosts/winnetou/etc/runlevels/default/apache2 +++ b/testing/hosts/winnetou/etc/runlevels/default/apache2 @@ -1,78 +1,121 @@ #!/sbin/runscript -# Copyright 1999-2004 Gentoo Foundation +# Copyright 1999-2007 Gentoo Foundation # Distributed under the terms of the GNU General Public License v2 -opts="${opts} reload" +opts="configtest fullstatus graceful gracefulstop modules reload" -[ "x${SERVERROOT}" != "x" ] && APACHE2_OPTS="${APACHE2_OPTS} -d ${SERVERROOT}" -[ "x${CONFIGFILE}" != "x" ] && APACHE2_OPTS="${APACHE2_OPTS} -f ${CONFIGFILE}" -[ "x${STARTUPERRORLOG}" != "x" ] && APACHE2_OPTS="${APACHE2_OPTS} -E ${STARTUPERRORLOG}" -# set a default for PIDFILE/RESTARTSTYLE for those that FAILED to follow -# instructiosn and update the conf.d/apache2 file. -# (bug #38787) -[ -z "${PIDFILE}" ] && PIDFILE=/var/run/apache2.pid -[ -z "${RESTARTSTYLE}" ] && RESTARTSTYLE="graceful" +depend() { + need net + use mysql dns logger netmount postgresql + after sshd +} + +configtest() { + ebegin "Checking Apache Configuration" + checkconfig + eend $? +} checkconfig() { - local myconf="/etc/apache2/conf/apache2.conf" - if [ "x${CONFIGFILE}" != "x" ]; then - if [ ${CONFIGFILE:0:1} = "/" ]; then - myconf="${CONFIGFILE}" - else - myconf="${SERVERROOT:-/usr/lib/apache2}/${CONFIGFILE}" - fi + SERVERROOT="${SERVERROOT:-/usr/lib/apache2}" + if [ ! -d ${SERVERROOT} ]; then + eerror "SERVERROOT does not exist: ${SERVERROOT}" + return 1 fi - if [ ! -r "${myconf}" ]; then - eerror "Unable to read configuration file: ${myconf}" + + CONFIGFILE="${CONFIGFILE:-/etc/apache2/httpd.conf}" + [ "${CONFIGFILE#/}" = "${CONFIGFILE}" ] && CONFIGFILE="${SERVERROOT}/${CONFIGFILE}" + if [ ! -r "${CONFIGFILE}" ]; then + eerror "Unable to read configuration file: ${CONFIGFILE}" return 1 fi - if [ -z "${PIDFILE}" ]; then - eerror "\$PIDFILE is not set!" - eerror "Did you etc-update /etc/conf.d/apache2?" - return 1 - fi - if [ -z "${RESTARTSTYLE}" ]; then - eerror "\$RESTARTSTYLE is not set!" - eerror "Did you etc-update /etc/conf.d/apache2?" - return 1 - fi - /usr/sbin/apache2 -t ${APACHE2_OPTS} 1>/dev/null 2>&1 + + APACHE2_OPTS="${APACHE2_OPTS} -d ${SERVERROOT}" + APACHE2_OPTS="${APACHE2_OPTS} -f ${CONFIGFILE}" + [ -n "${STARTUPERRORLOG}" ] && APACHE2_OPTS="${APACHE2_OPTS} -E ${STARTUPERRORLOG}" + + APACHE2="/usr/sbin/apache2" + + ${APACHE2} ${APACHE2_OPTS} -t 1>/dev/null 2>&1 ret=$? if [ $ret -ne 0 ]; then eerror "Apache2 has detected a syntax error in your configuration files:" - /usr/sbin/apache2 -t ${APACHE2_OPTS} + ${APACHE2} ${APACHE2_OPTS} -t fi - return $ret -} -depend() { - need net - use mysql dns logger netmount postgres - after sshd + return $ret } start() { checkconfig || return 1 ebegin "Starting apache2" [ -f /var/log/apache2/ssl_scache ] && rm /var/log/apache2/ssl_scache - [ -f /usr/lib/apache2/build/envvars ] && . /usr/lib/apache2/build/envvars - env -i PATH=$PATH /sbin/start-stop-daemon --quiet \ - --start --startas /usr/sbin/apache2 \ - --pidfile ${PIDFILE} -- -k start ${APACHE2_OPTS} + + start-stop-daemon --start --exec ${APACHE2} -- ${APACHE2_OPTS} -k start eend $? } stop() { + checkconfig || return 1 ebegin "Stopping apache2" - /usr/sbin/apache2ctl stop >/dev/null - start-stop-daemon -o --quiet --stop --pidfile ${PIDFILE} + start-stop-daemon --stop --retry -TERM/5/-KILL/5 --exec ${APACHE2} --pidfile /var/run/apache2.pid eend $? } reload() { - # restarting apache2 is much easier than apache1. The server handles most of the work for us. - # see http://httpd.apache.org/docs-2.0/stopping.html for more details - ebegin "Restarting apache2" - /usr/sbin/apache2 ${APACHE2_OPTS} -k ${RESTARTSTYLE} + RELOAD_TYPE="${RELOAD_TYPE:-graceful}" + + checkconfig || return 1 + if [ "${RELOAD_TYPE}" = "restart" ]; then + ebegin "Restarting apache2" + start-stop-daemon --stop --oknodo --signal HUP --exec ${APACHE2} --pidfile /var/run/apache2.pid + eend $? + elif [ "${RELOAD_TYPE}" = "graceful" ]; then + ebegin "Gracefully restarting apache2" + start-stop-daemon --stop --oknodo --signal USR1 --exec ${APACHE2} --pidfile /var/run/apache2.pid + eend $? + else + eerror "${RELOAD_TYPE} is not a valid RELOAD_TYPE. Please edit /etc/conf.d/apache2" + fi +} + +graceful() { + checkconfig || return 1 + ebegin "Gracefully restarting apache2" + start-stop-daemon --stop --signal USR1 --exec ${APACHE2} --pidfile /var/run/apache2.pid + eend $? +} + +gracefulstop() { + checkconfig || return 1 + + # zap! + if service_started "${myservice}"; then + mark_service_stopped "${myservice}" + fi + + ebegin "Gracefully stopping apache2" + # 28 is SIGWINCH + start-stop-daemon --stop --signal 28 --exec ${APACHE2} --pidfile /var/run/apache2.pid eend $? } + +modules() { + checkconfig || return 1 + + ${APACHE2} ${APACHE2_OPTS} -M 2>&1 +} + +status() { + LYNX="${LYNX:-lynx -dump}" + STATUSURL="${STATUSURL:-http://localhost/server-status}" + + ${LYNX} ${STATUSURL} | awk ' /process$/ { print; exit } { print } ' +} + +fullstatus() { + LYNX="${LYNX:-lynx -dump}" + STATUSURL="${STATUSURL:-http://localhost/server-status}" + + ${LYNX} ${STATUSURL} +} diff --git a/testing/images/a-m-c-w-d-ip6.png b/testing/images/a-m-c-w-d-ip6.png new file mode 100644 index 000000000..2b81d5c2b Binary files /dev/null and b/testing/images/a-m-c-w-d-ip6.png differ diff --git a/testing/images/a-m-c-w-ip6.png b/testing/images/a-m-c-w-ip6.png new file mode 100644 index 000000000..374ca8069 Binary files /dev/null and b/testing/images/a-m-c-w-ip6.png differ diff --git a/testing/images/a-m-c-w-s-b-med.png b/testing/images/a-m-c-w-s-b-med.png new file mode 100644 index 000000000..5b31fa120 Binary files /dev/null and b/testing/images/a-m-c-w-s-b-med.png differ diff --git a/testing/images/a-m-w-s-b-ip6.png b/testing/images/a-m-w-s-b-ip6.png new file mode 100644 index 000000000..fbce9793e Binary files /dev/null and b/testing/images/a-m-w-s-b-ip6.png differ diff --git a/testing/images/a-v-m-c-w-med.png b/testing/images/a-v-m-c-w-med.png new file mode 100644 index 000000000..9a47aa360 Binary files /dev/null and b/testing/images/a-v-m-c-w-med.png differ diff --git a/testing/images/m-w-s-ip6.png b/testing/images/m-w-s-ip6.png new file mode 100644 index 000000000..50d05b70e Binary files /dev/null and b/testing/images/m-w-s-ip6.png differ diff --git a/testing/images/m-w-s.png b/testing/images/m-w-s.png index 5f1aee2aa..14115c1f3 100755 Binary files a/testing/images/m-w-s.png and b/testing/images/m-w-s.png differ diff --git a/testing/scripts/build-umlrootfs b/testing/scripts/build-umlrootfs index 3498f216e..b205f62a6 100755 --- a/testing/scripts/build-umlrootfs +++ b/testing/scripts/build-umlrootfs @@ -14,7 +14,7 @@ # or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License # for more details. # -# RCSID $Id: build-umlrootfs 3273 2007-10-08 20:18:34Z andreas $ +# RCSID $Id: build-umlrootfs 3404 2007-12-19 00:47:56Z andreas $ DIR=`dirname $0` @@ -141,10 +141,21 @@ then echo -n " --enable-ldap" >> $INSTALLSHELL fi +if [ "$USE_EAP_AKA" = "yes" ] +then + echo -n " --enable-eap-aka" >> $INSTALLSHELL +fi + +if [ "$USE_P2P" = "yes" ] +then + echo -n " --enable-p2p" >> $INSTALLSHELL +fi + if [ "$USE_LEAK_DETECTIVE" = "yes" ] then echo -n " --enable-leak-detective" >> $INSTALLSHELL fi + echo "" >> $INSTALLSHELL echo "make" >> $INSTALLSHELL echo "make install" >> $INSTALLSHELL diff --git a/testing/testing.conf b/testing/testing.conf index aecedd7ae..7665f877a 100755 --- a/testing/testing.conf +++ b/testing/testing.conf @@ -21,28 +21,30 @@ UMLTESTDIR=~/strongswan-testing # Bzipped kernel sources # (file extension .tar.bz2 required) -KERNEL=$UMLTESTDIR/linux-2.6.22.1.tar.bz2 +KERNEL=$UMLTESTDIR/linux-2.6.23.11.tar.bz2 # Extract kernel version KERNELVERSION=`basename $KERNEL .tar.bz2 | sed -e 's/linux-//'` # Kernel configuration file -KERNELCONFIG=$UMLTESTDIR/.config-2.6.22 +KERNELCONFIG=$UMLTESTDIR/.config-2.6.23 # Bzipped uml patch for kernel # (not needed anymore for 2.6.9 kernel or higher) #UMLPATCH=$UMLTESTDIR/uml_jmpbuf-2.6.18.patch.bz2 # Bzipped source of strongSwan -STRONGSWAN=$UMLTESTDIR/strongswan-4.1.7.tar.bz2 +STRONGSWAN=$UMLTESTDIR/strongswan-4.1.10.tar.bz2 # strongSwan compile options (use "yes" or "no") USE_LIBCURL="yes" USE_LDAP="yes" +USE_EAP_AKA="yes" +USE_P2P="yes" USE_LEAK_DETECTIVE="no" # Gentoo linux root filesystem -ROOTFS=$UMLTESTDIR/gentoo-fs-20070702.tar.bz2 +ROOTFS=$UMLTESTDIR/gentoo-fs-20071108.tar.bz2 # Size of the finished root filesystem in MB ROOTFSSIZE=544 diff --git a/testing/tests/ikev1/host2host-transport/evaltest.dat b/testing/tests/ikev1/host2host-transport/evaltest.dat index d19f970f2..04c0eb3a2 100644 --- a/testing/tests/ikev1/host2host-transport/evaltest.dat +++ b/testing/tests/ikev1/host2host-transport/evaltest.dat @@ -1,5 +1,7 @@ moon::ipsec status::host-host.*STATE_QUICK_I2.*IPsec SA established::YES sun::ipsec status::host-host.*STATE_QUICK_R2.*IPsec SA established::YES +moon::ip xfrm state::mode transport::YES +sun::ip xfrm state::mode transport::YES moon::ping -c 1 PH_IP_SUN::64 bytes from PH_IP_SUN: icmp_seq=1::YES sun::tcpdump::IP moon.strongswan.org > sun.strongswan.org: ESP::YES sun::tcpdump::IP sun.strongswan.org > moon.strongswan.org: ESP::YES diff --git a/testing/tests/ikev2/host2host-transport/evaltest.dat b/testing/tests/ikev2/host2host-transport/evaltest.dat index a46e4e4e4..2dd58c9d7 100644 --- a/testing/tests/ikev2/host2host-transport/evaltest.dat +++ b/testing/tests/ikev2/host2host-transport/evaltest.dat @@ -1,5 +1,8 @@ +moon::cat /var/log/daemon.log::received USE_TRANSPORT_MODE notify::YES moon::ipsec status::host-host.*INSTALLED.*TRANSPORT::YES sun::ipsec status::host-host.*INSTALLED.*TRANSPORT::YES +moon::ip xfrm state::mode transport::YES +sun::ip xfrm state::mode transport::YES moon::ping -c 1 PH_IP_SUN::64 bytes from PH_IP_SUN: icmp_seq=1::YES sun::tcpdump::IP moon.strongswan.org > sun.strongswan.org: ESP::YES sun::tcpdump::IP sun.strongswan.org > moon.strongswan.org: ESP::YES diff --git a/testing/tests/ikev2/host2host-transport/hosts/moon/etc/ipsec.conf b/testing/tests/ikev2/host2host-transport/hosts/moon/etc/ipsec.conf index b80aa80c4..7f6c5a58a 100755 --- a/testing/tests/ikev2/host2host-transport/hosts/moon/etc/ipsec.conf +++ b/testing/tests/ikev2/host2host-transport/hosts/moon/etc/ipsec.conf @@ -10,6 +10,7 @@ conn %default keylife=20m rekeymargin=3m keyingtries=1 + mobike=no keyexchange=ikev2 conn host-host diff --git a/testing/tests/ikev2/host2host-transport/hosts/sun/etc/ipsec.conf b/testing/tests/ikev2/host2host-transport/hosts/sun/etc/ipsec.conf index dd1811083..af52fb22b 100755 --- a/testing/tests/ikev2/host2host-transport/hosts/sun/etc/ipsec.conf +++ b/testing/tests/ikev2/host2host-transport/hosts/sun/etc/ipsec.conf @@ -10,6 +10,7 @@ conn %default keylife=20m rekeymargin=3m keyingtries=1 + mobike=no keyexchange=ikev2 conn host-host diff --git a/testing/tests/ikev2/reauth-early/description.txt b/testing/tests/ikev2/reauth-early/description.txt new file mode 100644 index 000000000..130d08d28 --- /dev/null +++ b/testing/tests/ikev2/reauth-early/description.txt @@ -0,0 +1,7 @@ +This scenario tests repeated authentication according to RFC 4478. +The iniator carol sets a large ikelifetime=20m but the responder +moon defining a much shorter ikelifetime=30s proposes this +value via an AUTH_LIFETIME notification to the initiator. Thus the +IKE reauthentication takes places after less than 30s. A ping from +carol to client alice hiding in the subnet behind moon +tests if the CHILD_SA has been inherited by the new IKE_SA. diff --git a/testing/tests/ikev2/reauth-early/evaltest.dat b/testing/tests/ikev2/reauth-early/evaltest.dat new file mode 100644 index 000000000..b4cbe2f41 --- /dev/null +++ b/testing/tests/ikev2/reauth-early/evaltest.dat @@ -0,0 +1,6 @@ +moon::ipsec statusall::rw\[2\].*ESTABLISHED::YES +carol::ipsec statusall::home\[2\].*ESTABLISHED::YES +carol::cat /var/log/daemon.log::received AUTH_LIFETIME of 30s, scheduling reauthentication in 25s::YES +carol::ping -c 1 PH_IP_ALICE::64 bytes from PH_IP_ALICE: icmp_seq=1::YES +moon::tcpdump::IP carol.strongswan.org > moon.strongswan.org: ESP::YES +moon::tcpdump::IP moon.strongswan.org > carol.strongswan.org: ESP::YES diff --git a/testing/tests/ikev2/reauth-early/hosts/carol/etc/ipsec.conf b/testing/tests/ikev2/reauth-early/hosts/carol/etc/ipsec.conf new file mode 100755 index 000000000..311dc3dc5 --- /dev/null +++ b/testing/tests/ikev2/reauth-early/hosts/carol/etc/ipsec.conf @@ -0,0 +1,23 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=5s + keyingtries=1 + +conn home + left=PH_IP_CAROL + leftcert=carolCert.pem + leftid=carol@strongswan.org + leftfirewall=yes + right=PH_IP_MOON + rightid=@moon.strongswan.org + rightsubnet=10.1.0.0/16 + keyexchange=ikev2 + auto=add diff --git a/testing/tests/ikev2/reauth-early/hosts/moon/etc/ipsec.conf b/testing/tests/ikev2/reauth-early/hosts/moon/etc/ipsec.conf new file mode 100755 index 000000000..64a7aef6d --- /dev/null +++ b/testing/tests/ikev2/reauth-early/hosts/moon/etc/ipsec.conf @@ -0,0 +1,22 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=30s + keylife=20m + rekeymargin=0s + keyingtries=1 + +conn rw + left=PH_IP_MOON + leftcert=moonCert.pem + leftid=@moon.strongswan.org + leftsubnet=10.1.0.0/16 + leftfirewall=yes + right=%any + keyexchange=ikev2 + auto=add diff --git a/testing/tests/ikev2/reauth-early/posttest.dat b/testing/tests/ikev2/reauth-early/posttest.dat new file mode 100644 index 000000000..94a400606 --- /dev/null +++ b/testing/tests/ikev2/reauth-early/posttest.dat @@ -0,0 +1,4 @@ +moon::ipsec stop +carol::ipsec stop +moon::/etc/init.d/iptables stop 2> /dev/null +carol::/etc/init.d/iptables stop 2> /dev/null diff --git a/testing/tests/ikev2/reauth-early/pretest.dat b/testing/tests/ikev2/reauth-early/pretest.dat new file mode 100644 index 000000000..7ed2423be --- /dev/null +++ b/testing/tests/ikev2/reauth-early/pretest.dat @@ -0,0 +1,7 @@ +moon::/etc/init.d/iptables start 2> /dev/null +carol::/etc/init.d/iptables start 2> /dev/null +moon::ipsec start +carol::ipsec start +carol::sleep 1 +carol::ipsec up home +carol::sleep 30 diff --git a/testing/tests/ikev2/reauth-early/test.conf b/testing/tests/ikev2/reauth-early/test.conf new file mode 100644 index 000000000..9cd583b16 --- /dev/null +++ b/testing/tests/ikev2/reauth-early/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="alice moon carol winnetou" + +# Corresponding block diagram +# +DIAGRAM="a-m-c-w.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="moon" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="moon carol" diff --git a/testing/tests/ikev2/reauth-late/description.txt b/testing/tests/ikev2/reauth-late/description.txt new file mode 100644 index 000000000..e4f05e1d4 --- /dev/null +++ b/testing/tests/ikev2/reauth-late/description.txt @@ -0,0 +1,8 @@ +This scenario tests repeated authentication according to RFC 4478. +The iniator carol sets a short ikelifetime=20m but the responder +moon defining a much larger ikelifetime=30s proposes this +value via an AUTH_LIFETIME notification to the initiator. The initatior +ignores this notification and schedules the IKE reauthentication within +the shorter interval of 30s. A ping from carol to client alice +hiding in the subnet behind moon tests if the CHILD_SA has been +inherited by the new IKE_SA. diff --git a/testing/tests/ikev2/reauth-late/evaltest.dat b/testing/tests/ikev2/reauth-late/evaltest.dat new file mode 100644 index 000000000..7ce2bf147 --- /dev/null +++ b/testing/tests/ikev2/reauth-late/evaltest.dat @@ -0,0 +1,7 @@ +moon::ipsec statusall::rw\[2\].*ESTABLISHED::YES +carol::ipsec statusall::home\[2\].*ESTABLISHED::YES +carol::cat /var/log/daemon.log::received AUTH_LIFETIME of 3600s, scheduling reauthentication in 3595s::YES +carol::cat /var/log/daemon.log::scheduling reauthentication in 2[0-5]s::YES +carol::ping -c 1 PH_IP_ALICE::64 bytes from PH_IP_ALICE: icmp_seq=1::YES +moon::tcpdump::IP carol.strongswan.org > moon.strongswan.org: ESP::YES +moon::tcpdump::IP moon.strongswan.org > carol.strongswan.org: ESP::YES diff --git a/testing/tests/ikev2/reauth-late/hosts/carol/etc/ipsec.conf b/testing/tests/ikev2/reauth-late/hosts/carol/etc/ipsec.conf new file mode 100755 index 000000000..32a43efac --- /dev/null +++ b/testing/tests/ikev2/reauth-late/hosts/carol/etc/ipsec.conf @@ -0,0 +1,23 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=30s + keylife=20m + rekeymargin=5s + keyingtries=1 + +conn home + left=PH_IP_CAROL + leftcert=carolCert.pem + leftid=carol@strongswan.org + leftfirewall=yes + right=PH_IP_MOON + rightid=@moon.strongswan.org + rightsubnet=10.1.0.0/16 + keyexchange=ikev2 + auto=add diff --git a/testing/tests/ikev2/reauth-late/hosts/moon/etc/ipsec.conf b/testing/tests/ikev2/reauth-late/hosts/moon/etc/ipsec.conf new file mode 100755 index 000000000..bdd186a04 --- /dev/null +++ b/testing/tests/ikev2/reauth-late/hosts/moon/etc/ipsec.conf @@ -0,0 +1,22 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=0s + keyingtries=1 + +conn rw + left=PH_IP_MOON + leftcert=moonCert.pem + leftid=@moon.strongswan.org + leftsubnet=10.1.0.0/16 + leftfirewall=yes + right=%any + keyexchange=ikev2 + auto=add diff --git a/testing/tests/ikev2/reauth-late/posttest.dat b/testing/tests/ikev2/reauth-late/posttest.dat new file mode 100644 index 000000000..94a400606 --- /dev/null +++ b/testing/tests/ikev2/reauth-late/posttest.dat @@ -0,0 +1,4 @@ +moon::ipsec stop +carol::ipsec stop +moon::/etc/init.d/iptables stop 2> /dev/null +carol::/etc/init.d/iptables stop 2> /dev/null diff --git a/testing/tests/ikev2/reauth-late/pretest.dat b/testing/tests/ikev2/reauth-late/pretest.dat new file mode 100644 index 000000000..7ed2423be --- /dev/null +++ b/testing/tests/ikev2/reauth-late/pretest.dat @@ -0,0 +1,7 @@ +moon::/etc/init.d/iptables start 2> /dev/null +carol::/etc/init.d/iptables start 2> /dev/null +moon::ipsec start +carol::ipsec start +carol::sleep 1 +carol::ipsec up home +carol::sleep 30 diff --git a/testing/tests/ikev2/reauth-late/test.conf b/testing/tests/ikev2/reauth-late/test.conf new file mode 100644 index 000000000..9cd583b16 --- /dev/null +++ b/testing/tests/ikev2/reauth-late/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="alice moon carol winnetou" + +# Corresponding block diagram +# +DIAGRAM="a-m-c-w.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="moon" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="moon carol" diff --git a/testing/tests/ikev2/rw-eap-aka-rsa/description.txt b/testing/tests/ikev2/rw-eap-aka-rsa/description.txt new file mode 100644 index 000000000..b4f766d6f --- /dev/null +++ b/testing/tests/ikev2/rw-eap-aka-rsa/description.txt @@ -0,0 +1,7 @@ +The roadwarrior carol sets up a connection to gateway moon. +carol uses the Extensible Authentication Protocol +in association with the Authentication and Key Agreement protocol +(EAP-AKA) to authenticate against the gateway. This protocol is used +in UMTS, but here a secret from ipsec.secrets is used instead of a USIM/(R)UIM. +Gateway moon additionaly uses an RSA signature to authenticate itself +against carol. diff --git a/testing/tests/ikev2/rw-eap-aka-rsa/evaltest.dat b/testing/tests/ikev2/rw-eap-aka-rsa/evaltest.dat new file mode 100644 index 000000000..5de841c03 --- /dev/null +++ b/testing/tests/ikev2/rw-eap-aka-rsa/evaltest.dat @@ -0,0 +1,10 @@ +carol::cat /var/log/daemon.log::authentication of 'moon.strongswan.org' with RSA signature successful::YES +carol::cat /var/log/daemon.log::authentication of 'moon.strongswan.org' with EAP successful::YES +moon::cat /var/log/daemon.log::authentication of 'carol@strongswan.org' with EAP successful::YES +moon::ipsec statusall::rw-eapaka.*ESTABLISHED::YES +carol::ipsec statusall::home.*ESTABLISHED::YES +carol::ping -c 1 PH_IP_ALICE::64 bytes from PH_IP_ALICE: icmp_seq=1::YES +moon::tcpdump::IP carol.strongswan.org > moon.strongswan.org: ESP::YES +moon::tcpdump::IP moon.strongswan.org > carol.strongswan.org: ESP::YES + + diff --git a/testing/tests/ikev2/rw-eap-aka-rsa/hosts/carol/etc/ipsec.conf b/testing/tests/ikev2/rw-eap-aka-rsa/hosts/carol/etc/ipsec.conf new file mode 100755 index 000000000..c2fe02639 --- /dev/null +++ b/testing/tests/ikev2/rw-eap-aka-rsa/hosts/carol/etc/ipsec.conf @@ -0,0 +1,23 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + authby=eap + +conn home + left=PH_IP_CAROL + leftnexthop=%direct + leftid=carol@strongswan.org + leftfirewall=yes + right=PH_IP_MOON + rightid=@moon.strongswan.org + rightsubnet=10.1.0.0/16 + rightsendcert=never + auto=add diff --git a/testing/tests/ikev2/rw-eap-aka-rsa/hosts/carol/etc/ipsec.secrets b/testing/tests/ikev2/rw-eap-aka-rsa/hosts/carol/etc/ipsec.secrets new file mode 100644 index 000000000..e03e89a0f --- /dev/null +++ b/testing/tests/ikev2/rw-eap-aka-rsa/hosts/carol/etc/ipsec.secrets @@ -0,0 +1,3 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +carol@strongswan.org : EAP "Ar3etTnp01qlpOgb" diff --git a/testing/tests/ikev2/rw-eap-aka-rsa/hosts/moon/etc/ipsec.conf b/testing/tests/ikev2/rw-eap-aka-rsa/hosts/moon/etc/ipsec.conf new file mode 100755 index 000000000..dbf38160f --- /dev/null +++ b/testing/tests/ikev2/rw-eap-aka-rsa/hosts/moon/etc/ipsec.conf @@ -0,0 +1,24 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + +conn rw-eapaka + authby=rsasig + eap=aka + left=PH_IP_MOON + leftsubnet=10.1.0.0/16 + leftid=@moon.strongswan.org + leftcert=moonCert.pem + leftfirewall=yes + rightid=*@strongswan.org + right=%any + auto=add diff --git a/testing/tests/ikev2/rw-eap-aka-rsa/hosts/moon/etc/ipsec.secrets b/testing/tests/ikev2/rw-eap-aka-rsa/hosts/moon/etc/ipsec.secrets new file mode 100644 index 000000000..aa3838385 --- /dev/null +++ b/testing/tests/ikev2/rw-eap-aka-rsa/hosts/moon/etc/ipsec.secrets @@ -0,0 +1,5 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +: RSA moonKey.pem + +carol@strongswan.org : EAP "Ar3etTnp01qlpOgb" diff --git a/testing/tests/ikev2/rw-eap-aka-rsa/posttest.dat b/testing/tests/ikev2/rw-eap-aka-rsa/posttest.dat new file mode 100644 index 000000000..94a400606 --- /dev/null +++ b/testing/tests/ikev2/rw-eap-aka-rsa/posttest.dat @@ -0,0 +1,4 @@ +moon::ipsec stop +carol::ipsec stop +moon::/etc/init.d/iptables stop 2> /dev/null +carol::/etc/init.d/iptables stop 2> /dev/null diff --git a/testing/tests/ikev2/rw-eap-aka-rsa/pretest.dat b/testing/tests/ikev2/rw-eap-aka-rsa/pretest.dat new file mode 100644 index 000000000..ed5498bfe --- /dev/null +++ b/testing/tests/ikev2/rw-eap-aka-rsa/pretest.dat @@ -0,0 +1,7 @@ +moon::/etc/init.d/iptables start 2> /dev/null +carol::/etc/init.d/iptables start 2> /dev/null +moon::ipsec start +carol::ipsec start +carol::sleep 1 +carol::ipsec up home +carol::sleep 1 diff --git a/testing/tests/ikev2/rw-eap-aka-rsa/test.conf b/testing/tests/ikev2/rw-eap-aka-rsa/test.conf new file mode 100644 index 000000000..2bd21499b --- /dev/null +++ b/testing/tests/ikev2/rw-eap-aka-rsa/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="alice carol moon" + +# Corresponding block diagram +# +DIAGRAM="a-m-c.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="moon" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="moon carol" diff --git a/testing/tests/ipv6/host2host-ikev1/description.txt b/testing/tests/ipv6/host2host-ikev1/description.txt index c59b32acb..b52c4caf8 100644 --- a/testing/tests/ipv6/host2host-ikev1/description.txt +++ b/testing/tests/ipv6/host2host-ikev1/description.txt @@ -1,3 +1,5 @@ An IPv6 ESP connection between the hosts moon and sun is successfully set up. -The authentication is based on X.509 certificates. In order to test the host-to-host tunnel -moon sends an IPv6 ICMP request to sun using the ping6 command. +The authentication is based on X.509 certificates. Upon the successful establishment of +the IPsec tunnel, leftfirewall=yes automatically inserts ip6tables-based firewall +rules that let pass the tunneled traffic. In order to test both the host-to-host tunnel +and the firewall rules, moon sends an IPv6 ICMP request to sun using the ping6 command. diff --git a/testing/tests/ipv6/host2host-ikev1/hosts/moon/etc/init.d/iptables b/testing/tests/ipv6/host2host-ikev1/hosts/moon/etc/init.d/iptables new file mode 100755 index 000000000..521d1ce31 --- /dev/null +++ b/testing/tests/ipv6/host2host-ikev1/hosts/moon/etc/init.d/iptables @@ -0,0 +1,100 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/host2host-ikev1/hosts/moon/etc/ipsec.conf b/testing/tests/ipv6/host2host-ikev1/hosts/moon/etc/ipsec.conf index 9499140c5..2814e881f 100755 --- a/testing/tests/ipv6/host2host-ikev1/hosts/moon/etc/ipsec.conf +++ b/testing/tests/ipv6/host2host-ikev1/hosts/moon/etc/ipsec.conf @@ -19,12 +19,9 @@ conn net-net conn host-host left=PH_IP6_MOON - leftnexthop=0::0 leftcert=moonCert.pem leftid=@moon.strongswan.org leftfirewall=yes right=PH_IP6_SUN - rightnexthop=0::0 rightid=@sun.strongswan.org auto=add - diff --git a/testing/tests/ipv6/host2host-ikev1/hosts/sun/etc/init.d/iptables b/testing/tests/ipv6/host2host-ikev1/hosts/sun/etc/init.d/iptables new file mode 100755 index 000000000..521d1ce31 --- /dev/null +++ b/testing/tests/ipv6/host2host-ikev1/hosts/sun/etc/init.d/iptables @@ -0,0 +1,100 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/host2host-ikev1/hosts/sun/etc/ipsec.conf b/testing/tests/ipv6/host2host-ikev1/hosts/sun/etc/ipsec.conf index c64904a6e..4cf027ad5 100755 --- a/testing/tests/ipv6/host2host-ikev1/hosts/sun/etc/ipsec.conf +++ b/testing/tests/ipv6/host2host-ikev1/hosts/sun/etc/ipsec.conf @@ -19,11 +19,9 @@ conn net-net conn host-host left=PH_IP6_SUN - leftnexthop=0::0 leftcert=sunCert.pem leftid=@sun.strongswan.org leftfirewall=yes right=PH_IP6_MOON - rightnexthop=0::0 rightid=@moon.strongswan.org auto=add diff --git a/testing/tests/ipv6/host2host-ikev1/posttest.dat b/testing/tests/ipv6/host2host-ikev1/posttest.dat index dff181797..5a9150bc8 100644 --- a/testing/tests/ipv6/host2host-ikev1/posttest.dat +++ b/testing/tests/ipv6/host2host-ikev1/posttest.dat @@ -1,2 +1,4 @@ moon::ipsec stop sun::ipsec stop +moon::/etc/init.d/iptables stop 2> /dev/null +sun::/etc/init.d/iptables stop 2> /dev/null diff --git a/testing/tests/ipv6/host2host-ikev1/pretest.dat b/testing/tests/ipv6/host2host-ikev1/pretest.dat index 4707af077..3536fd886 100644 --- a/testing/tests/ipv6/host2host-ikev1/pretest.dat +++ b/testing/tests/ipv6/host2host-ikev1/pretest.dat @@ -1,3 +1,5 @@ +moon::/etc/init.d/iptables start 2> /dev/null +sun::/etc/init.d/iptables start 2> /dev/null moon::ipsec start sun::ipsec start moon::sleep 2 diff --git a/testing/tests/ipv6/host2host-ikev1/test.conf b/testing/tests/ipv6/host2host-ikev1/test.conf index cf2e704fd..6ab5b8a96 100644 --- a/testing/tests/ipv6/host2host-ikev1/test.conf +++ b/testing/tests/ipv6/host2host-ikev1/test.conf @@ -9,7 +9,7 @@ UMLHOSTS="moon winnetou sun" # Corresponding block diagram # -DIAGRAM="m-w-s.png" +DIAGRAM="m-w-s-ip6.png" # UML instances on which tcpdump is to be started # diff --git a/testing/tests/ipv6/host2host-ikev2/description.txt b/testing/tests/ipv6/host2host-ikev2/description.txt index c59b32acb..b52c4caf8 100644 --- a/testing/tests/ipv6/host2host-ikev2/description.txt +++ b/testing/tests/ipv6/host2host-ikev2/description.txt @@ -1,3 +1,5 @@ An IPv6 ESP connection between the hosts moon and sun is successfully set up. -The authentication is based on X.509 certificates. In order to test the host-to-host tunnel -moon sends an IPv6 ICMP request to sun using the ping6 command. +The authentication is based on X.509 certificates. Upon the successful establishment of +the IPsec tunnel, leftfirewall=yes automatically inserts ip6tables-based firewall +rules that let pass the tunneled traffic. In order to test both the host-to-host tunnel +and the firewall rules, moon sends an IPv6 ICMP request to sun using the ping6 command. diff --git a/testing/tests/ipv6/host2host-ikev2/hosts/moon/etc/init.d/iptables b/testing/tests/ipv6/host2host-ikev2/hosts/moon/etc/init.d/iptables new file mode 100755 index 000000000..25074a0f1 --- /dev/null +++ b/testing/tests/ipv6/host2host-ikev2/hosts/moon/etc/init.d/iptables @@ -0,0 +1,107 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow last UDP fragment + ip6tables -A INPUT -i eth0 -p udp -m frag --fraglast -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + # log dropped packets + ip6tables -A INPUT -j LOG --log-prefix " IN: " + ip6tables -A OUTPUT -j LOG --log-prefix " OUT: " + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/host2host-ikev2/hosts/moon/etc/ipsec.conf b/testing/tests/ipv6/host2host-ikev2/hosts/moon/etc/ipsec.conf index 44c85068e..ccc8037b5 100755 --- a/testing/tests/ipv6/host2host-ikev2/hosts/moon/etc/ipsec.conf +++ b/testing/tests/ipv6/host2host-ikev2/hosts/moon/etc/ipsec.conf @@ -2,6 +2,7 @@ config setup strictcrlpolicy=no + crlcheckinterval=180 plutostart=no conn %default @@ -18,12 +19,10 @@ conn net-net conn host-host left=PH_IP6_MOON - leftnexthop=0::0 leftcert=moonCert.pem leftid=@moon.strongswan.org leftfirewall=yes right=PH_IP6_SUN - rightnexthop=0::0 rightid=@sun.strongswan.org auto=add diff --git a/testing/tests/ipv6/host2host-ikev2/hosts/sun/etc/init.d/iptables b/testing/tests/ipv6/host2host-ikev2/hosts/sun/etc/init.d/iptables new file mode 100755 index 000000000..25074a0f1 --- /dev/null +++ b/testing/tests/ipv6/host2host-ikev2/hosts/sun/etc/init.d/iptables @@ -0,0 +1,107 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow last UDP fragment + ip6tables -A INPUT -i eth0 -p udp -m frag --fraglast -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + # log dropped packets + ip6tables -A INPUT -j LOG --log-prefix " IN: " + ip6tables -A OUTPUT -j LOG --log-prefix " OUT: " + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/host2host-ikev2/hosts/sun/etc/ipsec.conf b/testing/tests/ipv6/host2host-ikev2/hosts/sun/etc/ipsec.conf index 8b3858b30..1ec8b49d6 100755 --- a/testing/tests/ipv6/host2host-ikev2/hosts/sun/etc/ipsec.conf +++ b/testing/tests/ipv6/host2host-ikev2/hosts/sun/etc/ipsec.conf @@ -2,6 +2,7 @@ config setup strictcrlpolicy=no + crlcheckinterval=180 plutostart=no conn %default @@ -18,11 +19,9 @@ conn net-net conn host-host left=PH_IP6_SUN - leftnexthop=0::0 leftcert=sunCert.pem leftid=@sun.strongswan.org leftfirewall=yes right=PH_IP6_MOON - rightnexthop=0::0 rightid=@moon.strongswan.org auto=add diff --git a/testing/tests/ipv6/host2host-ikev2/posttest.dat b/testing/tests/ipv6/host2host-ikev2/posttest.dat index dff181797..5a9150bc8 100644 --- a/testing/tests/ipv6/host2host-ikev2/posttest.dat +++ b/testing/tests/ipv6/host2host-ikev2/posttest.dat @@ -1,2 +1,4 @@ moon::ipsec stop sun::ipsec stop +moon::/etc/init.d/iptables stop 2> /dev/null +sun::/etc/init.d/iptables stop 2> /dev/null diff --git a/testing/tests/ipv6/host2host-ikev2/pretest.dat b/testing/tests/ipv6/host2host-ikev2/pretest.dat index 4707af077..3536fd886 100644 --- a/testing/tests/ipv6/host2host-ikev2/pretest.dat +++ b/testing/tests/ipv6/host2host-ikev2/pretest.dat @@ -1,3 +1,5 @@ +moon::/etc/init.d/iptables start 2> /dev/null +sun::/etc/init.d/iptables start 2> /dev/null moon::ipsec start sun::ipsec start moon::sleep 2 diff --git a/testing/tests/ipv6/host2host-ikev2/test.conf b/testing/tests/ipv6/host2host-ikev2/test.conf index cf2e704fd..6ab5b8a96 100644 --- a/testing/tests/ipv6/host2host-ikev2/test.conf +++ b/testing/tests/ipv6/host2host-ikev2/test.conf @@ -9,7 +9,7 @@ UMLHOSTS="moon winnetou sun" # Corresponding block diagram # -DIAGRAM="m-w-s.png" +DIAGRAM="m-w-s-ip6.png" # UML instances on which tcpdump is to be started # diff --git a/testing/tests/ipv6/net2net-ikev1/description.txt b/testing/tests/ipv6/net2net-ikev1/description.txt new file mode 100644 index 000000000..5952ecc2d --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev1/description.txt @@ -0,0 +1,6 @@ +An IPv6 ESP tunnel connection between the gateways moon and sun is successfully set up. +It connects the two subnets hiding behind their respective gateways. The authentication is based on +X.509 certificates. Upon the successful establishment of the IPsec tunnel, leftfirewall=yes +automatically inserts ip6tables-based firewall rules that let pass the tunneled traffic. +In order to test both the net-to-net tunnel and the firewall rules, client alice behind moon +sends an IPv6 ICMP request to client bob behind sun using the ping6 command. diff --git a/testing/tests/ipv6/net2net-ikev1/evaltest.dat b/testing/tests/ipv6/net2net-ikev1/evaltest.dat new file mode 100644 index 000000000..459b0a630 --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev1/evaltest.dat @@ -0,0 +1,5 @@ +moon::ipsec status::net-net.*STATE_QUICK_I2.*IPsec SA established::YES +sun::ipsec status::net-net.*STATE_QUICK_R2.*IPsec SA established::YES +alice::ping6 -c 1 -p deadbeef ip6-bob.strongswan.org::64 bytes from ip6-bob.strongswan.org: icmp_seq=1::YES +sun::tcpdump::IP6 ip6-moon.strongswan.org > ip6-sun.strongswan.org: ESP::YES +sun::tcpdump::IP6 ip6-sun.strongswan.org > ip6-moon.strongswan.org: ESP::YES diff --git a/testing/tests/ipv6/net2net-ikev1/hosts/moon/etc/init.d/iptables b/testing/tests/ipv6/net2net-ikev1/hosts/moon/etc/init.d/iptables new file mode 100755 index 000000000..521d1ce31 --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev1/hosts/moon/etc/init.d/iptables @@ -0,0 +1,100 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/net2net-ikev1/hosts/moon/etc/ipsec.conf b/testing/tests/ipv6/net2net-ikev1/hosts/moon/etc/ipsec.conf new file mode 100755 index 000000000..84abbb07a --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev1/hosts/moon/etc/ipsec.conf @@ -0,0 +1,28 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + plutodebug=control + crlcheckinterval=180 + strictcrlpolicy=no + charonstart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + +conn net-net + also=host-host + leftsubnet=fec1::0/16 + rightsubnet=fec2::0/16 + +conn host-host + left=PH_IP6_MOON + leftcert=moonCert.pem + leftid=@moon.strongswan.org + leftfirewall=yes + right=PH_IP6_SUN + rightid=@sun.strongswan.org + auto=add + diff --git a/testing/tests/ipv6/net2net-ikev1/hosts/sun/etc/init.d/iptables b/testing/tests/ipv6/net2net-ikev1/hosts/sun/etc/init.d/iptables new file mode 100755 index 000000000..521d1ce31 --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev1/hosts/sun/etc/init.d/iptables @@ -0,0 +1,100 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/net2net-ikev1/hosts/sun/etc/ipsec.conf b/testing/tests/ipv6/net2net-ikev1/hosts/sun/etc/ipsec.conf new file mode 100755 index 000000000..4cf027ad5 --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev1/hosts/sun/etc/ipsec.conf @@ -0,0 +1,27 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + plutodebug=control + crlcheckinterval=180 + strictcrlpolicy=no + charonstart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + +conn net-net + also=host-host + leftsubnet=fec2::0/16 + rightsubnet=fec1::0/16 + +conn host-host + left=PH_IP6_SUN + leftcert=sunCert.pem + leftid=@sun.strongswan.org + leftfirewall=yes + right=PH_IP6_MOON + rightid=@moon.strongswan.org + auto=add diff --git a/testing/tests/ipv6/net2net-ikev1/posttest.dat b/testing/tests/ipv6/net2net-ikev1/posttest.dat new file mode 100644 index 000000000..4c95e2afe --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev1/posttest.dat @@ -0,0 +1,8 @@ +moon::ipsec stop +sun::ipsec stop +alice::"ip route del fec2:\:/16 via fec1:\:1" +moon::"ip route del fec2:\:/16 via fec0:\:2" +sun::"ip route del fec1:\:/16 via fec0:\:1" +bob::"ip route del fec1:\:/16 via fec2:\:1" +moon::/etc/init.d/iptables stop 2> /dev/null +sun::/etc/init.d/iptables stop 2> /dev/null diff --git a/testing/tests/ipv6/net2net-ikev1/pretest.dat b/testing/tests/ipv6/net2net-ikev1/pretest.dat new file mode 100644 index 000000000..e360bfbaa --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev1/pretest.dat @@ -0,0 +1,10 @@ +moon::/etc/init.d/iptables start 2> /dev/null +sun::/etc/init.d/iptables start 2> /dev/null +alice::"ip route add fec2:\:/16 via fec1:\:1" +moon::"ip route add fec2:\:/16 via fec0:\:2" +sun::"ip route add fec1:\:/16 via fec0:\:1" +bob::"ip route add fec1:\:/16 via fec2:\:1" +moon::ipsec start +sun::ipsec start +moon::sleep 2 +moon::ipsec up net-net diff --git a/testing/tests/ipv6/net2net-ikev1/test.conf b/testing/tests/ipv6/net2net-ikev1/test.conf new file mode 100644 index 000000000..991d884db --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev1/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="alice moon winnetou sun bob" + +# Corresponding block diagram +# +DIAGRAM="a-m-w-s-b-ip6.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="sun" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="moon sun" diff --git a/testing/tests/ipv6/net2net-ikev2/description.txt b/testing/tests/ipv6/net2net-ikev2/description.txt new file mode 100644 index 000000000..5952ecc2d --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev2/description.txt @@ -0,0 +1,6 @@ +An IPv6 ESP tunnel connection between the gateways moon and sun is successfully set up. +It connects the two subnets hiding behind their respective gateways. The authentication is based on +X.509 certificates. Upon the successful establishment of the IPsec tunnel, leftfirewall=yes +automatically inserts ip6tables-based firewall rules that let pass the tunneled traffic. +In order to test both the net-to-net tunnel and the firewall rules, client alice behind moon +sends an IPv6 ICMP request to client bob behind sun using the ping6 command. diff --git a/testing/tests/ipv6/net2net-ikev2/evaltest.dat b/testing/tests/ipv6/net2net-ikev2/evaltest.dat new file mode 100644 index 000000000..1b4e7c88a --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev2/evaltest.dat @@ -0,0 +1,5 @@ +moon::ipsec status::net-net.*INSTALLED::YES +sun::ipsec status::net.net.*INSTALLED::YES +alice::ping6 -c 1 -p deadbeef ip6-bob.strongswan.org::64 bytes from ip6-bob.strongswan.org: icmp_seq=1::YES +sun::tcpdump::IP6 ip6-moon.strongswan.org > ip6-sun.strongswan.org: ESP::YES +sun::tcpdump::IP6 ip6-sun.strongswan.org > ip6-moon.strongswan.org: ESP::YES diff --git a/testing/tests/ipv6/net2net-ikev2/hosts/moon/etc/init.d/iptables b/testing/tests/ipv6/net2net-ikev2/hosts/moon/etc/init.d/iptables new file mode 100755 index 000000000..25074a0f1 --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev2/hosts/moon/etc/init.d/iptables @@ -0,0 +1,107 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow last UDP fragment + ip6tables -A INPUT -i eth0 -p udp -m frag --fraglast -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + # log dropped packets + ip6tables -A INPUT -j LOG --log-prefix " IN: " + ip6tables -A OUTPUT -j LOG --log-prefix " OUT: " + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/net2net-ikev2/hosts/moon/etc/ipsec.conf b/testing/tests/ipv6/net2net-ikev2/hosts/moon/etc/ipsec.conf new file mode 100755 index 000000000..651e17e90 --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev2/hosts/moon/etc/ipsec.conf @@ -0,0 +1,28 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + strictcrlpolicy=no + crlcheckinterval=180 + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + mobike=no + +conn net-net + also=host-host + leftsubnet=fec1::0/16 + rightsubnet=fec2::0/16 + +conn host-host + left=PH_IP6_MOON + leftcert=moonCert.pem + leftid=@moon.strongswan.org + leftfirewall=yes + right=PH_IP6_SUN + rightid=@sun.strongswan.org + auto=add diff --git a/testing/tests/ipv6/net2net-ikev2/hosts/sun/etc/init.d/iptables b/testing/tests/ipv6/net2net-ikev2/hosts/sun/etc/init.d/iptables new file mode 100755 index 000000000..25074a0f1 --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev2/hosts/sun/etc/init.d/iptables @@ -0,0 +1,107 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow last UDP fragment + ip6tables -A INPUT -i eth0 -p udp -m frag --fraglast -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + # log dropped packets + ip6tables -A INPUT -j LOG --log-prefix " IN: " + ip6tables -A OUTPUT -j LOG --log-prefix " OUT: " + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/net2net-ikev2/hosts/sun/etc/ipsec.conf b/testing/tests/ipv6/net2net-ikev2/hosts/sun/etc/ipsec.conf new file mode 100755 index 000000000..4ba0bcbc0 --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev2/hosts/sun/etc/ipsec.conf @@ -0,0 +1,28 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + strictcrlpolicy=no + crlcheckinterval=180 + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + mobike=no + +conn net-net + also=host-host + leftsubnet=fec2::0/16 + rightsubnet=fec1::0/16 + +conn host-host + left=PH_IP6_SUN + leftcert=sunCert.pem + leftid=@sun.strongswan.org + leftfirewall=yes + right=PH_IP6_MOON + rightid=@moon.strongswan.org + auto=add diff --git a/testing/tests/ipv6/net2net-ikev2/posttest.dat b/testing/tests/ipv6/net2net-ikev2/posttest.dat new file mode 100644 index 000000000..4c95e2afe --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev2/posttest.dat @@ -0,0 +1,8 @@ +moon::ipsec stop +sun::ipsec stop +alice::"ip route del fec2:\:/16 via fec1:\:1" +moon::"ip route del fec2:\:/16 via fec0:\:2" +sun::"ip route del fec1:\:/16 via fec0:\:1" +bob::"ip route del fec1:\:/16 via fec2:\:1" +moon::/etc/init.d/iptables stop 2> /dev/null +sun::/etc/init.d/iptables stop 2> /dev/null diff --git a/testing/tests/ipv6/net2net-ikev2/pretest.dat b/testing/tests/ipv6/net2net-ikev2/pretest.dat new file mode 100644 index 000000000..e360bfbaa --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev2/pretest.dat @@ -0,0 +1,10 @@ +moon::/etc/init.d/iptables start 2> /dev/null +sun::/etc/init.d/iptables start 2> /dev/null +alice::"ip route add fec2:\:/16 via fec1:\:1" +moon::"ip route add fec2:\:/16 via fec0:\:2" +sun::"ip route add fec1:\:/16 via fec0:\:1" +bob::"ip route add fec1:\:/16 via fec2:\:1" +moon::ipsec start +sun::ipsec start +moon::sleep 2 +moon::ipsec up net-net diff --git a/testing/tests/ipv6/net2net-ikev2/test.conf b/testing/tests/ipv6/net2net-ikev2/test.conf new file mode 100644 index 000000000..991d884db --- /dev/null +++ b/testing/tests/ipv6/net2net-ikev2/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="alice moon winnetou sun bob" + +# Corresponding block diagram +# +DIAGRAM="a-m-w-s-b-ip6.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="sun" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="moon sun" diff --git a/testing/tests/ipv6/rw-ikev1/description.txt b/testing/tests/ipv6/rw-ikev1/description.txt new file mode 100644 index 000000000..046c4b50c --- /dev/null +++ b/testing/tests/ipv6/rw-ikev1/description.txt @@ -0,0 +1,7 @@ +The roadwarrior carol sets up a connection to gateway moon. +The authentication is based on X.509 certificates. Upon the successful +establishment of the IPsec tunnel, leftfirewall=yes automatically inserts +ip6tables-based firewall rules that let pass the tunneled traffic. +In order to test both the IPv6 ESP tunnel and the firewall rules, carol +sends an IPv6 ICMP request to the client alice behind the gateway moon +using the ping6 command. diff --git a/testing/tests/ipv6/rw-ikev1/evaltest.dat b/testing/tests/ipv6/rw-ikev1/evaltest.dat new file mode 100644 index 000000000..894e9118e --- /dev/null +++ b/testing/tests/ipv6/rw-ikev1/evaltest.dat @@ -0,0 +1,5 @@ +carol::ipsec status::home.*STATE_QUICK_I2.*IPsec SA established::YES +moon::ipsec status::rw.*STATE_QUICK_R2.*IPsec SA established::YES +carol::ping6 -c 1 ip6-alice.strongswan.org::64 bytes from ip6-alice.strongswan.org: icmp_seq=1::YES +moon::tcpdump::IP6 ip6-carol.strongswan.org > ip6-moon.strongswan.org: ESP::YES +moon::tcpdump::IP6 ip6-moon.strongswan.org > ip6-carol.strongswan.org: ESP::YES diff --git a/testing/tests/ipv6/rw-ikev1/hosts/carol/etc/init.d/iptables b/testing/tests/ipv6/rw-ikev1/hosts/carol/etc/init.d/iptables new file mode 100755 index 000000000..521d1ce31 --- /dev/null +++ b/testing/tests/ipv6/rw-ikev1/hosts/carol/etc/init.d/iptables @@ -0,0 +1,100 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/rw-ikev1/hosts/carol/etc/ipsec.conf b/testing/tests/ipv6/rw-ikev1/hosts/carol/etc/ipsec.conf new file mode 100755 index 000000000..b27609917 --- /dev/null +++ b/testing/tests/ipv6/rw-ikev1/hosts/carol/etc/ipsec.conf @@ -0,0 +1,27 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + plutodebug=control + crlcheckinterval=180 + strictcrlpolicy=no + charonstart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + +conn home + left=PH_IP6_CAROL + leftcert=carolCert.pem + leftid=carol@strongswan.org + leftfirewall=yes + right=PH_IP6_MOON + rightsubnet=fec1::/16 + rightid=@moon.strongswan.org + auto=add + + + + diff --git a/testing/tests/ipv6/rw-ikev1/hosts/moon/etc/init.d/iptables b/testing/tests/ipv6/rw-ikev1/hosts/moon/etc/init.d/iptables new file mode 100755 index 000000000..521d1ce31 --- /dev/null +++ b/testing/tests/ipv6/rw-ikev1/hosts/moon/etc/init.d/iptables @@ -0,0 +1,100 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/rw-ikev1/hosts/moon/etc/ipsec.conf b/testing/tests/ipv6/rw-ikev1/hosts/moon/etc/ipsec.conf new file mode 100755 index 000000000..0129ef744 --- /dev/null +++ b/testing/tests/ipv6/rw-ikev1/hosts/moon/etc/ipsec.conf @@ -0,0 +1,22 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + plutodebug=control + crlcheckinterval=180 + strictcrlpolicy=no + charonstart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + +conn rw + left=PH_IP6_MOON + leftcert=moonCert.pem + leftid=@moon.strongswan.org + leftsubnet=fec1::/16 + leftfirewall=yes + right=%any6 + auto=add diff --git a/testing/tests/ipv6/rw-ikev1/posttest.dat b/testing/tests/ipv6/rw-ikev1/posttest.dat new file mode 100644 index 000000000..d37b96f9c --- /dev/null +++ b/testing/tests/ipv6/rw-ikev1/posttest.dat @@ -0,0 +1,6 @@ +moon::ipsec stop +carol::ipsec stop +alice::"ip route del fec0:\:/16 via fec1:\:1" +carol::"ip route del fec1:\:/16 via fec0:\:1" +moon::/etc/init.d/iptables stop 2> /dev/null +carol::/etc/init.d/iptables stop 2> /dev/null diff --git a/testing/tests/ipv6/rw-ikev1/pretest.dat b/testing/tests/ipv6/rw-ikev1/pretest.dat new file mode 100644 index 000000000..2b3bf90a7 --- /dev/null +++ b/testing/tests/ipv6/rw-ikev1/pretest.dat @@ -0,0 +1,8 @@ +moon::/etc/init.d/iptables start 2> /dev/null +carol::/etc/init.d/iptables start 2> /dev/null +alice::"ip route add fec0:\:/16 via fec1:\:1" +carol::"ip route add fec1:\:/16 via fec0:\:1" +carol::ipsec start +moon::ipsec start +carol::sleep 2 +carol::ipsec up home diff --git a/testing/tests/ipv6/rw-ikev1/test.conf b/testing/tests/ipv6/rw-ikev1/test.conf new file mode 100644 index 000000000..bce9814db --- /dev/null +++ b/testing/tests/ipv6/rw-ikev1/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="alice moon carol winnetou" + +# Corresponding block diagram +# +DIAGRAM="a-m-c-w-ip6.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="moon" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="moon carol" diff --git a/testing/tests/ipv6/rw-ikev2/description.txt b/testing/tests/ipv6/rw-ikev2/description.txt new file mode 100644 index 000000000..17461370e --- /dev/null +++ b/testing/tests/ipv6/rw-ikev2/description.txt @@ -0,0 +1,7 @@ +The roadwarriors carol and dave set up an IPv6 connection each +to gateway moon. The authentication is based on X.509 certificates. +Upon the successful establishment of the IPv6 ESP tunnels, leftfirewall=yes +automatically inserts ip6tables-based firewall rules that let pass the tunneled traffic. +In order to test both tunnel and firewall, both carol and dave send +an IPv6 ICMP request to the client alice behind the gateway moon +using the ping6 command. diff --git a/testing/tests/ipv6/rw-ikev2/evaltest.dat b/testing/tests/ipv6/rw-ikev2/evaltest.dat new file mode 100644 index 000000000..cee1853c4 --- /dev/null +++ b/testing/tests/ipv6/rw-ikev2/evaltest.dat @@ -0,0 +1,10 @@ +moon::ipsec statusall::rw.*ESTABLISHED::YES +carol::ipsec statusall::home.*ESTABLISHED::YES +dave::ipsec statusall::home.*ESTABLISHED::YES +carol::ping6 -c 1 ip6-alice.strongswan.org::64 bytes from ip6-alice.strongswan.org: icmp_seq=1::YES +dave::ping6 -c 1 ip6-alice.strongswan.org::64 bytes from ip6-alice.strongswan.org: icmp_seq=1::YES +moon::tcpdump::IP6 ip6-carol.strongswan.org > ip6-moon.strongswan.org: ESP::YES +moon::tcpdump::IP6 ip6-moon.strongswan.org > ip6-carol.strongswan.org: ESP::YES +moon::tcpdump::IP6 ip6-dave.strongswan.org > ip6-moon.strongswan.org: ESP::YES +moon::tcpdump::IP6 ip6-moon.strongswan.org > ip6-dave.strongswan.org: ESP::YES + diff --git a/testing/tests/ipv6/rw-ikev2/hosts/carol/etc/init.d/iptables b/testing/tests/ipv6/rw-ikev2/hosts/carol/etc/init.d/iptables new file mode 100755 index 000000000..25074a0f1 --- /dev/null +++ b/testing/tests/ipv6/rw-ikev2/hosts/carol/etc/init.d/iptables @@ -0,0 +1,107 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow last UDP fragment + ip6tables -A INPUT -i eth0 -p udp -m frag --fraglast -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + # log dropped packets + ip6tables -A INPUT -j LOG --log-prefix " IN: " + ip6tables -A OUTPUT -j LOG --log-prefix " OUT: " + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/rw-ikev2/hosts/carol/etc/ipsec.conf b/testing/tests/ipv6/rw-ikev2/hosts/carol/etc/ipsec.conf new file mode 100755 index 000000000..92388586a --- /dev/null +++ b/testing/tests/ipv6/rw-ikev2/hosts/carol/etc/ipsec.conf @@ -0,0 +1,23 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + +conn home + left=PH_IP6_CAROL + leftcert=carolCert.pem + leftid=carol@strongswan.org + leftfirewall=yes + right=PH_IP6_MOON + rightid=@moon.strongswan.org + rightsubnet=fec1::/16 + keyexchange=ikev2 + auto=add diff --git a/testing/tests/ipv6/rw-ikev2/hosts/dave/etc/init.d/iptables b/testing/tests/ipv6/rw-ikev2/hosts/dave/etc/init.d/iptables new file mode 100755 index 000000000..25074a0f1 --- /dev/null +++ b/testing/tests/ipv6/rw-ikev2/hosts/dave/etc/init.d/iptables @@ -0,0 +1,107 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow last UDP fragment + ip6tables -A INPUT -i eth0 -p udp -m frag --fraglast -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + # log dropped packets + ip6tables -A INPUT -j LOG --log-prefix " IN: " + ip6tables -A OUTPUT -j LOG --log-prefix " OUT: " + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/rw-ikev2/hosts/dave/etc/ipsec.conf b/testing/tests/ipv6/rw-ikev2/hosts/dave/etc/ipsec.conf new file mode 100755 index 000000000..ed1eb39ca --- /dev/null +++ b/testing/tests/ipv6/rw-ikev2/hosts/dave/etc/ipsec.conf @@ -0,0 +1,23 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + +conn home + left=PH_IP6_DAVE + leftcert=daveCert.pem + leftid=dave@strongswan.org + leftfirewall=yes + right=PH_IP6_MOON + rightid=@moon.strongswan.org + rightsubnet=fec1::/16 + keyexchange=ikev2 + auto=add diff --git a/testing/tests/ipv6/rw-ikev2/hosts/moon/etc/init.d/iptables b/testing/tests/ipv6/rw-ikev2/hosts/moon/etc/init.d/iptables new file mode 100755 index 000000000..25074a0f1 --- /dev/null +++ b/testing/tests/ipv6/rw-ikev2/hosts/moon/etc/init.d/iptables @@ -0,0 +1,107 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow last UDP fragment + ip6tables -A INPUT -i eth0 -p udp -m frag --fraglast -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + # log dropped packets + ip6tables -A INPUT -j LOG --log-prefix " IN: " + ip6tables -A OUTPUT -j LOG --log-prefix " OUT: " + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/rw-ikev2/hosts/moon/etc/ipsec.conf b/testing/tests/ipv6/rw-ikev2/hosts/moon/etc/ipsec.conf new file mode 100755 index 000000000..f78ba45e0 --- /dev/null +++ b/testing/tests/ipv6/rw-ikev2/hosts/moon/etc/ipsec.conf @@ -0,0 +1,22 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + +conn rw + left=PH_IP6_MOON + leftcert=moonCert.pem + leftid=@moon.strongswan.org + leftsubnet=fec1::/16 + leftfirewall=yes + right=%any + keyexchange=ikev2 + auto=add diff --git a/testing/tests/ipv6/rw-ikev2/posttest.dat b/testing/tests/ipv6/rw-ikev2/posttest.dat new file mode 100644 index 000000000..07e89d7da --- /dev/null +++ b/testing/tests/ipv6/rw-ikev2/posttest.dat @@ -0,0 +1,9 @@ +moon::ipsec stop +carol::ipsec stop +dave::ipsec stop +moon::/etc/init.d/iptables stop 2> /dev/null +carol::/etc/init.d/iptables stop 2> /dev/null +dave::/etc/init.d/iptables stop 2> /dev/null +alice::"ip route del fec0:\:/16 via fec1:\:1" +carol::"ip route del fec1:\:/16 via fec0:\:1" +dave::"ip route del fec1:\:/16 via fec0:\:1" diff --git a/testing/tests/ipv6/rw-ikev2/pretest.dat b/testing/tests/ipv6/rw-ikev2/pretest.dat new file mode 100644 index 000000000..dea60a040 --- /dev/null +++ b/testing/tests/ipv6/rw-ikev2/pretest.dat @@ -0,0 +1,12 @@ +moon::/etc/init.d/iptables start 2> /dev/null +carol::/etc/init.d/iptables start 2> /dev/null +dave::/etc/init.d/iptables start 2> /dev/null +alice::"ip route add fec0:\:/16 via fec1:\:1" +carol::"ip route add fec1:\:/16 via fec0:\:1" +dave::"ip route add fec1:\:/16 via fec0:\:1" +moon::ipsec start +carol::ipsec start +dave::ipsec start +carol::sleep 1 +carol::ipsec up home +dave::ipsec up home diff --git a/testing/tests/ipv6/rw-ikev2/test.conf b/testing/tests/ipv6/rw-ikev2/test.conf new file mode 100644 index 000000000..80cf5e3a1 --- /dev/null +++ b/testing/tests/ipv6/rw-ikev2/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="alice moon carol winnetou dave" + +# Corresponding block diagram +# +DIAGRAM="a-m-c-w-d-ip6.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="moon" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="moon carol dave" diff --git a/testing/tests/ipv6/rw-psk-ikev1/description.txt b/testing/tests/ipv6/rw-psk-ikev1/description.txt new file mode 100644 index 000000000..81072ebf6 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev1/description.txt @@ -0,0 +1,5 @@ +The roadwarrior carol sets up an IPv6 tunnel connection to gateway moon. +The authentication is based on Preshared Keys (PSK) and IPv6 addresses (ID_IPV6_ADDR). +firewall=yes automatically inserts ip6tables-based firewall rules that let pass +the tunneled traffic. In order to test the tunnel carol sends an IPv6 +ICMP request to client alice behind the gateway moon using the ping6 command. diff --git a/testing/tests/ipv6/rw-psk-ikev1/evaltest.dat b/testing/tests/ipv6/rw-psk-ikev1/evaltest.dat new file mode 100644 index 000000000..4046d0bbc --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev1/evaltest.dat @@ -0,0 +1,5 @@ +carol::ipsec status::home.*STATE_QUICK_I2.*IPsec SA established::YES +moon::ipsec status::rw.*STATE_QUICK_R2.*IPsec SA established::YES +carol::ping6 -c 1 ip6-alice.strongswan.org::64 bytes from ip6-alice.strongswan.org: icmp_seq=1::YES +moon::tcpdump::IP6 ip6-carol.strongswan.org > ip6-moon.strongswan.org: ESP::YES +moon::tcpdump::IP6 ip6-moon.strongswan.org > ip6-carol.strongswan.org: ESP::YES diff --git a/testing/tests/ipv6/rw-psk-ikev1/hosts/carol/etc/init.d/iptables b/testing/tests/ipv6/rw-psk-ikev1/hosts/carol/etc/init.d/iptables new file mode 100755 index 000000000..521d1ce31 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev1/hosts/carol/etc/init.d/iptables @@ -0,0 +1,100 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/rw-psk-ikev1/hosts/carol/etc/ipsec.conf b/testing/tests/ipv6/rw-psk-ikev1/hosts/carol/etc/ipsec.conf new file mode 100755 index 000000000..5d77c2dd5 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev1/hosts/carol/etc/ipsec.conf @@ -0,0 +1,19 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + plutodebug=control + charonstart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + authby=secret + +conn home + left=PH_IP6_CAROL + leftfirewall=yes + right=PH_IP6_MOON + rightsubnet=fec1::/16 + auto=add diff --git a/testing/tests/ipv6/rw-psk-ikev1/hosts/carol/etc/ipsec.secrets b/testing/tests/ipv6/rw-psk-ikev1/hosts/carol/etc/ipsec.secrets new file mode 100644 index 000000000..42c84fc49 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev1/hosts/carol/etc/ipsec.secrets @@ -0,0 +1,3 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +PH_IP6_CAROL PH_IP6_MOON : PSK 0sv+NkxY9LLZvwj4qCC2o/gGrWDF2d21jL diff --git a/testing/tests/ipv6/rw-psk-ikev1/hosts/moon/etc/init.d/iptables b/testing/tests/ipv6/rw-psk-ikev1/hosts/moon/etc/init.d/iptables new file mode 100755 index 000000000..521d1ce31 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev1/hosts/moon/etc/init.d/iptables @@ -0,0 +1,100 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/rw-psk-ikev1/hosts/moon/etc/ipsec.conf b/testing/tests/ipv6/rw-psk-ikev1/hosts/moon/etc/ipsec.conf new file mode 100755 index 000000000..78f674026 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev1/hosts/moon/etc/ipsec.conf @@ -0,0 +1,19 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + plutodebug=control + charonstart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + authby=secret + +conn rw + left=PH_IP6_MOON + leftsubnet=fec1::/16 + leftfirewall=yes + right=%any6 + auto=add diff --git a/testing/tests/ipv6/rw-psk-ikev1/hosts/moon/etc/ipsec.secrets b/testing/tests/ipv6/rw-psk-ikev1/hosts/moon/etc/ipsec.secrets new file mode 100644 index 000000000..ac738c1aa --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev1/hosts/moon/etc/ipsec.secrets @@ -0,0 +1,3 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +PH_IP6_MOON %any6 : PSK 0sv+NkxY9LLZvwj4qCC2o/gGrWDF2d21jL diff --git a/testing/tests/ipv6/rw-psk-ikev1/posttest.dat b/testing/tests/ipv6/rw-psk-ikev1/posttest.dat new file mode 100644 index 000000000..d37b96f9c --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev1/posttest.dat @@ -0,0 +1,6 @@ +moon::ipsec stop +carol::ipsec stop +alice::"ip route del fec0:\:/16 via fec1:\:1" +carol::"ip route del fec1:\:/16 via fec0:\:1" +moon::/etc/init.d/iptables stop 2> /dev/null +carol::/etc/init.d/iptables stop 2> /dev/null diff --git a/testing/tests/ipv6/rw-psk-ikev1/pretest.dat b/testing/tests/ipv6/rw-psk-ikev1/pretest.dat new file mode 100644 index 000000000..6fbbccaae --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev1/pretest.dat @@ -0,0 +1,10 @@ +moon::/etc/init.d/iptables start 2> /dev/null +carol::/etc/init.d/iptables start 2> /dev/null +alice::"ip route add fec0:\:/16 via fec1:\:1" +carol::"ip route add fec1:\:/16 via fec0:\:1" +moon::rm /etc/ipsec.d/cacerts/* +carol::rm /etc/ipsec.d/cacerts/* +carol::ipsec start +moon::ipsec start +carol::sleep 2 +carol::ipsec up home diff --git a/testing/tests/ipv6/rw-psk-ikev1/test.conf b/testing/tests/ipv6/rw-psk-ikev1/test.conf new file mode 100644 index 000000000..bce9814db --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev1/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="alice moon carol winnetou" + +# Corresponding block diagram +# +DIAGRAM="a-m-c-w-ip6.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="moon" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="moon carol" diff --git a/testing/tests/ipv6/rw-psk-ikev2/description.txt b/testing/tests/ipv6/rw-psk-ikev2/description.txt new file mode 100644 index 000000000..66fc09053 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/description.txt @@ -0,0 +1,7 @@ +The roadwarriors carol and dave set up an IPv6 tunnel connection each +to gateway moon. The authentication is based on distinct pre-shared keys +and IPv6 addresses. Upon the successful establishment of the IPsec tunnels, +leftfirewall=yes automatically inserts ip6tables-based firewall rules that +let pass the tunneled traffic. In order to test both tunnel and firewall, both +carol and dave send an IPv6 ICMP request to client alice +behind the gateway moon using the ping6 command. diff --git a/testing/tests/ipv6/rw-psk-ikev2/evaltest.dat b/testing/tests/ipv6/rw-psk-ikev2/evaltest.dat new file mode 100644 index 000000000..cee1853c4 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/evaltest.dat @@ -0,0 +1,10 @@ +moon::ipsec statusall::rw.*ESTABLISHED::YES +carol::ipsec statusall::home.*ESTABLISHED::YES +dave::ipsec statusall::home.*ESTABLISHED::YES +carol::ping6 -c 1 ip6-alice.strongswan.org::64 bytes from ip6-alice.strongswan.org: icmp_seq=1::YES +dave::ping6 -c 1 ip6-alice.strongswan.org::64 bytes from ip6-alice.strongswan.org: icmp_seq=1::YES +moon::tcpdump::IP6 ip6-carol.strongswan.org > ip6-moon.strongswan.org: ESP::YES +moon::tcpdump::IP6 ip6-moon.strongswan.org > ip6-carol.strongswan.org: ESP::YES +moon::tcpdump::IP6 ip6-dave.strongswan.org > ip6-moon.strongswan.org: ESP::YES +moon::tcpdump::IP6 ip6-moon.strongswan.org > ip6-dave.strongswan.org: ESP::YES + diff --git a/testing/tests/ipv6/rw-psk-ikev2/hosts/carol/etc/init.d/iptables b/testing/tests/ipv6/rw-psk-ikev2/hosts/carol/etc/init.d/iptables new file mode 100755 index 000000000..25074a0f1 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/hosts/carol/etc/init.d/iptables @@ -0,0 +1,107 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow last UDP fragment + ip6tables -A INPUT -i eth0 -p udp -m frag --fraglast -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + # log dropped packets + ip6tables -A INPUT -j LOG --log-prefix " IN: " + ip6tables -A OUTPUT -j LOG --log-prefix " OUT: " + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/rw-psk-ikev2/hosts/carol/etc/ipsec.conf b/testing/tests/ipv6/rw-psk-ikev2/hosts/carol/etc/ipsec.conf new file mode 100755 index 000000000..b656b9ec7 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/hosts/carol/etc/ipsec.conf @@ -0,0 +1,19 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + authby=secret + +conn home + left=PH_IP6_CAROL + leftfirewall=yes + right=PH_IP6_MOON + rightsubnet=fec1::/16 + auto=add diff --git a/testing/tests/ipv6/rw-psk-ikev2/hosts/carol/etc/ipsec.secrets b/testing/tests/ipv6/rw-psk-ikev2/hosts/carol/etc/ipsec.secrets new file mode 100644 index 000000000..2abcb4e0a --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/hosts/carol/etc/ipsec.secrets @@ -0,0 +1,3 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +PH_IP6_CAROL : PSK 0sFpZAZqEN6Ti9sqt4ZP5EWcqx diff --git a/testing/tests/ipv6/rw-psk-ikev2/hosts/dave/etc/init.d/iptables b/testing/tests/ipv6/rw-psk-ikev2/hosts/dave/etc/init.d/iptables new file mode 100755 index 000000000..25074a0f1 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/hosts/dave/etc/init.d/iptables @@ -0,0 +1,107 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow last UDP fragment + ip6tables -A INPUT -i eth0 -p udp -m frag --fraglast -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + # log dropped packets + ip6tables -A INPUT -j LOG --log-prefix " IN: " + ip6tables -A OUTPUT -j LOG --log-prefix " OUT: " + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/rw-psk-ikev2/hosts/dave/etc/ipsec.conf b/testing/tests/ipv6/rw-psk-ikev2/hosts/dave/etc/ipsec.conf new file mode 100755 index 000000000..c62f4ff07 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/hosts/dave/etc/ipsec.conf @@ -0,0 +1,20 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + authby=secret + +conn home + left=PH_IP6_DAVE + leftfirewall=yes + right=PH_IP6_MOON + rightsubnet=fec1::/16 + auto=add diff --git a/testing/tests/ipv6/rw-psk-ikev2/hosts/dave/etc/ipsec.secrets b/testing/tests/ipv6/rw-psk-ikev2/hosts/dave/etc/ipsec.secrets new file mode 100644 index 000000000..2375cd559 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/hosts/dave/etc/ipsec.secrets @@ -0,0 +1,3 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +PH_IP6_DAVE : PSK 0sjVzONCF02ncsgiSlmIXeqhGN diff --git a/testing/tests/ipv6/rw-psk-ikev2/hosts/moon/etc/init.d/iptables b/testing/tests/ipv6/rw-psk-ikev2/hosts/moon/etc/init.d/iptables new file mode 100755 index 000000000..25074a0f1 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/hosts/moon/etc/init.d/iptables @@ -0,0 +1,107 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow last UDP fragment + ip6tables -A INPUT -i eth0 -p udp -m frag --fraglast -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + # log dropped packets + ip6tables -A INPUT -j LOG --log-prefix " IN: " + ip6tables -A OUTPUT -j LOG --log-prefix " OUT: " + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/rw-psk-ikev2/hosts/moon/etc/ipsec.conf b/testing/tests/ipv6/rw-psk-ikev2/hosts/moon/etc/ipsec.conf new file mode 100755 index 000000000..0cf988768 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/hosts/moon/etc/ipsec.conf @@ -0,0 +1,19 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + authby=secret + +conn rw + left=PH_IP6_MOON + leftsubnet=fec1::/16 + leftfirewall=yes + right=%any + auto=add diff --git a/testing/tests/ipv6/rw-psk-ikev2/hosts/moon/etc/ipsec.secrets b/testing/tests/ipv6/rw-psk-ikev2/hosts/moon/etc/ipsec.secrets new file mode 100644 index 000000000..88c418353 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/hosts/moon/etc/ipsec.secrets @@ -0,0 +1,5 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +PH_IP6_CAROL : PSK 0sFpZAZqEN6Ti9sqt4ZP5EWcqx + +PH_IP6_DAVE : PSK 0sjVzONCF02ncsgiSlmIXeqhGN diff --git a/testing/tests/ipv6/rw-psk-ikev2/posttest.dat b/testing/tests/ipv6/rw-psk-ikev2/posttest.dat new file mode 100644 index 000000000..07e89d7da --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/posttest.dat @@ -0,0 +1,9 @@ +moon::ipsec stop +carol::ipsec stop +dave::ipsec stop +moon::/etc/init.d/iptables stop 2> /dev/null +carol::/etc/init.d/iptables stop 2> /dev/null +dave::/etc/init.d/iptables stop 2> /dev/null +alice::"ip route del fec0:\:/16 via fec1:\:1" +carol::"ip route del fec1:\:/16 via fec0:\:1" +dave::"ip route del fec1:\:/16 via fec0:\:1" diff --git a/testing/tests/ipv6/rw-psk-ikev2/pretest.dat b/testing/tests/ipv6/rw-psk-ikev2/pretest.dat new file mode 100644 index 000000000..07b0ebd7d --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/pretest.dat @@ -0,0 +1,15 @@ +moon::/etc/init.d/iptables start 2> /dev/null +carol::/etc/init.d/iptables start 2> /dev/null +dave::/etc/init.d/iptables start 2> /dev/null +alice::"ip route add fec0:\:/16 via fec1:\:1" +carol::"ip route add fec1:\:/16 via fec0:\:1" +dave::"ip route add fec1:\:/16 via fec0:\:1" +moon::rm /etc/ipsec.d/cacerts/* +carol::rm /etc/ipsec.d/cacerts/* +dave::rm /etc/ipsec.d/cacerts/* +moon::ipsec start +carol::ipsec start +dave::ipsec start +carol::sleep 1 +carol::ipsec up home +dave::ipsec up home diff --git a/testing/tests/ipv6/rw-psk-ikev2/test.conf b/testing/tests/ipv6/rw-psk-ikev2/test.conf new file mode 100644 index 000000000..80cf5e3a1 --- /dev/null +++ b/testing/tests/ipv6/rw-psk-ikev2/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="alice moon carol winnetou dave" + +# Corresponding block diagram +# +DIAGRAM="a-m-c-w-d-ip6.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="moon" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="moon carol dave" diff --git a/testing/tests/ipv6/transport-ikev1/description.txt b/testing/tests/ipv6/transport-ikev1/description.txt new file mode 100644 index 000000000..2d54790aa --- /dev/null +++ b/testing/tests/ipv6/transport-ikev1/description.txt @@ -0,0 +1,5 @@ +An IPv6 ESP transport connection between the hosts moon and sun is successfully set up. +The authentication is based on X.509 certificates. Upon the successful establishment of +the IPsec SA, leftfirewall=yes automatically inserts ip6tables-based firewall +rules that let pass the protected traffic. In order to test both the transport connection +and the firewall rules, moon sends an IPv6 ICMP request to sun using the ping6 command. diff --git a/testing/tests/ipv6/transport-ikev1/evaltest.dat b/testing/tests/ipv6/transport-ikev1/evaltest.dat new file mode 100644 index 000000000..2010557c1 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev1/evaltest.dat @@ -0,0 +1,7 @@ +moon::ipsec status::host-host.*STATE_QUICK_I2.*IPsec SA established::YES +sun::ipsec status::host-host.*STATE_QUICK_R2.*IPsec SA established::YES +moon::ip xfrm state::mode transport::YES +sun::ip xfrm state::mode transport::YES +moon::ping6 -c 1 -p deadbeef ip6-sun.strongswan.org::64 bytes from ip6-sun.strongswan.org: icmp_seq=1::YES +sun::tcpdump::IP6 ip6-moon.strongswan.org > ip6-sun.strongswan.org: ESP::YES +sun::tcpdump::IP6 ip6-sun.strongswan.org > ip6-moon.strongswan.org: ESP::YES diff --git a/testing/tests/ipv6/transport-ikev1/hosts/moon/etc/init.d/iptables b/testing/tests/ipv6/transport-ikev1/hosts/moon/etc/init.d/iptables new file mode 100755 index 000000000..521d1ce31 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev1/hosts/moon/etc/init.d/iptables @@ -0,0 +1,100 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/transport-ikev1/hosts/moon/etc/ipsec.conf b/testing/tests/ipv6/transport-ikev1/hosts/moon/etc/ipsec.conf new file mode 100755 index 000000000..8bc0deba8 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev1/hosts/moon/etc/ipsec.conf @@ -0,0 +1,23 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + plutodebug=control + crlcheckinterval=180 + strictcrlpolicy=no + charonstart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + +conn host-host + left=PH_IP6_MOON + leftcert=moonCert.pem + leftid=@moon.strongswan.org + leftfirewall=yes + right=PH_IP6_SUN + rightid=@sun.strongswan.org + type=transport + auto=add diff --git a/testing/tests/ipv6/transport-ikev1/hosts/sun/etc/init.d/iptables b/testing/tests/ipv6/transport-ikev1/hosts/sun/etc/init.d/iptables new file mode 100755 index 000000000..521d1ce31 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev1/hosts/sun/etc/init.d/iptables @@ -0,0 +1,100 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/transport-ikev1/hosts/sun/etc/ipsec.conf b/testing/tests/ipv6/transport-ikev1/hosts/sun/etc/ipsec.conf new file mode 100755 index 000000000..b68082dd9 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev1/hosts/sun/etc/ipsec.conf @@ -0,0 +1,23 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + plutodebug=control + crlcheckinterval=180 + strictcrlpolicy=no + charonstart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + +conn host-host + left=PH_IP6_SUN + leftcert=sunCert.pem + leftid=@sun.strongswan.org + leftfirewall=yes + right=PH_IP6_MOON + rightid=@moon.strongswan.org + type=transport + auto=add diff --git a/testing/tests/ipv6/transport-ikev1/posttest.dat b/testing/tests/ipv6/transport-ikev1/posttest.dat new file mode 100644 index 000000000..5a9150bc8 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev1/posttest.dat @@ -0,0 +1,4 @@ +moon::ipsec stop +sun::ipsec stop +moon::/etc/init.d/iptables stop 2> /dev/null +sun::/etc/init.d/iptables stop 2> /dev/null diff --git a/testing/tests/ipv6/transport-ikev1/pretest.dat b/testing/tests/ipv6/transport-ikev1/pretest.dat new file mode 100644 index 000000000..3536fd886 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev1/pretest.dat @@ -0,0 +1,6 @@ +moon::/etc/init.d/iptables start 2> /dev/null +sun::/etc/init.d/iptables start 2> /dev/null +moon::ipsec start +sun::ipsec start +moon::sleep 2 +moon::ipsec up host-host diff --git a/testing/tests/ipv6/transport-ikev1/test.conf b/testing/tests/ipv6/transport-ikev1/test.conf new file mode 100644 index 000000000..6ab5b8a96 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev1/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="moon winnetou sun" + +# Corresponding block diagram +# +DIAGRAM="m-w-s-ip6.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="sun" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="moon sun" diff --git a/testing/tests/ipv6/transport-ikev2/description.txt b/testing/tests/ipv6/transport-ikev2/description.txt new file mode 100644 index 000000000..2d54790aa --- /dev/null +++ b/testing/tests/ipv6/transport-ikev2/description.txt @@ -0,0 +1,5 @@ +An IPv6 ESP transport connection between the hosts moon and sun is successfully set up. +The authentication is based on X.509 certificates. Upon the successful establishment of +the IPsec SA, leftfirewall=yes automatically inserts ip6tables-based firewall +rules that let pass the protected traffic. In order to test both the transport connection +and the firewall rules, moon sends an IPv6 ICMP request to sun using the ping6 command. diff --git a/testing/tests/ipv6/transport-ikev2/evaltest.dat b/testing/tests/ipv6/transport-ikev2/evaltest.dat new file mode 100644 index 000000000..1ea5bcebe --- /dev/null +++ b/testing/tests/ipv6/transport-ikev2/evaltest.dat @@ -0,0 +1,8 @@ +moon::cat /var/log/daemon.log::received USE_TRANSPORT_MODE notify::YES +moon::ipsec status::host-host.*INSTALLED.*TRANSPORT::YES +sun::ipsec status::host-host.*INSTALLED.*TRANSPORT::YES +moon::ip xfrm state::mode transport::YES +sun::ip xfrm state::mode transport::YES +moon::ping6 -c 1 -p deadbeef ip6-sun.strongswan.org::64 bytes from ip6-sun.strongswan.org: icmp_seq=1::YES +sun::tcpdump::IP6 ip6-moon.strongswan.org > ip6-sun.strongswan.org: ESP::YES +sun::tcpdump::IP6 ip6-sun.strongswan.org > ip6-moon.strongswan.org: ESP::YES diff --git a/testing/tests/ipv6/transport-ikev2/hosts/moon/etc/init.d/iptables b/testing/tests/ipv6/transport-ikev2/hosts/moon/etc/init.d/iptables new file mode 100755 index 000000000..25074a0f1 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev2/hosts/moon/etc/init.d/iptables @@ -0,0 +1,107 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow last UDP fragment + ip6tables -A INPUT -i eth0 -p udp -m frag --fraglast -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + # log dropped packets + ip6tables -A INPUT -j LOG --log-prefix " IN: " + ip6tables -A OUTPUT -j LOG --log-prefix " OUT: " + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/transport-ikev2/hosts/moon/etc/ipsec.conf b/testing/tests/ipv6/transport-ikev2/hosts/moon/etc/ipsec.conf new file mode 100755 index 000000000..7df72bd4f --- /dev/null +++ b/testing/tests/ipv6/transport-ikev2/hosts/moon/etc/ipsec.conf @@ -0,0 +1,24 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + strictcrlpolicy=no + crlcheckinterval=180 + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + mobike=no + keyexchange=ikev2 + +conn host-host + left=PH_IP6_MOON + leftcert=moonCert.pem + leftid=@moon.strongswan.org + leftfirewall=yes + right=PH_IP6_SUN + rightid=@sun.strongswan.org + type=transport + auto=add diff --git a/testing/tests/ipv6/transport-ikev2/hosts/sun/etc/init.d/iptables b/testing/tests/ipv6/transport-ikev2/hosts/sun/etc/init.d/iptables new file mode 100755 index 000000000..25074a0f1 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev2/hosts/sun/etc/init.d/iptables @@ -0,0 +1,107 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # enable IP forwarding + echo 1 > /proc/sys/net/ipv6/conf/all/forwarding + echo 1 > /proc/sys/net/ipv4/ip_forward + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + /sbin/ip6tables -P INPUT DROP + /sbin/ip6tables -P OUTPUT DROP + /sbin/ip6tables -P FORWARD DROP + + # allow esp + ip6tables -A INPUT -i eth0 -p 50 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + ip6tables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow MobIKE + ip6tables -A INPUT -i eth0 -p udp --sport 4500 --dport 4500 -j ACCEPT + ip6tables -A OUTPUT -o eth0 -p udp --dport 4500 --sport 4500 -j ACCEPT + + # allow last UDP fragment + ip6tables -A INPUT -i eth0 -p udp -m frag --fraglast -j ACCEPT + + # allow ICMPv6 neighbor-solicitations + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-solicitation -j ACCEPT + + # allow ICMPv6 neighbor-advertisements + ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + ip6tables -A OUTPUT -p icmpv6 --icmpv6-type neighbor-advertisement -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + # log dropped packets + ip6tables -A INPUT -j LOG --log-prefix " IN: " + ip6tables -A OUTPUT -j LOG --log-prefix " OUT: " + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/ip6tables -t filter -P INPUT ACCEPT + /sbin/ip6tables -t filter -P FORWARD ACCEPT + /sbin/ip6tables -t filter -P OUTPUT ACCEPT + + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/ip6tables -F -t $a + /sbin/ip6tables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/ipv6/transport-ikev2/hosts/sun/etc/ipsec.conf b/testing/tests/ipv6/transport-ikev2/hosts/sun/etc/ipsec.conf new file mode 100755 index 000000000..b306ec666 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev2/hosts/sun/etc/ipsec.conf @@ -0,0 +1,24 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + strictcrlpolicy=no + crlcheckinterval=180 + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + mobike=no + keyexchange=ikev2 + +conn host-host + left=PH_IP6_SUN + leftcert=sunCert.pem + leftid=@sun.strongswan.org + leftfirewall=yes + right=PH_IP6_MOON + rightid=@moon.strongswan.org + type=transport + auto=add diff --git a/testing/tests/ipv6/transport-ikev2/posttest.dat b/testing/tests/ipv6/transport-ikev2/posttest.dat new file mode 100644 index 000000000..5a9150bc8 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev2/posttest.dat @@ -0,0 +1,4 @@ +moon::ipsec stop +sun::ipsec stop +moon::/etc/init.d/iptables stop 2> /dev/null +sun::/etc/init.d/iptables stop 2> /dev/null diff --git a/testing/tests/ipv6/transport-ikev2/pretest.dat b/testing/tests/ipv6/transport-ikev2/pretest.dat new file mode 100644 index 000000000..3536fd886 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev2/pretest.dat @@ -0,0 +1,6 @@ +moon::/etc/init.d/iptables start 2> /dev/null +sun::/etc/init.d/iptables start 2> /dev/null +moon::ipsec start +sun::ipsec start +moon::sleep 2 +moon::ipsec up host-host diff --git a/testing/tests/ipv6/transport-ikev2/test.conf b/testing/tests/ipv6/transport-ikev2/test.conf new file mode 100644 index 000000000..6ab5b8a96 --- /dev/null +++ b/testing/tests/ipv6/transport-ikev2/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="moon winnetou sun" + +# Corresponding block diagram +# +DIAGRAM="m-w-s-ip6.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="sun" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="moon sun" diff --git a/testing/tests/p2pnat/behind-same-nat/description.txt b/testing/tests/p2pnat/behind-same-nat/description.txt new file mode 100644 index 000000000..1d06ca3b5 --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/description.txt @@ -0,0 +1,6 @@ +The peers alice and venus are hidden behind the same NAT router moon +but both are not aware of this fact. Thus they try to resolve the apparent double-NAT +situation with the help of the mediation server carol where they register under +the pseudonyms 6cu1UTVw@medsrv.org and F1ubAio8@medsrv.org, respectively. +Based on the set of endpoints relayed to them by the mediation server, the peers find out +that they can communicate directly with each other without a NAT router in between. diff --git a/testing/tests/p2pnat/behind-same-nat/evaltest.dat b/testing/tests/p2pnat/behind-same-nat/evaltest.dat new file mode 100644 index 000000000..0036e073f --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/evaltest.dat @@ -0,0 +1,11 @@ +alice::ipsec statusall::medsrv.*ESTABLISHED::YES +venus::ipsec statusall::medsrv.*ESTABLISHED::YES +carol::ipsec statusall::medsrv.*ESTABLISHED.*PH_IP_MOON.*6cu1UTVw@medsrv.org::YES +carol::ipsec statusall::medsrv.*ESTABLISHED.*PH_IP_MOON.*F1ubAio8@medsrv.org::YES +alice::cat /var/log/daemon.log::received P2P_CALLBACK::YES +alice::ipsec statusall::p2p.*ESTABLISHED::YES +venus::ipsec statusall::p2p.*ESTABLISHED::YES +alice::ipsec statusall::p2p.*INSTALLED::YES +venus::ipsec statusall::p2p.*INSTALLED::YES +alice::ping -c 1 PH_IP_VENUS::64 bytes from PH_IP_VENUS: icmp_seq=1::YES +venus::ping -c 1 PH_IP_ALICE::64 bytes from PH_IP_ALICE: icmp_seq=1::YES diff --git a/testing/tests/p2pnat/behind-same-nat/hosts/alice/etc/init.d/iptables b/testing/tests/p2pnat/behind-same-nat/hosts/alice/etc/init.d/iptables new file mode 100755 index 000000000..937486984 --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/hosts/alice/etc/init.d/iptables @@ -0,0 +1,78 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + # allow esp + iptables -A INPUT -i eth0 -p 50 -j ACCEPT + iptables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + iptables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + iptables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow NAT-T including P2P + iptables -A INPUT -i eth0 -p udp --dport 4500 -j ACCEPT + iptables -A OUTPUT -o eth0 -p udp --sport 4500 -j ACCEPT + + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/p2pnat/behind-same-nat/hosts/alice/etc/ipsec.conf b/testing/tests/p2pnat/behind-same-nat/hosts/alice/etc/ipsec.conf new file mode 100755 index 000000000..e481996f7 --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/hosts/alice/etc/ipsec.conf @@ -0,0 +1,36 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + mobike=no + dpdaction=restart + dpddelay=60s + left=%defaultroute + leftfirewall=yes + +conn medsrv + leftid=6cu1UTVw@medsrv.org + right=PH_IP_CAROL + rightid=carol@strongswan.org + p2p_mediation=yes + authby=psk + auto=add + +conn p2p + leftcert=aliceCert.pem + leftid=alice@strongswan.org + right=%any + rightid=@venus.strongswan.org + rightsubnet=PH_IP_VENUS/32 + p2p_mediated_by=medsrv + p2p_peerid=F1ubAio8@medsrv.org + auto=start diff --git a/testing/tests/p2pnat/behind-same-nat/hosts/alice/etc/ipsec.secrets b/testing/tests/p2pnat/behind-same-nat/hosts/alice/etc/ipsec.secrets new file mode 100644 index 000000000..59396bbeb --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/hosts/alice/etc/ipsec.secrets @@ -0,0 +1,7 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +: RSA aliceKey.pem + +# secret used for mediation connection + +6cu1UTVw@medsrv.org : PSK "BAXz/6cSITttd0CzF9799p859Pi4LPnP" diff --git a/testing/tests/p2pnat/behind-same-nat/hosts/carol/etc/init.d/iptables b/testing/tests/p2pnat/behind-same-nat/hosts/carol/etc/init.d/iptables new file mode 100755 index 000000000..40510ce60 --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/hosts/carol/etc/init.d/iptables @@ -0,0 +1,77 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + # allow esp + iptables -A INPUT -i eth0 -p 50 -j ACCEPT + iptables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE behind NAT + iptables -A INPUT -i eth0 -p udp --dport 500 -j ACCEPT + iptables -A OUTPUT -o eth0 -p udp --sport 500 -j ACCEPT + + # allow NAT-T + iptables -A INPUT -i eth0 -p udp --dport 4500 -j ACCEPT + iptables -A OUTPUT -o eth0 -p udp --sport 4500 -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/p2pnat/behind-same-nat/hosts/carol/etc/ipsec.conf b/testing/tests/p2pnat/behind-same-nat/hosts/carol/etc/ipsec.conf new file mode 100755 index 000000000..712d888b1 --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/hosts/carol/etc/ipsec.conf @@ -0,0 +1,25 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + mobike=no + dpdaction=clear + dpddelay=60s + +conn medsrv + left=PH_IP_CAROL + leftcert=carolCert.pem + leftid=carol@strongswan.org + leftfirewall=yes + right=%any + p2p_mediation=yes + auto=add diff --git a/testing/tests/p2pnat/behind-same-nat/hosts/carol/etc/ipsec.secrets b/testing/tests/p2pnat/behind-same-nat/hosts/carol/etc/ipsec.secrets new file mode 100644 index 000000000..f1b30db72 --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/hosts/carol/etc/ipsec.secrets @@ -0,0 +1,11 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +: RSA carolKey.pem "nH5ZQEWtku0RJEZ6" + +# Mediation clients with random IDs + +6cu1UTVw@medsrv.org : PSK "BAXz/6cSITttd0CzF9799p859Pi4LPnP" + +F1ubAio8@medsrv.org : PSK "9tb3wiUGqUwCSRIRAwLFWfkdA8u6hHA8" + +av9oEPMz@medsrv.org : PSK "ZVm3FLOiweS1ywUDpR/L9FvpwNYp9svt" diff --git a/testing/tests/p2pnat/behind-same-nat/hosts/venus/etc/init.d/iptables b/testing/tests/p2pnat/behind-same-nat/hosts/venus/etc/init.d/iptables new file mode 100755 index 000000000..06d0ebca8 --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/hosts/venus/etc/init.d/iptables @@ -0,0 +1,78 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + # allow esp + iptables -A INPUT -i eth0 -p 50 -j ACCEPT + iptables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE + iptables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + iptables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow NAT-T including P2P + iptables -A INPUT -i eth0 -p udp --dport 4500 -j ACCEPT + iptables -A OUTPUT -o eth0 -p udp --sport 4500 -j ACCEPT + + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/p2pnat/behind-same-nat/hosts/venus/etc/ipsec.conf b/testing/tests/p2pnat/behind-same-nat/hosts/venus/etc/ipsec.conf new file mode 100755 index 000000000..d21009353 --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/hosts/venus/etc/ipsec.conf @@ -0,0 +1,36 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + mobike=no + dpdaction=restart + dpddelay=60s + left=%defaultroute + leftfirewall=yes + +conn medsrv + leftid=F1ubAio8@medsrv.org + right=PH_IP_CAROL + rightid=carol@strongswan.org + authby=psk + p2p_mediation=yes + auto=start + +conn p2p + leftcert=venusCert.pem + leftid=@venus.strongswan.org + right=%any + rightid=alice@strongswan.org + rightsubnet=PH_IP_ALICE/32 + p2p_mediated_by=medsrv + p2p_peerid=6cu1UTVw@medsrv.org + auto=add diff --git a/testing/tests/p2pnat/behind-same-nat/hosts/venus/etc/ipsec.secrets b/testing/tests/p2pnat/behind-same-nat/hosts/venus/etc/ipsec.secrets new file mode 100644 index 000000000..0032a6d3a --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/hosts/venus/etc/ipsec.secrets @@ -0,0 +1,7 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +: RSA venusKey.pem + +# secret used for mediation connection + +F1ubAio8@medsrv.org : PSK "9tb3wiUGqUwCSRIRAwLFWfkdA8u6hHA8" diff --git a/testing/tests/p2pnat/behind-same-nat/posttest.dat b/testing/tests/p2pnat/behind-same-nat/posttest.dat new file mode 100644 index 000000000..36cd0f36d --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/posttest.dat @@ -0,0 +1,8 @@ +venus::ipsec stop +alice::ipsec stop +carol::ipsec stop +alice::/etc/init.d/iptables stop 2> /dev/null +moon::/etc/init.d/iptables stop 2> /dev/null +carol::/etc/init.d/iptables stop 2> /dev/null +venus::/etc/init.d/iptables stop 2> /dev/null +moon::conntrack -F diff --git a/testing/tests/p2pnat/behind-same-nat/pretest.dat b/testing/tests/p2pnat/behind-same-nat/pretest.dat new file mode 100644 index 000000000..912222eef --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/pretest.dat @@ -0,0 +1,14 @@ +alice::/etc/init.d/iptables start 2> /dev/null +venus::/etc/init.d/iptables start 2> /dev/null +moon::/etc/init.d/iptables start 2> /dev/null +carol::/etc/init.d/iptables start 2> /dev/null +moon::iptables -t nat -A POSTROUTING -o eth0 -s 10.1.0.0/16 -p udp -j SNAT --to-source PH_IP_MOON:1100-1200 +moon::iptables -t nat -A POSTROUTING -o eth0 -s 10.1.0.0/16 -p tcp -j SNAT --to-source PH_IP_MOON:2000-2100 +moon::iptables -A FORWARD -i eth1 -o eth0 -s 10.1.0.0/16 -j ACCEPT +moon::iptables -A FORWARD -i eth0 -o eth1 -d 10.1.0.0/16 -j ACCEPT +carol::ipsec start +carol::sleep 1 +alice::ipsec start +alice::sleep 1 +venus::ipsec start +venus::sleep 2 diff --git a/testing/tests/p2pnat/behind-same-nat/test.conf b/testing/tests/p2pnat/behind-same-nat/test.conf new file mode 100644 index 000000000..f98a0ab1b --- /dev/null +++ b/testing/tests/p2pnat/behind-same-nat/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="alice venus moon carol winnetou" + +# Corresponding block diagram +# +DIAGRAM="a-v-m-c-w-med.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="moon" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="alice venus carol" diff --git a/testing/tests/p2pnat/medsrv-psk/description.txt b/testing/tests/p2pnat/medsrv-psk/description.txt new file mode 100644 index 000000000..16b3735bf --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/description.txt @@ -0,0 +1,7 @@ +The peers alice and bob are hidden behind the NAT routers moon and sun, +respectively. Due to this double-NAT situation they cannot set up an IPsec tunnel directly +but need the assistance from the mediation server carol with which they register under +the pseudonyms 6cu1UTVw@medsrv.org and av9oEPMz@medsrv.org, respectively, +authenticating by means of individual pre-shared keys. Using the set of endpoints relayed +to them by the mediation server, the peers are able to set up a direct IPsec connection.. +In order to test the double NAT-ed IPsec tunnel both peers ping each other. diff --git a/testing/tests/p2pnat/medsrv-psk/evaltest.dat b/testing/tests/p2pnat/medsrv-psk/evaltest.dat new file mode 100644 index 000000000..b8280c325 --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/evaltest.dat @@ -0,0 +1,12 @@ +alice::ipsec statusall::medsrv.*ESTABLISHED::YES +bob::ipsec statusall::medsrv.*ESTABLISHED::YES +carol::ipsec statusall::medsrv.*ESTABLISHED.*PH_IP_MOON.*6cu1UTVw@medsrv.org::YES +carol::ipsec statusall::medsrv.*ESTABLISHED.*PH_IP_SUN.*v9oEPMz@medsrv.org::YES +alice::ipsec statusall::p2p.*ESTABLISHED::YES +bob::ipsec statusall::p2p.*ESTABLISHED::YES +alice::ipsec statusall::p2p.*INSTALLED::YES +bob::ipsec statusall::p2p.*INSTALLED::YES +alice::ping -c 1 PH_IP_BOB::64 bytes from PH_IP_BOB: icmp_seq=1::YES +bob::ping -c 1 PH_IP_ALICE::64 bytes from PH_IP_ALICE: icmp_seq=1::YES +moon::tcpdump::IP moon.strongswan.org.* > sun.strongswan.org.*: UDP::YES +moon::tcpdump::IP sun.strongswan.org.* > moon.strongswan.org.*: UDP::YES diff --git a/testing/tests/p2pnat/medsrv-psk/hosts/alice/etc/init.d/iptables b/testing/tests/p2pnat/medsrv-psk/hosts/alice/etc/init.d/iptables new file mode 100755 index 000000000..09b4cabfa --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/hosts/alice/etc/init.d/iptables @@ -0,0 +1,74 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + # allow IKE + iptables -A INPUT -i eth0 -p udp --sport 500 --dport 500 -j ACCEPT + iptables -A OUTPUT -o eth0 -p udp --dport 500 --sport 500 -j ACCEPT + + # allow NAT-T including P2P + iptables -A INPUT -i eth0 -p udp --dport 4500 -j ACCEPT + iptables -A OUTPUT -o eth0 -p udp --sport 4500 -j ACCEPT + + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/p2pnat/medsrv-psk/hosts/alice/etc/ipsec.conf b/testing/tests/p2pnat/medsrv-psk/hosts/alice/etc/ipsec.conf new file mode 100755 index 000000000..370934ce7 --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/hosts/alice/etc/ipsec.conf @@ -0,0 +1,36 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + mobike=no + dpdaction=restart + dpddelay=60s + left=%defaultroute + leftfirewall=yes + +conn medsrv + leftid=6cu1UTVw@medsrv.org + right=PH_IP_CAROL + rightid=carol@strongswan.org + p2p_mediation=yes + authby=psk + auto=add + +conn p2p + leftcert=aliceCert.pem + leftid=alice@strongswan.org + right=%any + rightid=bob@strongswan.org + rightsubnet=PH_IP_BOB/32 + p2p_mediated_by=medsrv + p2p_peerid=av9oEPMz@medsrv.org + auto=start diff --git a/testing/tests/p2pnat/medsrv-psk/hosts/alice/etc/ipsec.secrets b/testing/tests/p2pnat/medsrv-psk/hosts/alice/etc/ipsec.secrets new file mode 100644 index 000000000..59396bbeb --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/hosts/alice/etc/ipsec.secrets @@ -0,0 +1,7 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +: RSA aliceKey.pem + +# secret used for mediation connection + +6cu1UTVw@medsrv.org : PSK "BAXz/6cSITttd0CzF9799p859Pi4LPnP" diff --git a/testing/tests/p2pnat/medsrv-psk/hosts/bob/etc/ipsec.conf b/testing/tests/p2pnat/medsrv-psk/hosts/bob/etc/ipsec.conf new file mode 100755 index 000000000..8d8d9391f --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/hosts/bob/etc/ipsec.conf @@ -0,0 +1,36 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + mobike=no + dpdaction=restart + dpddelay=60s + left=%defaultroute + leftfirewall=yes + +conn medsrv + leftid=av9oEPMz@medsrv.org + right=PH_IP_CAROL + rightid=carol@strongswan.org + authby=psk + p2p_mediation=yes + auto=start + +conn p2p + leftcert=bobCert.pem + leftid=bob@strongswan.org + right=%any + rightid=alice@strongswan.org + rightsubnet=PH_IP_ALICE/32 + p2p_mediated_by=medsrv + p2p_peerid=6cu1UTVw@medsrv.org + auto=add diff --git a/testing/tests/p2pnat/medsrv-psk/hosts/bob/etc/ipsec.secrets b/testing/tests/p2pnat/medsrv-psk/hosts/bob/etc/ipsec.secrets new file mode 100644 index 000000000..0dc3958da --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/hosts/bob/etc/ipsec.secrets @@ -0,0 +1,7 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +: RSA bobKey.pem + +# secret used for mediation connection + +av9oEPMz@medsrv.org : PSK "ZVm3FLOiweS1ywUDpR/L9FvpwNYp9svt" diff --git a/testing/tests/p2pnat/medsrv-psk/hosts/carol/etc/init.d/iptables b/testing/tests/p2pnat/medsrv-psk/hosts/carol/etc/init.d/iptables new file mode 100755 index 000000000..40510ce60 --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/hosts/carol/etc/init.d/iptables @@ -0,0 +1,77 @@ +#!/sbin/runscript +# Copyright 1999-2004 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +opts="start stop reload" + +depend() { + before net + need logger +} + +start() { + ebegin "Starting firewall" + + # default policy is DROP + /sbin/iptables -P INPUT DROP + /sbin/iptables -P OUTPUT DROP + /sbin/iptables -P FORWARD DROP + + # allow esp + iptables -A INPUT -i eth0 -p 50 -j ACCEPT + iptables -A OUTPUT -o eth0 -p 50 -j ACCEPT + + # allow IKE behind NAT + iptables -A INPUT -i eth0 -p udp --dport 500 -j ACCEPT + iptables -A OUTPUT -o eth0 -p udp --sport 500 -j ACCEPT + + # allow NAT-T + iptables -A INPUT -i eth0 -p udp --dport 4500 -j ACCEPT + iptables -A OUTPUT -o eth0 -p udp --sport 4500 -j ACCEPT + + # allow crl fetch from winnetou + iptables -A INPUT -i eth0 -p tcp --sport 80 -s PH_IP_WINNETOU -j ACCEPT + iptables -A OUTPUT -o eth0 -p tcp --dport 80 -d PH_IP_WINNETOU -j ACCEPT + + # allow ssh + iptables -A INPUT -p tcp --dport 22 -j ACCEPT + iptables -A OUTPUT -p tcp --sport 22 -j ACCEPT + + eend $? +} + +stop() { + ebegin "Stopping firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + + if [ $a == nat ]; then + /sbin/iptables -t nat -P PREROUTING ACCEPT + /sbin/iptables -t nat -P POSTROUTING ACCEPT + /sbin/iptables -t nat -P OUTPUT ACCEPT + elif [ $a == mangle ]; then + /sbin/iptables -t mangle -P PREROUTING ACCEPT + /sbin/iptables -t mangle -P INPUT ACCEPT + /sbin/iptables -t mangle -P FORWARD ACCEPT + /sbin/iptables -t mangle -P OUTPUT ACCEPT + /sbin/iptables -t mangle -P POSTROUTING ACCEPT + elif [ $a == filter ]; then + /sbin/iptables -t filter -P INPUT ACCEPT + /sbin/iptables -t filter -P FORWARD ACCEPT + /sbin/iptables -t filter -P OUTPUT ACCEPT + fi + done + eend $? +} + +reload() { + ebegin "Flushing firewall" + for a in `cat /proc/net/ip_tables_names`; do + /sbin/iptables -F -t $a + /sbin/iptables -X -t $a + done; + eend $? + start +} + diff --git a/testing/tests/p2pnat/medsrv-psk/hosts/carol/etc/ipsec.conf b/testing/tests/p2pnat/medsrv-psk/hosts/carol/etc/ipsec.conf new file mode 100755 index 000000000..712d888b1 --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/hosts/carol/etc/ipsec.conf @@ -0,0 +1,25 @@ +# /etc/ipsec.conf - strongSwan IPsec configuration file + +config setup + crlcheckinterval=180 + strictcrlpolicy=no + plutostart=no + +conn %default + ikelifetime=60m + keylife=20m + rekeymargin=3m + keyingtries=1 + keyexchange=ikev2 + mobike=no + dpdaction=clear + dpddelay=60s + +conn medsrv + left=PH_IP_CAROL + leftcert=carolCert.pem + leftid=carol@strongswan.org + leftfirewall=yes + right=%any + p2p_mediation=yes + auto=add diff --git a/testing/tests/p2pnat/medsrv-psk/hosts/carol/etc/ipsec.secrets b/testing/tests/p2pnat/medsrv-psk/hosts/carol/etc/ipsec.secrets new file mode 100644 index 000000000..64089431a --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/hosts/carol/etc/ipsec.secrets @@ -0,0 +1,9 @@ +# /etc/ipsec.secrets - strongSwan IPsec secrets file + +: RSA carolKey.pem "nH5ZQEWtku0RJEZ6" + +# Mediation clients with random IDs + +6cu1UTVw@medsrv.org : PSK "BAXz/6cSITttd0CzF9799p859Pi4LPnP" + +av9oEPMz@medsrv.org : PSK "ZVm3FLOiweS1ywUDpR/L9FvpwNYp9svt" diff --git a/testing/tests/p2pnat/medsrv-psk/posttest.dat b/testing/tests/p2pnat/medsrv-psk/posttest.dat new file mode 100644 index 000000000..ca3cebc0a --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/posttest.dat @@ -0,0 +1,10 @@ +bob::ipsec stop +alice::ipsec stop +carol::ipsec stop +alice::/etc/init.d/iptables stop 2> /dev/null +moon::/etc/init.d/iptables stop 2> /dev/null +carol::/etc/init.d/iptables stop 2> /dev/null +sun::/etc/init.d/iptables stop 2> /dev/null +bob::/etc/init.d/iptables stop 2> /dev/null +moon::conntrack -F +sun::conntrack -F diff --git a/testing/tests/p2pnat/medsrv-psk/pretest.dat b/testing/tests/p2pnat/medsrv-psk/pretest.dat new file mode 100644 index 000000000..a5c9a2fbb --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/pretest.dat @@ -0,0 +1,19 @@ +alice::/etc/init.d/iptables start 2> /dev/null +moon::/etc/init.d/iptables start 2> /dev/null +carol::/etc/init.d/iptables start 2> /dev/null +sun::/etc/init.d/iptables start 2> /dev/null +bob::/etc/init.d/iptables start 2> /dev/null +moon::iptables -t nat -A POSTROUTING -o eth0 -s 10.1.0.0/16 -p udp -j SNAT --to-source PH_IP_MOON:1100-1200 +moon::iptables -t nat -A POSTROUTING -o eth0 -s 10.1.0.0/16 -p tcp -j SNAT --to-source PH_IP_MOON:2000-2100 +moon::iptables -A FORWARD -i eth1 -o eth0 -s 10.1.0.0/16 -j ACCEPT +moon::iptables -A FORWARD -i eth0 -o eth1 -d 10.1.0.0/16 -j ACCEPT +sun::iptables -t nat -A POSTROUTING -o eth0 -s 10.2.0.0/16 -p udp -j SNAT --to-source PH_IP_SUN:1200-1300 +sun::iptables -t nat -A POSTROUTING -o eth0 -s 10.2.0.0/16 -p tcp -j SNAT --to-source PH_IP_SUN:2000-2100 +sun::iptables -A FORWARD -i eth1 -o eth0 -s 10.2.0.0/16 -j ACCEPT +sun::iptables -A FORWARD -i eth0 -o eth1 -d 10.2.0.0/16 -j ACCEPT +carol::ipsec start +carol::sleep 1 +bob::ipsec start +bob::sleep 1 +alice::ipsec start +alice::sleep 2 diff --git a/testing/tests/p2pnat/medsrv-psk/test.conf b/testing/tests/p2pnat/medsrv-psk/test.conf new file mode 100644 index 000000000..2dc4cd8c1 --- /dev/null +++ b/testing/tests/p2pnat/medsrv-psk/test.conf @@ -0,0 +1,21 @@ +#!/bin/bash +# +# This configuration file provides information on the +# UML instances used for this test + +# All UML instances that are required for this test +# +UMLHOSTS="alice moon carol winnetou sun bob" + +# Corresponding block diagram +# +DIAGRAM="a-m-c-w-s-b-med.png" + +# UML instances on which tcpdump is to be started +# +TCPDUMPHOSTS="moon" + +# UML instances on which IPsec is started +# Used for IPsec logging purposes +# +IPSECHOSTS="alice carol bob" -- cgit v1.2.3