diff options
| author | Yves-Alexis Perez <corsac@debian.org> | 2013-10-17 21:23:38 +0200 |
|---|---|---|
| committer | Yves-Alexis Perez <corsac@debian.org> | 2013-10-17 21:23:38 +0200 |
| commit | 9d37ad77ef660b92ea51b69d74e14f931d2a04e2 (patch) | |
| tree | d6bbb4a5fed1959f8675df9ee7c03713b543fcc9 /src/libcharon/plugins/tnc_ifmap | |
| parent | 104f57d4b0fb6d7547d6898352eaa5fb4b222010 (diff) | |
| parent | e5ee4e7fcdd58b7d86bf1b458da2c63e8e19627b (diff) | |
| download | vyos-strongswan-9d37ad77ef660b92ea51b69d74e14f931d2a04e2.tar.gz vyos-strongswan-9d37ad77ef660b92ea51b69d74e14f931d2a04e2.zip | |
Merge tag 'v5.1.0-1' into sid
tag strongSwan 5.1.0-1
Diffstat (limited to 'src/libcharon/plugins/tnc_ifmap')
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/Makefile.am | 23 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/Makefile.in | 173 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/tnc_ifmap_http.c | 245 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/tnc_ifmap_http.h | 68 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/tnc_ifmap_listener.c | 44 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/tnc_ifmap_listener.h | 2 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/tnc_ifmap_plugin.c | 55 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/tnc_ifmap_plugin.h | 2 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/tnc_ifmap_renew_session_job.c | 103 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/tnc_ifmap_renew_session_job.h | 51 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap.c | 1003 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap.h | 50 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap_msg.c | 256 | ||||
| -rw-r--r-- | src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap_msg.h | 62 |
14 files changed, 1589 insertions, 548 deletions
diff --git a/src/libcharon/plugins/tnc_ifmap/Makefile.am b/src/libcharon/plugins/tnc_ifmap/Makefile.am index b8a57b119..dfbb1b632 100644 --- a/src/libcharon/plugins/tnc_ifmap/Makefile.am +++ b/src/libcharon/plugins/tnc_ifmap/Makefile.am @@ -1,10 +1,12 @@ +AM_CPPFLAGS = \ + -I$(top_srcdir)/src/libstrongswan \ + -I$(top_srcdir)/src/libtls \ + -I$(top_srcdir)/src/libhydra \ + -I$(top_srcdir)/src/libcharon -INCLUDES = -I$(top_srcdir)/src/libstrongswan -I$(top_srcdir)/src/libhydra \ - -I$(top_srcdir)/src/libcharon ${axis2c_CFLAGS} - -AM_CFLAGS = -rdynamic - -libstrongswan_tnc_ifmap_la_LIBADD = ${axis2c_LIBS} -laxutil -laxis2_engine -laxis2_http_sender +AM_CFLAGS = \ + ${xml_CFLAGS} \ + -rdynamic if MONOLITHIC noinst_LTLIBRARIES = libstrongswan-tnc-ifmap.la @@ -12,10 +14,15 @@ else plugin_LTLIBRARIES = libstrongswan-tnc-ifmap.la endif +libstrongswan_tnc_ifmap_la_LIBADD = \ + $(top_builddir)/src/libtls/libtls.la ${xml_LIBS} + libstrongswan_tnc_ifmap_la_SOURCES = \ tnc_ifmap_plugin.h tnc_ifmap_plugin.c \ tnc_ifmap_listener.h tnc_ifmap_listener.c \ - tnc_ifmap_soap.h tnc_ifmap_soap.c + tnc_ifmap_soap.h tnc_ifmap_soap.c \ + tnc_ifmap_soap_msg.h tnc_ifmap_soap_msg.c \ + tnc_ifmap_http.h tnc_ifmap_http.c \ + tnc_ifmap_renew_session_job.h tnc_ifmap_renew_session_job.c libstrongswan_tnc_ifmap_la_LDFLAGS = -module -avoid-version - diff --git a/src/libcharon/plugins/tnc_ifmap/Makefile.in b/src/libcharon/plugins/tnc_ifmap/Makefile.in index 54deb7cd7..6bb68b32c 100644 --- a/src/libcharon/plugins/tnc_ifmap/Makefile.in +++ b/src/libcharon/plugins/tnc_ifmap/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -16,6 +16,23 @@ @SET_MAKE@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -45,10 +62,11 @@ am__aclocal_m4_deps = $(top_srcdir)/m4/config/libtool.m4 \ $(top_srcdir)/m4/macros/with.m4 \ $(top_srcdir)/m4/macros/enable-disable.m4 \ $(top_srcdir)/m4/macros/add-plugin.m4 \ - $(top_srcdir)/configure.in + $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ $(ACLOCAL_M4) mkinstalldirs = $(install_sh) -d +CONFIG_HEADER = $(top_builddir)/config.h CONFIG_CLEAN_FILES = CONFIG_CLEAN_VPATH_FILES = am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; @@ -72,57 +90,93 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(plugindir)" LTLIBRARIES = $(noinst_LTLIBRARIES) $(plugin_LTLIBRARIES) am__DEPENDENCIES_1 = -libstrongswan_tnc_ifmap_la_DEPENDENCIES = $(am__DEPENDENCIES_1) +libstrongswan_tnc_ifmap_la_DEPENDENCIES = \ + $(top_builddir)/src/libtls/libtls.la $(am__DEPENDENCIES_1) am_libstrongswan_tnc_ifmap_la_OBJECTS = tnc_ifmap_plugin.lo \ - tnc_ifmap_listener.lo tnc_ifmap_soap.lo + tnc_ifmap_listener.lo tnc_ifmap_soap.lo tnc_ifmap_soap_msg.lo \ + tnc_ifmap_http.lo tnc_ifmap_renew_session_job.lo libstrongswan_tnc_ifmap_la_OBJECTS = \ $(am_libstrongswan_tnc_ifmap_la_OBJECTS) -libstrongswan_tnc_ifmap_la_LINK = $(LIBTOOL) --tag=CC \ +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) +am__v_lt_0 = --silent +libstrongswan_tnc_ifmap_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libstrongswan_tnc_ifmap_la_LDFLAGS) \ $(LDFLAGS) -o $@ @MONOLITHIC_FALSE@am_libstrongswan_tnc_ifmap_la_rpath = -rpath \ @MONOLITHIC_FALSE@ $(plugindir) @MONOLITHIC_TRUE@am_libstrongswan_tnc_ifmap_la_rpath = -DEFAULT_INCLUDES = -I.@am__isrc@ +DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles am__mv = mv -f COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -LTCOMPILE = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ - --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) \ - $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ + $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ + $(AM_CFLAGS) $(CFLAGS) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) +am__v_CC_0 = @echo " CC " $@; +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) +am__v_at_0 = @ CCLD = $(CC) -LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ - --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) \ - $(LDFLAGS) -o $@ +LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ + $(AM_LDFLAGS) $(LDFLAGS) -o $@ +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) +am__v_CCLD_0 = @echo " CCLD " $@; +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) +am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libstrongswan_tnc_ifmap_la_SOURCES) DIST_SOURCES = $(libstrongswan_tnc_ifmap_la_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac ETAGS = etags CTAGS = ctags DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) ACLOCAL = @ACLOCAL@ ALLOCA = @ALLOCA@ AMTAR = @AMTAR@ +AM_DEFAULT_VERBOSITY = @AM_DEFAULT_VERBOSITY@ AR = @AR@ AUTOCONF = @AUTOCONF@ AUTOHEADER = @AUTOHEADER@ AUTOMAKE = @AUTOMAKE@ AWK = @AWK@ +BFDLIB = @BFDLIB@ BTLIB = @BTLIB@ CC = @CC@ CCDEPMODE = @CCDEPMODE@ CFLAGS = @CFLAGS@ +CHECK_CFLAGS = @CHECK_CFLAGS@ +CHECK_LIBS = @CHECK_LIBS@ +COVERAGE_CFLAGS = @COVERAGE_CFLAGS@ +COVERAGE_LDFLAGS = @COVERAGE_LDFLAGS@ CPP = @CPP@ CPPFLAGS = @CPPFLAGS@ CYGPATH_W = @CYGPATH_W@ DEFS = @DEFS@ DEPDIR = @DEPDIR@ DLLIB = @DLLIB@ +DLLTOOL = @DLLTOOL@ DSYMUTIL = @DSYMUTIL@ DUMPBIN = @DUMPBIN@ ECHO_C = @ECHO_C@ @@ -131,13 +185,16 @@ ECHO_T = @ECHO_T@ EGREP = @EGREP@ EXEEXT = @EXEEXT@ FGREP = @FGREP@ +GENHTML = @GENHTML@ GPERF = @GPERF@ +GPRBUILD = @GPRBUILD@ GREP = @GREP@ INSTALL = @INSTALL@ INSTALL_DATA = @INSTALL_DATA@ INSTALL_PROGRAM = @INSTALL_PROGRAM@ INSTALL_SCRIPT = @INSTALL_SCRIPT@ INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +LCOV = @LCOV@ LD = @LD@ LDFLAGS = @LDFLAGS@ LEX = @LEX@ @@ -150,6 +207,7 @@ LIPO = @LIPO@ LN_S = @LN_S@ LTLIBOBJS = @LTLIBOBJS@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MYSQLCFLAG = @MYSQLCFLAG@ MYSQLCONFIG = @MYSQLCONFIG@ @@ -177,11 +235,13 @@ RANLIB = @RANLIB@ RTLIB = @RTLIB@ RUBY = @RUBY@ RUBYINCLUDE = @RUBYINCLUDE@ +RUBYLIB = @RUBYLIB@ SED = @SED@ SET_MAKE = @SET_MAKE@ SHELL = @SHELL@ SOCKLIB = @SOCKLIB@ STRIP = @STRIP@ +UNWINDLIB = @UNWINDLIB@ VERSION = @VERSION@ YACC = @YACC@ YFLAGS = @YFLAGS@ @@ -189,6 +249,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ am__include = @am__include@ @@ -197,8 +258,6 @@ am__quote = @am__quote@ am__tar = @am__tar@ am__untar = @am__untar@ attest_plugins = @attest_plugins@ -axis2c_CFLAGS = @axis2c_CFLAGS@ -axis2c_LIBS = @axis2c_LIBS@ bindir = @bindir@ build = @build@ build_alias = @build_alias@ @@ -207,14 +266,19 @@ build_os = @build_os@ build_vendor = @build_vendor@ builddir = @builddir@ c_plugins = @c_plugins@ +charon_natt_port = @charon_natt_port@ +charon_plugins = @charon_plugins@ +charon_udp_port = @charon_udp_port@ clearsilver_LIBS = @clearsilver_LIBS@ +cmd_plugins = @cmd_plugins@ datadir = @datadir@ datarootdir = @datarootdir@ dbusservicedir = @dbusservicedir@ -default_pkcs11 = @default_pkcs11@ +dev_headers = @dev_headers@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +fips_mode = @fips_mode@ gtk_CFLAGS = @gtk_CFLAGS@ gtk_LIBS = @gtk_LIBS@ h_plugins = @h_plugins@ @@ -228,17 +292,17 @@ imcvdir = @imcvdir@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ +ipsec_script = @ipsec_script@ +ipsec_script_upper = @ipsec_script_upper@ ipsecdir = @ipsecdir@ ipsecgroup = @ipsecgroup@ ipseclibdir = @ipseclibdir@ ipsecuser = @ipsecuser@ -libcharon_plugins = @libcharon_plugins@ libdir = @libdir@ libexecdir = @libexecdir@ linux_headers = @linux_headers@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ maemo_CFLAGS = @maemo_CFLAGS@ maemo_LIBS = @maemo_LIBS@ manager_plugins = @manager_plugins@ @@ -248,16 +312,15 @@ mkdir_p = @mkdir_p@ nm_CFLAGS = @nm_CFLAGS@ nm_LIBS = @nm_LIBS@ nm_ca_dir = @nm_ca_dir@ +nm_plugins = @nm_plugins@ oldincludedir = @oldincludedir@ openac_plugins = @openac_plugins@ -p_plugins = @p_plugins@ pcsclite_CFLAGS = @pcsclite_CFLAGS@ pcsclite_LIBS = @pcsclite_LIBS@ pdfdir = @pdfdir@ piddir = @piddir@ pki_plugins = @pki_plugins@ plugindir = @plugindir@ -pluto_plugins = @pluto_plugins@ pool_plugins = @pool_plugins@ prefix = @prefix@ program_transform_name = @program_transform_name@ @@ -285,17 +348,28 @@ top_srcdir = @top_srcdir@ urandom_device = @urandom_device@ xml_CFLAGS = @xml_CFLAGS@ xml_LIBS = @xml_LIBS@ -INCLUDES = -I$(top_srcdir)/src/libstrongswan -I$(top_srcdir)/src/libhydra \ - -I$(top_srcdir)/src/libcharon ${axis2c_CFLAGS} +AM_CPPFLAGS = \ + -I$(top_srcdir)/src/libstrongswan \ + -I$(top_srcdir)/src/libtls \ + -I$(top_srcdir)/src/libhydra \ + -I$(top_srcdir)/src/libcharon + +AM_CFLAGS = \ + ${xml_CFLAGS} \ + -rdynamic -AM_CFLAGS = -rdynamic -libstrongswan_tnc_ifmap_la_LIBADD = ${axis2c_LIBS} -laxutil -laxis2_engine -laxis2_http_sender @MONOLITHIC_TRUE@noinst_LTLIBRARIES = libstrongswan-tnc-ifmap.la @MONOLITHIC_FALSE@plugin_LTLIBRARIES = libstrongswan-tnc-ifmap.la +libstrongswan_tnc_ifmap_la_LIBADD = \ + $(top_builddir)/src/libtls/libtls.la ${xml_LIBS} + libstrongswan_tnc_ifmap_la_SOURCES = \ tnc_ifmap_plugin.h tnc_ifmap_plugin.c \ tnc_ifmap_listener.h tnc_ifmap_listener.c \ - tnc_ifmap_soap.h tnc_ifmap_soap.c + tnc_ifmap_soap.h tnc_ifmap_soap.c \ + tnc_ifmap_soap_msg.h tnc_ifmap_soap_msg.c \ + tnc_ifmap_http.h tnc_ifmap_http.c \ + tnc_ifmap_renew_session_job.h tnc_ifmap_renew_session_job.c libstrongswan_tnc_ifmap_la_LDFLAGS = -module -avoid-version all: all-am @@ -343,7 +417,6 @@ clean-noinstLTLIBRARIES: done install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(plugindir)" || $(MKDIR_P) "$(DESTDIR)$(plugindir)" @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -351,6 +424,8 @@ install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ } @@ -372,8 +447,8 @@ clean-pluginLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libstrongswan-tnc-ifmap.la: $(libstrongswan_tnc_ifmap_la_OBJECTS) $(libstrongswan_tnc_ifmap_la_DEPENDENCIES) - $(libstrongswan_tnc_ifmap_la_LINK) $(am_libstrongswan_tnc_ifmap_la_rpath) $(libstrongswan_tnc_ifmap_la_OBJECTS) $(libstrongswan_tnc_ifmap_la_LIBADD) $(LIBS) +libstrongswan-tnc-ifmap.la: $(libstrongswan_tnc_ifmap_la_OBJECTS) $(libstrongswan_tnc_ifmap_la_DEPENDENCIES) $(EXTRA_libstrongswan_tnc_ifmap_la_DEPENDENCIES) + $(AM_V_CCLD)$(libstrongswan_tnc_ifmap_la_LINK) $(am_libstrongswan_tnc_ifmap_la_rpath) $(libstrongswan_tnc_ifmap_la_OBJECTS) $(libstrongswan_tnc_ifmap_la_LIBADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -381,30 +456,33 @@ mostlyclean-compile: distclean-compile: -rm -f *.tab.c +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tnc_ifmap_http.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tnc_ifmap_listener.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tnc_ifmap_plugin.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tnc_ifmap_renew_session_job.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tnc_ifmap_soap.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tnc_ifmap_soap_msg.Plo@am__quote@ .c.o: -@am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: -@am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` -@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: -@am__fastdepCC_TRUE@ $(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -511,10 +589,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_http.c b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_http.c new file mode 100644 index 000000000..001a3fbee --- /dev/null +++ b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_http.c @@ -0,0 +1,245 @@ +/* + * Copyright (C) 2013 Andreas Steffen + * HSR 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 <http://www.fsf.org/copyleft/gpl.txt>. + * + * 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. + */ + +#define _GNU_SOURCE /* for asprintf() */ + +#include "tnc_ifmap_http.h" + +#include <utils/debug.h> +#include <utils/lexparser.h> + +#include <stdio.h> + +typedef struct private_tnc_ifmap_http_t private_tnc_ifmap_http_t; + +/** + * Private data of an tnc_ifmap_http_t object. + */ +struct private_tnc_ifmap_http_t { + + /** + * Public tnc_ifmap_http_t interface. + */ + tnc_ifmap_http_t public; + + /** + * HTTPS Server URI with https:// prefix removed + */ + char *uri; + + /** + * Optional base64-encoded username:password for HTTP Basic Authentication + */ + chunk_t user_pass; + + /** + * HTTP chunked mode + */ + bool chunked; + +}; + +METHOD(tnc_ifmap_http_t, build, status_t, + private_tnc_ifmap_http_t *this, chunk_t *in, chunk_t *out) +{ + char *host, *path, *request, auth[128]; + int len; + + /* Duplicate host[/path] string since we are going to manipulate it */ + len = strlen(this->uri) + 2; + host = malloc(len); + memset(host, '\0', len); + strcpy(host, this->uri); + + /* Extract appended path or set to root */ + path = strchr(host, '/'); + if (!path) + { + path = host + len - 2; + *path = '/'; + } + + /* Use Basic Authentication? */ + if (this->user_pass.len) + { + snprintf(auth, sizeof(auth), "Authorization: Basic %.*s\r\n", + (int)this->user_pass.len, this->user_pass.ptr); + } + else + { + *auth = '\0'; + } + + /* Write HTTP POST request, TODO break up into chunks */ + len = asprintf(&request, + "POST %s HTTP/1.1\r\n" + "Host: %.*s\r\n" + "%s" + "Content-Type: application/soap+xml;charset=utf-8\r\n" + "Content-Length: %d\r\n" + "\r\n" + "%.*s", path, (int)(path-host), host, auth, (int)in->len, + (int)in->len, in->ptr); + free(host); + + if (len == -1) + { + return FAILED; + } + *out = chunk_create(request, len); + DBG3(DBG_TLS, "sending HTTP POST request %B", out); + + return SUCCESS; +} + +static bool process_header(chunk_t *in, bool *chunked, u_int *content_len) +{ + chunk_t line, version, parameter; + int code; + u_int len; + + /* Process HTTP protocol version */ + if (!fetchline(in, &line) || !extract_token(&version, ' ', &line) || + !match("HTTP/1.1", &version) || sscanf(line.ptr, "%d", &code) != 1) + { + DBG1(DBG_TNC, "malformed http response header"); + return FALSE; + } + if (code != 200) + { + DBG1(DBG_TNC, "http response returns error code %d", code); + return FALSE; + } + + *content_len = 0; + *chunked = FALSE; + + /* Process HTTP header line by line until the HTTP body is reached */ + while (fetchline(in, &line)) + { + if (line.len == 0) + { + break; + } + if (extract_token(¶meter, ':', &line) && eat_whitespace(&line)) + { + if (match("Content-Length", ¶meter)) + { + if (sscanf(line.ptr, "%u", &len) == 1) + { + *content_len = len; + } + } + else if (match("Transfer-Encoding", ¶meter) && + match("chunked", &line)) + { + *chunked = TRUE; + } + } + } + + return TRUE; +} + +METHOD(tnc_ifmap_http_t, process, status_t, + private_tnc_ifmap_http_t *this, chunk_t *in, chunk_t *out) +{ + u_int len = 0; + chunk_t line, out_chunk; + + DBG3(DBG_TLS, "receiving HTTP response %B", in); + + if (!this->chunked) + { + if (!process_header(in, &this->chunked, &len)) + { + return FAILED; + } + } + + while (in->len) + { + if (this->chunked) + { + if (!fetchline(in, &line) || sscanf(line.ptr, "%x", &len) != 1) + { + return FAILED; + } + DBG3(DBG_TLS, "received HTTP response is chunked (%u bytes)", len); + + /* Received last chunk? */ + if (len == 0) + { + return SUCCESS; + } + } + + /* Check size of of remaining HTTP body */ + if (len > in->len) + { + DBG1(DBG_TNC, "insufficient data in HTTP body"); + return FAILED; + } + + if (this->chunked) + { + out_chunk = *in; + out_chunk.len = len; + *out = chunk_cat("mc", *out, out_chunk); + *in = chunk_skip(*in, len); + if (!fetchline(in, &line) || line.len > 0) + { + return FAILED; + } + } + else + { + if (len) + { + in->len = len; + } + *out = chunk_clone(*in); + return SUCCESS; + } + } + return NEED_MORE; +} + +METHOD(tnc_ifmap_http_t, destroy, void, + private_tnc_ifmap_http_t *this) +{ + free(this); +} + +/** + * See header + */ +tnc_ifmap_http_t *tnc_ifmap_http_create(char *uri, chunk_t user_pass) +{ + private_tnc_ifmap_http_t *this; + + INIT(this, + .public = { + .build = _build, + .process = _process, + .destroy = _destroy, + }, + .uri = uri, + .user_pass = user_pass, + ); + + return &this->public; +} + diff --git a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_http.h b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_http.h new file mode 100644 index 000000000..3d3084744 --- /dev/null +++ b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_http.h @@ -0,0 +1,68 @@ +/* + * Copyright (C) 2013 Andreas Steffen + * HSR 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 <http://www.fsf.org/copyleft/gpl.txt>. + * + * 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. + */ + +/** + * @defgroup tnc_ifmap_http tnc_ifmap_http + * @{ @ingroup tnc_ifmap + */ + +#ifndef TNC_IFMAP_HTTP_H_ +#define TNC_IFMAP_HTTP_H_ + +#include <library.h> +#include <tls_socket.h> + +#include <libxml/parser.h> + +typedef struct tnc_ifmap_http_t tnc_ifmap_http_t; + +/** + * Interface for building and processing HTTP messages + */ +struct tnc_ifmap_http_t { + + /** + * Build a HTTP POST message + * + * @param in input data + * @param out HTTP POST request + * @result status return code + */ + status_t (*build)(tnc_ifmap_http_t *this, chunk_t *in, chunk_t *out); + + /** + * Receive a HTTP [chunked] response + * + * @param in [chunked] HTTP response + * @param out output data + * @result status return code + */ + status_t (*process)(tnc_ifmap_http_t *this, chunk_t *in, chunk_t *out); + + /** + * Destroy a tnc_ifmap_http_t object. + */ + void (*destroy)(tnc_ifmap_http_t *this); +}; + +/** + * Create a tnc_ifmap_http instance. + * + * @param uri HTTPS URI with https:// prefix removed + * @param user_pass Optional username:password for HTTP Basic Authentication + */ +tnc_ifmap_http_t *tnc_ifmap_http_create(char *uri, chunk_t user_pass); + +#endif /** TNC_IFMAP_HTTP_H_ @}*/ diff --git a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_listener.c b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_listener.c index 4fd33696c..4ad19c530 100644 --- a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_listener.c +++ b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_listener.c @@ -1,5 +1,5 @@ /* - * Copyright (C) 2011 Andreas Steffen + * Copyright (C) 2011-2013 Andreas Steffen * HSR Hochschule fuer Technik Rapperswil * * This program is free software; you can redistribute it and/or modify it @@ -15,10 +15,13 @@ #include "tnc_ifmap_listener.h" #include "tnc_ifmap_soap.h" +#include "tnc_ifmap_renew_session_job.h" #include <daemon.h> #include <hydra.h> -#include <debug.h> +#include <utils/debug.h> + +#define IFMAP_RENEW_SESSION_INTERVAL 150 typedef struct private_tnc_ifmap_listener_t private_tnc_ifmap_listener_t; @@ -49,7 +52,7 @@ static bool publish_device_ip_addresses(private_tnc_ifmap_listener_t *this) bool success = TRUE; enumerator = hydra->kernel_interface->create_address_enumerator( - hydra->kernel_interface, FALSE, FALSE); + hydra->kernel_interface, ADDR_TYPE_REGULAR); while (enumerator->enumerate(enumerator, &host)) { if (!this->ifmap->publish_device_ip(this->ifmap, host)) @@ -68,8 +71,8 @@ static bool publish_device_ip_addresses(private_tnc_ifmap_listener_t *this) */ static bool reload_metadata(private_tnc_ifmap_listener_t *this) { - enumerator_t *enumerator; ike_sa_t *ike_sa; + enumerator_t *enumerator; bool success = TRUE; enumerator = charon->controller->create_ike_sa_enumerator( @@ -80,14 +83,15 @@ static bool reload_metadata(private_tnc_ifmap_listener_t *this) { continue; } - if (!this->ifmap->publish_ike_sa(this->ifmap, ike_sa, TRUE)) + if (!this->ifmap->publish_ike_sa(this->ifmap, ike_sa, TRUE) || + !this->ifmap->publish_virtual_ips(this->ifmap, ike_sa, TRUE)) { success = FALSE; break; } } enumerator->destroy(enumerator); - + return success; } @@ -101,6 +105,13 @@ METHOD(listener_t, ike_updown, bool, return TRUE; } +METHOD(listener_t, assign_vips, bool, + private_tnc_ifmap_listener_t *this, ike_sa_t *ike_sa, bool assign) +{ + this->ifmap->publish_virtual_ips(this->ifmap, ike_sa, assign); + return TRUE; +} + METHOD(listener_t, alert, bool, private_tnc_ifmap_listener_t *this, ike_sa_t *ike_sa, alert_t alert, va_list args) @@ -117,7 +128,14 @@ METHOD(listener_t, alert, bool, METHOD(tnc_ifmap_listener_t, destroy, void, private_tnc_ifmap_listener_t *this) { - DESTROY_IF(this->ifmap); + if (this->ifmap) + { + if (this->ifmap->get_session_id(this->ifmap)) + { + this->ifmap->endSession(this->ifmap); + } + this->ifmap->destroy(this->ifmap); + } free(this); } @@ -127,11 +145,14 @@ METHOD(tnc_ifmap_listener_t, destroy, void, tnc_ifmap_listener_t *tnc_ifmap_listener_create(bool reload) { private_tnc_ifmap_listener_t *this; + job_t *job; + u_int32_t reschedule; INIT(this, .public = { .listener = { .ike_updown = _ike_updown, + .assign_vips = _assign_vips, .alert = _alert, }, .destroy = _destroy, @@ -168,6 +189,15 @@ tnc_ifmap_listener_t *tnc_ifmap_listener_create(bool reload) } } + /* schedule periodic transmission of IF-MAP renewSession request */ + reschedule = lib->settings->get_int(lib->settings, + "%s.plugins.tnc-ifmap.renew_session_interval", + IFMAP_RENEW_SESSION_INTERVAL, charon->name); + + job = (job_t*)tnc_ifmap_renew_session_job_create( + this->ifmap->get_ref(this->ifmap), reschedule); + lib->scheduler->schedule_job(lib->scheduler, job, reschedule); + return &this->public; } diff --git a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_listener.h b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_listener.h index 878505b38..4ecccf4df 100644 --- a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_listener.h +++ b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_listener.h @@ -1,5 +1,5 @@ /* - * Copyright (C) 2011 Andreas Steffen + * Copyright (C) 2011-2013 Andreas Steffen * HSR Hochschule fuer Technik Rapperswil * * This program is free software; you can redistribute it and/or modify it diff --git a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_plugin.c b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_plugin.c index de4d12e0b..85ad49bd8 100644 --- a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_plugin.c +++ b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_plugin.c @@ -1,5 +1,5 @@ /* - * Copyright (C) 2011 Andreas Steffen + * Copyright (C) 2011-2013 Andreas Steffen * HSR Hochschule fuer Technik Rapperswil * * This program is free software; you can redistribute it and/or modify it @@ -42,6 +42,46 @@ METHOD(plugin_t, get_name, char*, return "tnc-ifmap"; } +/** + * Register tnc_ifmap plugin features + */ +static bool register_tnc_ifmap(private_tnc_ifmap_plugin_t *this, + plugin_feature_t *feature, bool reg, void *data) +{ + if (reg) + { + this->listener = tnc_ifmap_listener_create(FALSE); + if (!this->listener) + { + return FALSE; + } + charon->bus->add_listener(charon->bus, &this->listener->listener); + } + else + { + if (this->listener) + { + charon->bus->remove_listener(charon->bus, &this->listener->listener); + this->listener->destroy(this->listener); + } + } + return TRUE; +} + +METHOD(plugin_t, get_features, int, + tnc_ifmap_plugin_t *this, plugin_feature_t *features[]) +{ + static plugin_feature_t f[] = { + PLUGIN_CALLBACK((plugin_feature_callback_t)register_tnc_ifmap, NULL), + PLUGIN_PROVIDE(CUSTOM, "tnc-ifmap-2.1"), + PLUGIN_SDEPEND(CERT_DECODE, CERT_X509), + PLUGIN_SDEPEND(PRIVKEY, KEY_RSA), + PLUGIN_SDEPEND(CUSTOM, "stroke"), + }; + *features = f; + return countof(f); +} + METHOD(plugin_t, reload, bool, private_tnc_ifmap_plugin_t *this) { @@ -56,19 +96,14 @@ METHOD(plugin_t, reload, bool, { return FALSE; } - charon->bus->add_listener(charon->bus, &this->listener->listener); + return TRUE; } METHOD(plugin_t, destroy, void, private_tnc_ifmap_plugin_t *this) { - if (this->listener) - { - charon->bus->remove_listener(charon->bus, &this->listener->listener); - this->listener->destroy(this->listener); - } free(this); } @@ -83,17 +118,13 @@ plugin_t *tnc_ifmap_plugin_create() .public = { .plugin = { .get_name = _get_name, + .get_features = _get_features, .reload = _reload, .destroy = _destroy, }, }, - .listener = tnc_ifmap_listener_create(FALSE), ); - if (this->listener) - { - charon->bus->add_listener(charon->bus, &this->listener->listener); - } return &this->public.plugin; } diff --git a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_plugin.h b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_plugin.h index 8172be7c9..d3bba7f9c 100644 --- a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_plugin.h +++ b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_plugin.h @@ -1,5 +1,5 @@ /* - * Copyright (C) 2011 Andreas Steffen + * Copyright (C) 2011-2013 Andreas Steffen * HSR Hochschule fuer Technik Rapperswil * * This program is free software; you can redistribute it and/or modify it diff --git a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_renew_session_job.c b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_renew_session_job.c new file mode 100644 index 000000000..f2c00a528 --- /dev/null +++ b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_renew_session_job.c @@ -0,0 +1,103 @@ +/* + * Copyright (C) 2013 Andreas Steffen + * HSR 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 <http://www.fsf.org/copyleft/gpl.txt>. + * + * 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 <stdlib.h> + +#include "tnc_ifmap_renew_session_job.h" + +#include <daemon.h> + + +typedef struct private_tnc_ifmap_renew_session_job_t private_tnc_ifmap_renew_session_job_t; + +/** + * Private data + */ +struct private_tnc_ifmap_renew_session_job_t { + + /** + * public tnc_ifmap_renew_session_job_t interface + */ + tnc_ifmap_renew_session_job_t public; + + /** + * TNC IF-MAP 2.0 SOAP interface + */ + tnc_ifmap_soap_t *ifmap; + + /** + * Reschedule time interval in seconds + */ + u_int32_t reschedule; +}; + +METHOD(job_t, destroy, void, + private_tnc_ifmap_renew_session_job_t *this) +{ + this->ifmap->destroy(this->ifmap); + free(this); +} + +METHOD(job_t, execute, job_requeue_t, + private_tnc_ifmap_renew_session_job_t *this) +{ + char *session_id; + + if (this->ifmap->orphaned(this->ifmap)) + { + session_id = this->ifmap->get_session_id(this->ifmap); + DBG2(DBG_TNC, "removing orphaned ifmap renewSession job for '%s'", + session_id); + return JOB_REQUEUE_NONE; + } + else + { + if (!this->ifmap->renewSession(this->ifmap)) + { + DBG1(DBG_TNC, "sending ifmap renewSession failed"); + /* TODO take some action */ + } + return JOB_RESCHEDULE(this->reschedule); + } +} + +METHOD(job_t, get_priority, job_priority_t, + private_tnc_ifmap_renew_session_job_t *this) +{ + return JOB_PRIO_MEDIUM; +} + +/* + * Described in header + */ +tnc_ifmap_renew_session_job_t *tnc_ifmap_renew_session_job_create( + tnc_ifmap_soap_t *ifmap, u_int32_t reschedule) +{ + private_tnc_ifmap_renew_session_job_t *this; + + INIT(this, + .public = { + .job_interface = { + .execute = _execute, + .get_priority = _get_priority, + .destroy = _destroy, + }, + }, + .ifmap = ifmap, + .reschedule = reschedule, + ); + + return &this->public; +} diff --git a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_renew_session_job.h b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_renew_session_job.h new file mode 100644 index 000000000..91e8fe404 --- /dev/null +++ b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_renew_session_job.h @@ -0,0 +1,51 @@ +/* + * Copyright (C) 2013 Andreas Steffen + * HSR 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 <http://www.fsf.org/copyleft/gpl.txt>. + * + * 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. + */ + +/** + * @defgroup tnc_ifmap_renew_session_job tnc_ifmap_renew_session_job + * @{ @ingroup cjobs + */ + +#ifndef TNC_IFMAP_RENEW_SESSION_JOB_H_ +#define TNC_IFMAP_RENEW_SESSION_JOB_H_ + +typedef struct tnc_ifmap_renew_session_job_t tnc_ifmap_renew_session_job_t; + +#include "tnc_ifmap_soap.h" + +#include <library.h> +#include <processing/jobs/job.h> + +/** + * Job periodically sending an IF-MAP RenewSession request. + */ +struct tnc_ifmap_renew_session_job_t { + + /** + * implements job_t interface + */ + job_t job_interface; +}; + +/** + * Creates an tnc_ifmap_renew_session job. + * + * @param ifmap TNC IF-MAP object + * @param reschedule reschedule time in seconds + */ +tnc_ifmap_renew_session_job_t *tnc_ifmap_renew_session_job_create( + tnc_ifmap_soap_t *ifmap, u_int32_t reschedule); + +#endif /** TNC_IFMAP_RENEW_SESSION_JOB_H_ @}*/ diff --git a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap.c b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap.c index 913cdab12..df7d2e2a1 100644 --- a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap.c +++ b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap.c @@ -1,5 +1,5 @@ /* - * Copyright (C) 2011 Andreas Steffen + * Copyright (C) 2011-2013 Andreas Steffen * HSR Hochschule fuer Technik Rapperswil * * This program is free software; you can redistribute it and/or modify it @@ -14,20 +14,24 @@ */ #include "tnc_ifmap_soap.h" +#include "tnc_ifmap_soap_msg.h" -#include <debug.h> +#include <utils/debug.h> +#include <credentials/sets/mem_cred.h> +#include <daemon.h> -#include <axis2_util.h> -#include <axis2_client.h> -#include <axis2_http_transport.h> -#include <axis2_http_transport_sender.h> -#include <axiom_soap.h> +#include <tls_socket.h> + +#include <errno.h> +#include <unistd.h> +#include <sys/types.h> +#include <sys/socket.h> + +#define IFMAP_NS "http://www.trustedcomputinggroup.org/2010/IFMAP/2" +#define IFMAP_META_NS "http://www.trustedcomputinggroup.org/2010/IFMAP-METADATA/2" +#define IFMAP_URI "https://localhost:8444/imap" +#define IFMAP_NO_FD -1 -#define IFMAP_NS "http://www.trustedcomputinggroup.org/2010/IFMAP/2" -#define IFMAP_META_NS "http://www.trustedcomputinggroup.org/2010/IFMAP-METADATA/2" -#define IFMAP_LOGFILE "strongswan_ifmap.log" -#define IFMAP_SERVER "https://localhost:8443/" - typedef struct private_tnc_ifmap_soap_t private_tnc_ifmap_soap_t; /** @@ -41,169 +45,156 @@ struct private_tnc_ifmap_soap_t { tnc_ifmap_soap_t public; /** - * Axis2/C environment + * SOAP Session ID */ - axutil_env_t *env; + xmlChar *session_id; /** - * Axis2 service client + * IF-MAP Publisher ID */ - axis2_svc_client_t* svc_client; + xmlChar *ifmap_publisher_id; /** - * SOAP Session ID + * IF-MAP namespace */ - char *session_id; + xmlNsPtr ns; /** - * IF-MAP Publisher ID + * IF-MAP metadata namespace */ - char *ifmap_publisher_id; + xmlNsPtr ns_meta; /** * PEP and PDP device name */ char *device_name; -}; - -/** - * Send request and receive result via SOAP - */ -static axiom_element_t* send_receive(private_tnc_ifmap_soap_t *this, - char *request_qname, axiom_node_t *request, - char *receipt_qname, axiom_node_t **result) - -{ - axiom_node_t *parent, *node; - axiom_element_t *parent_el, *el; - axutil_qname_t *qname; + /** + * HTTPS Server URI with https:// prefix removed + */ + char *uri; - /* send request and receive result */ - DBG2(DBG_TNC, "sending ifmap %s", request_qname); + /** + * Optional base64-encoded username:password for HTTP Basic Authentication + */ + chunk_t user_pass; - parent = axis2_svc_client_send_receive(this->svc_client, this->env, request); - if (!parent) - { - DBG1(DBG_TNC, "no ifmap %s received from MAP server", receipt_qname); - return NULL; - } - DBG2(DBG_TNC, "received ifmap %s", receipt_qname); + /** + * IF-MAP Server (IP address and port) + */ + host_t *host; - /* extract the parent element */ - parent_el = (axiom_element_t*)axiom_node_get_data_element(parent, this->env); + /** + * TLS socket + */ + tls_socket_t *tls; - /* look for a child node with the given receipt qname */ - qname = axutil_qname_create_from_string(this->env, strdup(receipt_qname)); - el = axiom_element_get_first_child_with_qname(parent_el, this->env, qname, - parent, &node); - axutil_qname_free(qname, this->env); + /** + * File descriptor for secure TCP socket + */ + int fd; - if (el) - { - if (result) - { - *result = parent; - } - else - { - /* no further processing requested */ - axiom_node_free_tree(parent, this->env); - } - return el; - } - DBG1(DBG_TNC, "child node with qname '%s' not found", receipt_qname); + /** + * In memory credential set + */ + mem_cred_t *creds; - /* free parent in the error case */ - axiom_node_free_tree(parent, this->env); + /** + * reference count + */ + refcount_t ref; - return NULL; -} +}; METHOD(tnc_ifmap_soap_t, newSession, bool, private_tnc_ifmap_soap_t *this) { - axiom_node_t *request, *result; - axiom_element_t *el; - axiom_namespace_t *ns; - axis2_char_t *value; - + tnc_ifmap_soap_msg_t *soap_msg; + xmlNodePtr request, result; - /* build newSession request */ - ns = axiom_namespace_create(this->env, IFMAP_NS, "ifmap"); - el = axiom_element_create(this->env, NULL, "newSession", ns, &request); + /*build newSession request */ + request = xmlNewNode(NULL, "newSession"); + this->ns = xmlNewNs(request, IFMAP_NS, "ifmap"); + xmlSetNs(request, this->ns); - /* send newSession request and receive newSessionResult */ - el = send_receive(this, "newSession", request, "newSessionResult", &result); - if (!el) + soap_msg = tnc_ifmap_soap_msg_create(this->uri, this->user_pass, this->tls); + if (!soap_msg->post(soap_msg, request, "newSessionResult", &result)) { + soap_msg->destroy(soap_msg); return FALSE; } - /* get session-id */ - value = axiom_element_get_attribute_value_by_name(el, this->env, - "session-id"); - this->session_id = strdup(value); + /* get session-id and ifmap-publisher-id properties */ + this->session_id = xmlGetProp(result, "session-id"); + this->ifmap_publisher_id = xmlGetProp(result, "ifmap-publisher-id"); + soap_msg->destroy(soap_msg); - /* get ifmap-publisher-id */ - value = axiom_element_get_attribute_value_by_name(el, this->env, - "ifmap-publisher-id"); - this->ifmap_publisher_id = strdup(value); - - DBG1(DBG_TNC, "session-id: %s, ifmap-publisher-id: %s", + DBG1(DBG_TNC, "created ifmap session '%s' as publisher '%s'", this->session_id, this->ifmap_publisher_id); /* set PEP and PDP device name (defaults to IF-MAP Publisher ID) */ this->device_name = lib->settings->get_str(lib->settings, - "charon.plugins.tnc-ifmap.device_name", - this->ifmap_publisher_id); + "%s.plugins.tnc-ifmap.device_name", + this->ifmap_publisher_id, charon->name); this->device_name = strdup(this->device_name); - /* free result */ - axiom_node_free_tree(result, this->env); - return this->session_id && this->ifmap_publisher_id; } +METHOD(tnc_ifmap_soap_t, renewSession, bool, + private_tnc_ifmap_soap_t *this) +{ + tnc_ifmap_soap_msg_t *soap_msg; + xmlNodePtr request; + bool success; + + /* build renewSession request */ + request = xmlNewNode(NULL, "renewSession"); + this->ns = xmlNewNs(request, IFMAP_NS, "ifmap"); + xmlSetNs(request, this->ns); + xmlNewProp(request, "session-id", this->session_id); + + soap_msg = tnc_ifmap_soap_msg_create(this->uri, this->user_pass, this->tls); + success = soap_msg->post(soap_msg, request, "renewSessionResult", NULL); + soap_msg->destroy(soap_msg); + + return success; +} + METHOD(tnc_ifmap_soap_t, purgePublisher, bool, private_tnc_ifmap_soap_t *this) { - axiom_node_t *request; - axiom_element_t *el; - axiom_namespace_t *ns; - axiom_attribute_t *attr; + tnc_ifmap_soap_msg_t *soap_msg; + xmlNodePtr request; + bool success; /* build purgePublisher request */ - ns = axiom_namespace_create(this->env, IFMAP_NS, "ifmap"); - el = axiom_element_create(this->env, NULL, "purgePublisher", ns, &request); - attr = axiom_attribute_create(this->env, "session-id", - this->session_id, NULL); - axiom_element_add_attribute(el, this->env, attr, request); - attr = axiom_attribute_create(this->env, "ifmap-publisher-id", - this->ifmap_publisher_id, NULL); - axiom_element_add_attribute(el, this->env, attr, request); - - /* send purgePublisher request and receive purgePublisherReceived */ - return send_receive(this, "purgePublisher", request, - "purgePublisherReceived", NULL); + request = xmlNewNode(NULL, "purgePublisher"); + this->ns = xmlNewNs(request, IFMAP_NS, "ifmap"); + xmlSetNs(request, this->ns); + xmlNewProp(request, "session-id", this->session_id); + xmlNewProp(request, "ifmap-publisher-id", this->ifmap_publisher_id); + + soap_msg = tnc_ifmap_soap_msg_create(this->uri, this->user_pass, this->tls); + success = soap_msg->post(soap_msg, request, "purgePublisherReceived", NULL); + soap_msg->destroy(soap_msg); + + return success; } /** * Create an access-request based on device_name and ike_sa_id */ -static axiom_node_t* create_access_request(private_tnc_ifmap_soap_t *this, - u_int32_t id) +static xmlNodePtr create_access_request(private_tnc_ifmap_soap_t *this, + u_int32_t id) { - axiom_element_t *el; - axiom_node_t *node; - axiom_attribute_t *attr; + xmlNodePtr node; char buf[BUF_LEN]; - el = axiom_element_create(this->env, NULL, "access-request", NULL, &node); + node = xmlNewNode(NULL, "access-request"); snprintf(buf, BUF_LEN, "%s:%d", this->device_name, id); - attr = axiom_attribute_create(this->env, "name", buf, NULL); - axiom_element_add_attribute(el, this->env, attr, node); + xmlNewProp(node, "name", buf); return node; } @@ -211,27 +202,22 @@ static axiom_node_t* create_access_request(private_tnc_ifmap_soap_t *this, /** * Create an identity */ -static axiom_node_t* create_identity(private_tnc_ifmap_soap_t *this, - identification_t *id, bool is_user) +static xmlNodePtr create_identity(private_tnc_ifmap_soap_t *this, + identification_t *id, bool is_user) { - axiom_element_t *el; - axiom_node_t *node; - axiom_attribute_t *attr; + xmlNodePtr node; char buf[BUF_LEN], *id_type; - el = axiom_element_create(this->env, NULL, "identity", NULL, &node); + node = xmlNewNode(NULL, "identity"); snprintf(buf, BUF_LEN, "%Y", id); - attr = axiom_attribute_create(this->env, "name", buf, NULL); - axiom_element_add_attribute(el, this->env, attr, node); + xmlNewProp(node, "name", buf); switch (id->get_type(id)) { case ID_IPV4_ADDR: id_type = "other"; - attr = axiom_attribute_create(this->env, "other-type-definition", - "36906:ipv4-address", NULL); - axiom_element_add_attribute(el, this->env, attr, node); + xmlNewProp(node, "other-type-definition", "36906:ipv4-address"); break; case ID_FQDN: id_type = is_user ? "username" : "dns-name"; @@ -241,27 +227,93 @@ static axiom_node_t* create_identity(private_tnc_ifmap_soap_t *this, break; case ID_IPV6_ADDR: id_type = "other"; - attr = axiom_attribute_create(this->env, "other-type-definition", - "36906:ipv6-address", NULL); - axiom_element_add_attribute(el, this->env, attr, node); + xmlNewProp(node, "other-type-definition", "36906:ipv6-address"); break; case ID_DER_ASN1_DN: id_type = "distinguished-name"; break; case ID_KEY_ID: id_type = "other"; - attr = axiom_attribute_create(this->env, "other-type-definition", - "36906:key-id", NULL); - axiom_element_add_attribute(el, this->env, attr, node); + xmlNewProp(node, "other-type-definition", "36906:key-id"); break; default: id_type = "other"; - attr = axiom_attribute_create(this->env, "other-type-definition", - "36906:other", NULL); - axiom_element_add_attribute(el, this->env, attr, node); + xmlNewProp(node, "other-type-definition", "36906:other"); } - attr = axiom_attribute_create(this->env, "type", id_type, NULL); - axiom_element_add_attribute(el, this->env, attr, node); + xmlNewProp(node, "type", id_type); + + return node; +} + +/** + * Create enforcement-report metadata + */ +static xmlNodePtr create_enforcement_report(private_tnc_ifmap_soap_t *this, + xmlChar *action, xmlChar *reason) +{ + xmlNodePtr node, node2, node3; + + node = xmlNewNode(NULL, "metadata"); + node2 = xmlNewNode(this->ns_meta, "enforcement-report"); + xmlAddChild(node, node2); + xmlNewProp(node2, "ifmap-cardinality", "multiValue"); + + node3 = xmlNewNode(NULL, "enforcement-action"); + xmlAddChild(node2, node3); + xmlNodeAddContent(node3, action); + + node3 = xmlNewNode(NULL, "enforcement-reason"); + xmlAddChild(node2, node3); + xmlNodeAddContent(node3, reason); + + return node; +} + +/** + * Create delete filter + */ +static xmlNodePtr create_delete_filter(private_tnc_ifmap_soap_t *this, + char *metadata) +{ + xmlNodePtr node; + char buf[BUF_LEN]; + + node = xmlNewNode(NULL, "delete"); + + snprintf(buf, BUF_LEN, "meta:%s[@ifmap-publisher-id='%s']", + metadata, this->ifmap_publisher_id); + xmlNewProp(node, "filter", buf); + + return node; +} + +/** + * Create a publish request + */ +static xmlNodePtr create_publish_request(private_tnc_ifmap_soap_t *this) +{ + xmlNodePtr request; + + request = xmlNewNode(NULL, "publish"); + this->ns = xmlNewNs(request, IFMAP_NS, "ifmap"); + xmlSetNs(request, this->ns); + this->ns_meta = xmlNewNs(request, IFMAP_META_NS, "meta"); + xmlNewProp(request, "session-id", this->session_id); + + return request; +} + +/** + * Create a device + */ +static xmlNodePtr create_device(private_tnc_ifmap_soap_t *this) +{ + xmlNodePtr node, node2; + + node = xmlNewNode(NULL, "device"); + node2 = xmlNewNode(NULL, "name"); + xmlAddChild(node, node2); + xmlNodeAddContent(node2, this->device_name); return node; } @@ -269,15 +321,13 @@ static axiom_node_t* create_identity(private_tnc_ifmap_soap_t *this, /** * Create an ip-address */ -static axiom_node_t* create_ip_address(private_tnc_ifmap_soap_t *this, - host_t *host) +static xmlNodePtr create_ip_address(private_tnc_ifmap_soap_t *this, + host_t *host) { - axiom_element_t *el; - axiom_node_t *node; - axiom_attribute_t *attr; + xmlNodePtr node; char buf[BUF_LEN]; - el = axiom_element_create(this->env, NULL, "ip-address", NULL, &node); + node = xmlNewNode(NULL, "ip-address"); if (host->get_family(host) == AF_INET6) { @@ -295,7 +345,7 @@ static axiom_node_t* create_ip_address(private_tnc_ifmap_soap_t *this, { written = snprintf(pos, len, "%s%x", first ? "" : ":", 256*address.ptr[i] + address.ptr[i+1]); - if (written < 0 || written > len) + if (written < 0 || written >= len) { break; } @@ -308,29 +358,9 @@ static axiom_node_t* create_ip_address(private_tnc_ifmap_soap_t *this, { snprintf(buf, BUF_LEN, "%H", host); } - attr = axiom_attribute_create(this->env, "value", buf, NULL); - axiom_element_add_attribute(el, this->env, attr, node); - attr = axiom_attribute_create(this->env, "type", - host->get_family(host) == AF_INET ? "IPv4" : "IPv6", NULL); - axiom_element_add_attribute(el, this->env, attr, node); - - return node; -} - -/** - * Create a device - */ -static axiom_node_t* create_device(private_tnc_ifmap_soap_t *this) -{ - axiom_element_t *el; - axiom_node_t *node, *node2, *node3; - axiom_text_t *text; - - el = axiom_element_create(this->env, NULL, "device", NULL, &node); - el = axiom_element_create(this->env, NULL, "name", NULL, &node2); - axiom_node_add_child(node, this->env, node2); - text = axiom_text_create(this->env, node2, this->device_name, &node3); + xmlNewProp(node, "value", buf); + xmlNewProp(node, "type", host->get_family(host) == AF_INET ? "IPv4" : "IPv6"); return node; } @@ -338,22 +368,15 @@ static axiom_node_t* create_device(private_tnc_ifmap_soap_t *this) /** * Create metadata */ -static axiom_node_t* create_metadata(private_tnc_ifmap_soap_t *this, - char *metadata) +static xmlNodePtr create_metadata(private_tnc_ifmap_soap_t *this, + xmlChar *metadata) { - axiom_element_t *el; - axiom_node_t *node, *node2; - axiom_attribute_t *attr; - axiom_namespace_t *ns_meta; + xmlNodePtr node, node2; - el = axiom_element_create(this->env, NULL, "metadata", NULL, &node); - ns_meta = axiom_namespace_create(this->env, IFMAP_META_NS, "meta"); - - el = axiom_element_create(this->env, NULL, metadata, ns_meta, &node2); - axiom_node_add_child(node, this->env, node2); - attr = axiom_attribute_create(this->env, "ifmap-cardinality", "singleValue", - NULL); - axiom_element_add_attribute(el, this->env, attr, node2); + node = xmlNewNode(NULL, "metadata"); + node2 = xmlNewNode(this->ns_meta, metadata); + xmlAddChild(node, node2); + xmlNewProp(node2, "ifmap-cardinality", "singleValue"); return node; } @@ -361,130 +384,45 @@ static axiom_node_t* create_metadata(private_tnc_ifmap_soap_t *this, /** * Create capability metadata */ -static axiom_node_t* create_capability(private_tnc_ifmap_soap_t *this, - identification_t *name) +static xmlNodePtr create_capability(private_tnc_ifmap_soap_t *this, + identification_t *name) { - axiom_element_t *el; - axiom_node_t *node, *node2, *node3; - axiom_namespace_t *ns_meta; - axiom_attribute_t *attr; - axiom_text_t *text; + xmlNodePtr node, node2; char buf[BUF_LEN]; - ns_meta = axiom_namespace_create(this->env, IFMAP_META_NS, "meta"); - el = axiom_element_create(this->env, NULL, "capability", ns_meta, &node); - attr = axiom_attribute_create(this->env, "ifmap-cardinality", "multiValue", - NULL); - axiom_element_add_attribute(el, this->env, attr, node); + node = xmlNewNode(this->ns_meta, "capability"); + xmlNewProp(node, "ifmap-cardinality", "multiValue"); - el = axiom_element_create(this->env, NULL, "name", NULL, &node2); - axiom_node_add_child(node, this->env, node2); + node2 = xmlNewNode(NULL, "name"); + xmlAddChild(node, node2); snprintf(buf, BUF_LEN, "%Y", name); - text = axiom_text_create(this->env, node2, buf, &node3); + xmlNodeAddContent(node2, buf); - el = axiom_element_create(this->env, NULL, "administrative-domain", NULL, &node2); - axiom_node_add_child(node, this->env, node2); - text = axiom_text_create(this->env, node2, "strongswan", &node3); - - return node; -} - -/** - * Create enforcement-report metadata - */ -static axiom_node_t* create_enforcement_report(private_tnc_ifmap_soap_t *this, - char *action, char *reason) -{ - axiom_element_t *el; - axiom_node_t *node, *node2, *node3, *node4; - axiom_namespace_t *ns_meta; - axiom_attribute_t *attr; - axiom_text_t *text; - - el = axiom_element_create(this->env, NULL, "metadata", NULL, &node); - - ns_meta = axiom_namespace_create(this->env, IFMAP_META_NS, "meta"); - el = axiom_element_create(this->env, NULL, "enforcement-report", ns_meta, - &node2); - attr = axiom_attribute_create(this->env, "ifmap-cardinality", - "multiValue", NULL); - axiom_element_add_attribute(el, this->env, attr, node2); - axiom_node_add_child(node, this->env, node2); - - el = axiom_element_create(this->env, NULL, "enforcement-action", NULL, - &node3); - axiom_node_add_child(node2, this->env, node3); - text = axiom_text_create(this->env, node3, action, &node4); - - el = axiom_element_create(this->env, NULL, "enforcement-reason", NULL, - &node3); - axiom_node_add_child(node2, this->env, node3); - text = axiom_text_create(this->env, node3, reason, &node4); - - return node; -} - -/** - * Create delete filter - */ -static axiom_node_t* create_delete_filter(private_tnc_ifmap_soap_t *this, - char *metadata) -{ - axiom_element_t *el; - axiom_node_t *node; - axiom_attribute_t *attr; - char buf[BUF_LEN]; - - el = axiom_element_create(this->env, NULL, "delete", NULL, &node); - - snprintf(buf, BUF_LEN, "meta:%s[@ifmap-publisher-id='%s']", - metadata, this->ifmap_publisher_id); - attr = axiom_attribute_create(this->env, "filter", buf, NULL); - axiom_element_add_attribute(el, this->env, attr, node); + node2 = xmlNewNode(NULL, "administrative-domain"); + xmlAddChild(node, node2); + xmlNodeAddContent(node2, "strongswan"); return node; } -/** - * Create a publish request - */ -static axiom_node_t* create_publish_request(private_tnc_ifmap_soap_t *this) -{ - axiom_element_t *el; - axiom_node_t *request; - axiom_namespace_t *ns, *ns_meta; - axiom_attribute_t *attr; - - ns = axiom_namespace_create(this->env, IFMAP_NS, "ifmap"); - el = axiom_element_create(this->env, NULL, "publish", ns, &request); - ns_meta = axiom_namespace_create(this->env, IFMAP_META_NS, "meta"); - axiom_element_declare_namespace(el, this->env, request, ns_meta); - attr = axiom_attribute_create(this->env, "session-id", this->session_id, - NULL); - axiom_element_add_attribute(el, this->env, attr, request); - - return request; -} - METHOD(tnc_ifmap_soap_t, publish_ike_sa, bool, private_tnc_ifmap_soap_t *this, ike_sa_t *ike_sa, bool up) { - axiom_node_t *request, *node, *node2; - axiom_element_t *el; - + tnc_ifmap_soap_msg_t *soap_msg; + xmlNodePtr request, node, node2 = NULL; enumerator_t *e1, *e2; auth_rule_t type; identification_t *id, *eap_id, *group; host_t *host; auth_cfg_t *auth; u_int32_t ike_sa_id; - bool is_user = FALSE, first = TRUE; + bool is_user = FALSE, first = TRUE, success; /* extract relevant data from IKE_SA*/ ike_sa_id = ike_sa->get_unique_id(ike_sa); + host = ike_sa->get_other_host(ike_sa); id = ike_sa->get_other_id(ike_sa); eap_id = ike_sa->get_other_eap_id(ike_sa); - host = ike_sa->get_other_host(ike_sa); /* in the presence of an EAP Identity, treat it as a username */ if (!id->equals(id, eap_id)) @@ -500,90 +438,79 @@ METHOD(tnc_ifmap_soap_t, publish_ike_sa, bool, if (up) { node = create_delete_filter(this, "enforcement-report"); - axiom_node_add_child(request, this->env, node); - axiom_node_add_child(node, this->env, - create_ip_address(this, host)); - axiom_node_add_child(node, this->env, - create_device(this)); + xmlAddChild(request, node); + xmlAddChild(node, create_ip_address(this, host)); + xmlAddChild(node, create_device(this)); } - + /** * update or delete authenticated-as metadata */ - if (up) + if (up) { - el = axiom_element_create(this->env, NULL, "update", NULL, &node); + node = xmlNewNode(NULL, "update"); } else { node = create_delete_filter(this, "authenticated-as"); } - axiom_node_add_child(request, this->env, node); + xmlAddChild(request, node); /* add access-request, identity and [if up] metadata */ - axiom_node_add_child(node, this->env, - create_access_request(this, ike_sa_id)); - axiom_node_add_child(node, this->env, - create_identity(this, id, is_user)); + xmlAddChild(node, create_access_request(this, ike_sa_id)); + xmlAddChild(node, create_identity(this, id, is_user)); if (up) { - axiom_node_add_child(node, this->env, - create_metadata(this, "authenticated-as")); + xmlAddChild(node, create_metadata(this, "authenticated-as")); } /** - * update or delete access-request-ip metadata + * update or delete access-request-ip metadata for physical IP address */ - if (up) + if (up) { - el = axiom_element_create(this->env, NULL, "update", NULL, &node); + node = xmlNewNode(NULL, "update"); } else { node = create_delete_filter(this, "access-request-ip"); } - axiom_node_add_child(request, this->env, node); + xmlAddChild(request, node); /* add access-request, ip-address and [if up] metadata */ - axiom_node_add_child(node, this->env, - create_access_request(this, ike_sa_id)); - axiom_node_add_child(node, this->env, - create_ip_address(this, host)); + xmlAddChild(node, create_access_request(this, ike_sa_id)); + xmlAddChild(node, create_ip_address(this, host)); if (up) { - axiom_node_add_child(node, this->env, - create_metadata(this, "access-request-ip")); + xmlAddChild(node, create_metadata(this, "access-request-ip")); } /** * update or delete authenticated-by metadata */ - if (up) + if (up) { - el = axiom_element_create(this->env, NULL, "update", NULL, &node); + node = xmlNewNode(NULL, "update"); } else { node = create_delete_filter(this, "authenticated-by"); } - axiom_node_add_child(request, this->env, node); + xmlAddChild(request, node); /* add access-request, device and [if up] metadata */ - axiom_node_add_child(node, this->env, - create_access_request(this, ike_sa_id)); - axiom_node_add_child(node, this->env, - create_device(this)); + xmlAddChild(node, create_access_request(this, ike_sa_id)); + xmlAddChild(node, create_device(this)); if (up) { - axiom_node_add_child(node, this->env, - create_metadata(this, "authenticated-by")); + xmlAddChild(node, create_metadata(this, "authenticated-by")); } /** * update or delete capability metadata */ e1 = ike_sa->create_auth_cfg_enumerator(ike_sa, FALSE); - while (e1->enumerate(e1, &auth)) + while (e1->enumerate(e1, &auth) && (first || up)) { e2 = auth->create_enumerator(auth); while (e2->enumerate(e2, &type, &group)) @@ -597,234 +524,364 @@ METHOD(tnc_ifmap_soap_t, publish_ike_sa, bool, if (up) { - el = axiom_element_create(this->env, NULL, "update", - NULL, &node); + node = xmlNewNode(NULL, "update"); } else { node = create_delete_filter(this, "capability"); } - axiom_node_add_child(request, this->env, node); - + xmlAddChild(request, node); + /* add access-request */ - axiom_node_add_child(node, this->env, - create_access_request(this, ike_sa_id)); + xmlAddChild(node, create_access_request(this, ike_sa_id)); if (!up) { break; } - el = axiom_element_create(this->env, NULL, "metadata", NULL, - &node2); - axiom_node_add_child(node, this->env, node2); + node2 = xmlNewNode(NULL, "metadata"); + xmlAddChild(node, node2); } - axiom_node_add_child(node2, this->env, - create_capability(this, group)); - } - if (!first && !up) - { - break; + xmlAddChild(node2, create_capability(this, group)); } } e2->destroy(e2); } e1->destroy(e1); - /* send publish request and receive publishReceived */ - return send_receive(this, "publish", request, "publishReceived", NULL); + soap_msg = tnc_ifmap_soap_msg_create(this->uri, this->user_pass, this->tls); + success = soap_msg->post(soap_msg, request, "publishReceived", NULL); + soap_msg->destroy(soap_msg); + + return success; } METHOD(tnc_ifmap_soap_t, publish_device_ip, bool, private_tnc_ifmap_soap_t *this, host_t *host) { - axiom_node_t *request, *node; - axiom_element_t *el; + tnc_ifmap_soap_msg_t *soap_msg; + xmlNodePtr request, update; + bool success; /* build publish update request */ request = create_publish_request(this); - el = axiom_element_create(this->env, NULL, "update", NULL, &node); - axiom_node_add_child(request, this->env, node); + update = xmlNewNode(NULL, "update"); + xmlAddChild(request, update); /* add device, ip-address and metadata */ - axiom_node_add_child(node, this->env, - create_device(this)); - axiom_node_add_child(node, this->env, - create_ip_address(this, host)); - axiom_node_add_child(node, this->env, - create_metadata(this, "device-ip")); - - /* send publish request and receive publishReceived */ - return send_receive(this, "publish", request, "publishReceived", NULL); + xmlAddChild(update, create_device(this)); + xmlAddChild(update, create_ip_address(this, host)); + xmlAddChild(update, create_metadata(this, "device-ip")); + + soap_msg = tnc_ifmap_soap_msg_create(this->uri, this->user_pass, this->tls); + success = soap_msg->post(soap_msg, request, "publishReceived", NULL); + soap_msg->destroy(soap_msg); + + return success; +} + +METHOD(tnc_ifmap_soap_t, publish_virtual_ips, bool, + private_tnc_ifmap_soap_t *this, ike_sa_t *ike_sa, bool assign) +{ + tnc_ifmap_soap_msg_t *soap_msg; + xmlNodePtr request, node; + u_int32_t ike_sa_id; + enumerator_t *enumerator; + host_t *vip; + bool success; + + /* extract relevant data from IKE_SA*/ + ike_sa_id = ike_sa->get_unique_id(ike_sa); + + /* build publish request */ + request = create_publish_request(this); + + enumerator = ike_sa->create_virtual_ip_enumerator(ike_sa, FALSE); + while (enumerator->enumerate(enumerator, &vip)) + { + /** + * update or delete access-request-ip metadata for a virtual IP address + */ + if (assign) + { + node = xmlNewNode(NULL, "update"); + } + else + { + node = create_delete_filter(this, "access-request-ip"); + } + xmlAddChild(request, node); + + /* add access-request, virtual ip-address and [if assign] metadata */ + xmlAddChild(node, create_access_request(this, ike_sa_id)); + xmlAddChild(node, create_ip_address(this, vip)); + if (assign) + { + xmlAddChild(node, create_metadata(this, "access-request-ip")); + } + } + enumerator->destroy(enumerator); + + soap_msg = tnc_ifmap_soap_msg_create(this->uri, this->user_pass, this->tls); + success = soap_msg->post(soap_msg, request, "publishReceived", NULL); + soap_msg->destroy(soap_msg); + + return success; } METHOD(tnc_ifmap_soap_t, publish_enforcement_report, bool, private_tnc_ifmap_soap_t *this, host_t *host, char *action, char *reason) { - axiom_node_t *request, *node; - axiom_element_t *el; + tnc_ifmap_soap_msg_t *soap_msg; + xmlNodePtr request, update; + bool success; /* build publish update request */ request = create_publish_request(this); - el = axiom_element_create(this->env, NULL, "update", NULL, &node); - axiom_node_add_child(request, this->env, node); + update = xmlNewNode(NULL, "update"); + xmlAddChild(request, update); /* add ip-address and metadata */ - axiom_node_add_child(node, this->env, - create_ip_address(this, host)); - axiom_node_add_child(node, this->env, - create_device(this)); - axiom_node_add_child(node, this->env, - create_enforcement_report(this, action, reason)); - - /* send publish request and receive publishReceived */ - return send_receive(this, "publish", request, "publishReceived", NULL); + xmlAddChild(update, create_ip_address(this, host)); + xmlAddChild(update, create_device(this)); + xmlAddChild(update, create_enforcement_report(this, action, reason)); + + soap_msg = tnc_ifmap_soap_msg_create(this->uri, this->user_pass, this->tls); + success = soap_msg->post(soap_msg, request, "publishReceived", NULL); + soap_msg->destroy(soap_msg); + + return success; } METHOD(tnc_ifmap_soap_t, endSession, bool, private_tnc_ifmap_soap_t *this) { - axiom_node_t *request; - axiom_element_t *el; - axiom_namespace_t *ns; - axiom_attribute_t *attr; + tnc_ifmap_soap_msg_t *soap_msg; + xmlNodePtr request; + bool success; /* build endSession request */ - ns = axiom_namespace_create(this->env, IFMAP_NS, "ifmap"); - el = axiom_element_create(this->env, NULL, "endSession", ns, &request); - attr = axiom_attribute_create(this->env, "session-id", this->session_id, NULL); - axiom_element_add_attribute(el, this->env, attr, request); + request = xmlNewNode(NULL, "endSession"); + this->ns = xmlNewNs(request, IFMAP_NS, "ifmap"); + xmlSetNs(request, this->ns); + xmlNewProp(request, "session-id", this->session_id); + + soap_msg = tnc_ifmap_soap_msg_create(this->uri, this->user_pass, this->tls); + success = soap_msg->post(soap_msg, request, "endSessionResult", NULL); + soap_msg->destroy(soap_msg); + + DBG1(DBG_TNC, "ended ifmap session '%s' as publisher '%s'", + this->session_id, this->ifmap_publisher_id); + + return success; +} + +METHOD(tnc_ifmap_soap_t, get_session_id, char*, + private_tnc_ifmap_soap_t *this) +{ + return this->session_id; +} + +METHOD(tnc_ifmap_soap_t, orphaned, bool, + private_tnc_ifmap_soap_t *this) +{ + return this->ref == 1; +} - /* send endSession request and receive end SessionResult */ - return send_receive(this, "endSession", request, "endSessionResult", NULL); +METHOD(tnc_ifmap_soap_t, get_ref, tnc_ifmap_soap_t*, + private_tnc_ifmap_soap_t *this) +{ + ref_get(&this->ref); + return &this->public; } METHOD(tnc_ifmap_soap_t, destroy, void, private_tnc_ifmap_soap_t *this) { - if (this->session_id) + if (ref_put(&this->ref)) { - endSession(this); - free(this->session_id); - free(this->ifmap_publisher_id); - free(this->device_name); - } - if (this->svc_client) - { - axis2_svc_client_free(this->svc_client, this->env); - } - if (this->env) - { - axutil_env_free(this->env); + if (this->session_id) + { + xmlFree(this->session_id); + xmlFree(this->ifmap_publisher_id); + free(this->device_name); + } + DESTROY_IF(this->tls); + DESTROY_IF(this->host); + + if (this->fd != IFMAP_NO_FD) + { + close(this->fd); + } + lib->credmgr->remove_set(lib->credmgr, &this->creds->set); + this->creds->destroy(this->creds); + free(this->user_pass.ptr); + free(this); } - free(this); } -static bool axis2c_init(private_tnc_ifmap_soap_t *this) +static bool soap_init(private_tnc_ifmap_soap_t *this) { - axis2_char_t *server, *server_cert, *key_file, *client_home; - axis2_char_t *ssl_passphrase, *username, *password; - axis2_endpoint_ref_t* endpoint_ref = NULL; - axis2_options_t *options = NULL; - axis2_transport_in_desc_t *transport_in; - axis2_transport_out_desc_t *transport_out; - axis2_transport_sender_t *transport_sender; - axutil_property_t* property; - - /* Getting configuration parameters from strongswan.conf */ - client_home = lib->settings->get_str(lib->settings, - "charon.plugins.tnc-ifmap.client_home", - AXIS2_GETENV("AXIS2C_HOME")); - server = lib->settings->get_str(lib->settings, - "charon.plugins.tnc-ifmap.server", IFMAP_SERVER); - server_cert = lib->settings->get_str(lib->settings, - "charon.plugins.tnc-ifmap.server_cert", NULL); - key_file = lib->settings->get_str(lib->settings, - "charon.plugins.tnc-ifmap.key_file", NULL); - ssl_passphrase = lib->settings->get_str(lib->settings, - "charon.plugins.tnc-ifmap.ssl_passphrase", NULL); - username = lib->settings->get_str(lib->settings, - "charon.plugins.tnc-ifmap.username", NULL); - password = lib->settings->get_str(lib->settings, - "charon.plugins.tnc-ifmap.password", NULL); + char *server_uri, *server_str, *port_str, *uri_str; + char *server_cert, *client_cert, *client_key, *user_pass; + int port; + auth_cfg_t *auth; + certificate_t *cert; + private_key_t *key; + identification_t *server_id, *client_id = NULL; + /* getting configuration parameters from strongswan.conf */ + server_uri = lib->settings->get_str(lib->settings, + "%s.plugins.tnc-ifmap.server_uri", IFMAP_URI, charon->name); + server_cert = lib->settings->get_str(lib->settings, + "%s.plugins.tnc-ifmap.server_cert", NULL, charon->name); + client_cert = lib->settings->get_str(lib->settings, + "%s.plugins.tnc-ifmap.client_cert", NULL, charon->name); + client_key = lib->settings->get_str(lib->settings, + "%s.plugins.tnc-ifmap.client_key", NULL, charon->name); + user_pass = lib->settings->get_str(lib->settings, + "%s.plugins.tnc-ifmap.username_password", NULL, charon->name); + + /* load [self-signed] MAP server certificate */ if (!server_cert) { DBG1(DBG_TNC, "MAP server certificate not defined"); return FALSE; } + cert = lib->creds->create(lib->creds, CRED_CERTIFICATE, CERT_X509, + BUILD_FROM_FILE, server_cert, BUILD_END); + if (!cert) + { + DBG1(DBG_TNC, "loading MAP server certificate from '%s' failed", + server_cert); + return FALSE; + } + DBG1(DBG_TNC, "loaded MAP server certificate from '%s'", server_cert); + server_id = cert->get_subject(cert); + this->creds->add_cert(this->creds, TRUE, cert); - if (!key_file && (!username || !password)) + /* check availability of client credentials */ + if (!client_cert && !user_pass) { - DBG1(DBG_TNC, "MAP client keyfile or %s%s%s not defined", - (!username) ? "username" : "", - (!username && ! password) ? " and " : "", - (!password) ? "password" : ""); + DBG1(DBG_TNC, "neither MAP client certificate " + "nor username:password defined"); return FALSE; } - /* Create Axis2/C environment and options */ - this->env = axutil_env_create_all(IFMAP_LOGFILE, AXIS2_LOG_LEVEL_TRACE); - options = axis2_options_create(this->env); + if (client_cert) + { + /* load MAP client certificate */ + cert = lib->creds->create(lib->creds, CRED_CERTIFICATE, CERT_X509, + BUILD_FROM_FILE, client_cert, BUILD_END); + if (!cert) + { + DBG1(DBG_TNC, "loading MAP client certificate from '%s' failed", + client_cert); + return FALSE; + } + DBG1(DBG_TNC, "loaded MAP client certificate from '%s'", client_cert); + this->creds->add_cert(this->creds, TRUE, cert); - /* Set path to the MAP server certificate */ - property =axutil_property_create_with_args(this->env, 0, 0, 0, - server_cert); - axis2_options_set_property(options, this->env, - AXIS2_SSL_SERVER_CERT, property); + /* load MAP client private key */ + if (client_key) + { + key = lib->creds->create(lib->creds, CRED_PRIVATE_KEY, KEY_RSA, + BUILD_FROM_FILE, client_key, BUILD_END); + if (!key) + { + DBG1(DBG_TNC, "loading MAP client private key from '%s' failed", + client_key); + return FALSE; + } + DBG1(DBG_TNC, "loaded MAP client RSA private key from '%s'", + client_key); + this->creds->add_key(this->creds, key); + } - if (key_file) + /* set client ID to certificate distinguished name */ + client_id = cert->get_subject(cert); + + /* check if we have a private key matching the certificate */ + auth = auth_cfg_create(); + auth->add(auth, AUTH_RULE_SUBJECT_CERT, cert); + key = lib->credmgr->get_private(lib->credmgr, KEY_RSA, client_id, auth); + auth->destroy(auth); + if (!key) + { + DBG1(DBG_TNC, "no RSA private key matching MAP client certificate"); + return FALSE; + } + } + else + { + /* set base64-encoded username:password for HTTP Basic Authentication */ + this->user_pass = chunk_to_base64(chunk_from_str(user_pass), NULL); + } + + /* remove HTTPS prefix if any */ + if (strlen(server_uri) >= 8 && strncaseeq(server_uri, "https://", 8)) { - /* Set path to the MAP client certificate */ - property =axutil_property_create_with_args(this->env, 0, 0, 0, - key_file); - axis2_options_set_property(options, this->env, - AXIS2_SSL_KEY_FILE, property); - if (ssl_passphrase) + server_uri += 8; + } + this->uri = server_uri; + + /* duplicate server string since we are going to manipulate it */ + server_str = strdup(server_uri); + + /* extract server name and port from server URI */ + port_str = strchr(server_str, ':'); + if (port_str) + { + *port_str++ = '\0'; + if (sscanf(port_str, "%d", &port) != 1) { - /* Provide SSL passphrase */ - property =axutil_property_create_with_args(this->env, 0, 0, 0, - ssl_passphrase); - axis2_options_set_property(options, this->env, - AXIS2_SSL_PASSPHRASE, property); - } + DBG1(DBG_TNC, "parsing server port %s failed", port_str); + free(server_str); + return FALSE; + } } - else + else { - /* Set up HTTP Basic MAP client authentication */ - axis2_options_set_http_auth_info(options, this->env, - username, password, "Basic"); + /* use default https port */ + port = 443; + uri_str = strchr(server_str, '/'); + if (uri_str) + { + *uri_str = '\0'; + } } - /* Define the MAP server as the to endpoint reference */ - endpoint_ref = axis2_endpoint_ref_create(this->env, server); - axis2_options_set_to(options, this->env, endpoint_ref); - - /* Set up https transport */ - transport_in = axis2_transport_in_desc_create(this->env, - AXIS2_TRANSPORT_ENUM_HTTPS); - transport_out = axis2_transport_out_desc_create(this->env, - AXIS2_TRANSPORT_ENUM_HTTPS); - transport_sender = axis2_http_transport_sender_create(this->env); - axis2_transport_out_desc_set_sender(transport_out, this->env, - transport_sender); - axis2_options_set_transport_in(options, this->env, transport_in); - axis2_options_set_transport_out(options, this->env, transport_out); - - /* Create the axis2 service client */ - this->svc_client = axis2_svc_client_create(this->env, client_home); - if (!this->svc_client) + /* open TCP socket and connect to MAP server */ + this->host = host_create_from_dns(server_str, 0, port); + if (!this->host) { - DBG1(DBG_TNC, "could not create axis2 service client"); - AXIS2_LOG_ERROR(this->env->log, AXIS2_LOG_SI, - "Stub invoke FAILED: Error code: %d :: %s", - this->env->error->error_number, - AXIS2_ERROR_GET_MESSAGE(this->env->error)); - destroy(this); + DBG1(DBG_TNC, "resolving hostname %s failed", server_str); + free(server_str); + return FALSE; + } + free(server_str); + + this->fd = socket(this->host->get_family(this->host), SOCK_STREAM, 0); + if (this->fd == IFMAP_NO_FD) + { + DBG1(DBG_TNC, "opening socket failed: %s", strerror(errno)); + return FALSE; + } + + if (connect(this->fd, this->host->get_sockaddr(this->host), + *this->host->get_sockaddr_len(this->host)) == -1) + { + DBG1(DBG_TNC, "connecting to %#H failed: %s", + this->host, strerror(errno)); return FALSE; } - axis2_svc_client_set_options(this->svc_client, this->env, options); - DBG1(DBG_TNC, "connecting as MAP client '%s' to MAP server at '%s'", - username, server); + /* open TLS socket */ + this->tls = tls_socket_create(FALSE, server_id, client_id, this->fd, NULL); + if (!this->tls) + { + DBG1(DBG_TNC, "creating TLS socket failed"); + return FALSE; + } return TRUE; } @@ -839,16 +896,26 @@ tnc_ifmap_soap_t *tnc_ifmap_soap_create() INIT(this, .public = { .newSession = _newSession, + .renewSession = _renewSession, .purgePublisher = _purgePublisher, .publish_ike_sa = _publish_ike_sa, .publish_device_ip = _publish_device_ip, + .publish_virtual_ips = _publish_virtual_ips, .publish_enforcement_report = _publish_enforcement_report, .endSession = _endSession, + .get_session_id = _get_session_id, + .orphaned = _orphaned, + .get_ref = _get_ref, .destroy = _destroy, }, + .fd = IFMAP_NO_FD, + .creds = mem_cred_create(), + .ref = 1, ); - if (!axis2c_init(this)) + lib->credmgr->add_set(lib->credmgr, &this->creds->set); + + if (!soap_init(this)) { destroy(this); return NULL; diff --git a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap.h b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap.h index 4bf421e33..fbc65a2b1 100644 --- a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap.h +++ b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap.h @@ -1,5 +1,5 @@ /* - * Copyright (C) 2011 Andreas Steffen + * Copyright (C) 2011-2013 Andreas Steffen * HSR Hochschule fuer Technik Rapperswil * * This program is free software; you can redistribute it and/or modify it @@ -15,14 +15,14 @@ /** * @defgroup tnc_ifmap_soap tnc_ifmap_soap - * @{ @ingroup tnc_ifmap + * @{ @ingroup tnc_ifmap */ #ifndef TNC_IFMAP_SOAP_H_ #define TNC_IFMAP_SOAP_H_ #include <library.h> -#include <utils/host.h> +#include <networking/host.h> #include <sa/ike_sa.h> typedef struct tnc_ifmap_soap_t tnc_ifmap_soap_t; @@ -40,6 +40,13 @@ struct tnc_ifmap_soap_t { bool (*newSession)(tnc_ifmap_soap_t *this); /** + * Check if the IF-MAP session is still active + * + * @return TRUE if command was successful + */ + bool (*renewSession)(tnc_ifmap_soap_t *this); + + /** * Purges all metadata published by this publisher * * @return TRUE if command was successful @@ -47,16 +54,16 @@ struct tnc_ifmap_soap_t { bool (*purgePublisher)(tnc_ifmap_soap_t *this); /** - * Publish metadata about established/deleted IKE_SAs + * Publish metadata about established/deleted IKE_SAs * - * @param ike_sa IKE_SA for which metadate is published + * @param ike_sa IKE_SA for which metadata is published * @param up TRUE if IKE_SEA is up, FALSE if down * @return TRUE if command was successful */ bool (*publish_ike_sa)(tnc_ifmap_soap_t *this, ike_sa_t *ike_sa, bool up); /** - * Publish PEP device-ip metadata + * Publish PEP device-ip metadata * * @param host IP address of local endpoint * @return TRUE if command was successful @@ -64,6 +71,16 @@ struct tnc_ifmap_soap_t { bool (*publish_device_ip)(tnc_ifmap_soap_t *this, host_t *host); /** + * Publish Virtual IP access-request-ip metadata + * + * @param ike_sa IKE_SA for which Virtual IP metadata is published + * @param assign TRUE if assigned, FALSE if removed + * @return TRUE if command was successful + */ + bool (*publish_virtual_ips)(tnc_ifmap_soap_t *this, ike_sa_t *ike_sa, + bool assign); + + /** * Publish enforcement-report metadata * * @param host Host to be enforced @@ -82,6 +99,27 @@ struct tnc_ifmap_soap_t { bool (*endSession)(tnc_ifmap_soap_t *this); /** + * Get ID of IF-MAP session + * + * @return IF-MAP session ID + */ + char* (*get_session_id)(tnc_ifmap_soap_t *this); + + /** + * Check for an orphaned IF-MAP session + * + * @return TRUE if IF-MAP session is orphaned + */ + bool (*orphaned)(tnc_ifmap_soap_t *this); + + /** + * Get a reference to an IF-MAP session + * + * @return referenced IF-MAP session + */ + tnc_ifmap_soap_t* (*get_ref)(tnc_ifmap_soap_t *this); + + /** * Destroy a tnc_ifmap_soap_t. */ void (*destroy)(tnc_ifmap_soap_t *this); diff --git a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap_msg.c b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap_msg.c new file mode 100644 index 000000000..b86288683 --- /dev/null +++ b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap_msg.c @@ -0,0 +1,256 @@ +/* + * Copyright (C) 2013 Andreas Steffen + * HSR 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 <http://www.fsf.org/copyleft/gpl.txt>. + * + * 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 "tnc_ifmap_soap_msg.h" +#include "tnc_ifmap_http.h" + +#include <utils/debug.h> + +#define SOAP_NS "http://www.w3.org/2003/05/soap-envelope" + +typedef struct private_tnc_ifmap_soap_msg_t private_tnc_ifmap_soap_msg_t; + +/** + * Private data of an tnc_ifmap_soap_msg_t object. + */ +struct private_tnc_ifmap_soap_msg_t { + + /** + * Public tnc_ifmap_soap_msg_t interface. + */ + tnc_ifmap_soap_msg_t public; + + /** + * HTTP POST request builder and response processing + */ + tnc_ifmap_http_t *http; + + /** + * TLS socket + */ + tls_socket_t *tls; + + /** + * XML Document + */ + xmlDocPtr doc; + +}; + +/** + * Find a child node with a given name + */ +static xmlNodePtr find_child(xmlNodePtr parent, const xmlChar* name) +{ + xmlNodePtr child; + + child = parent->xmlChildrenNode; + while (child) + { + if (xmlStrcmp(child->name, name) == 0) + { + return child; + } + child = child->next; + } + + DBG1(DBG_TNC, "child node \"%s\" not found", name); + return NULL; +} + +METHOD(tnc_ifmap_soap_msg_t, post, bool, + private_tnc_ifmap_soap_msg_t *this, xmlNodePtr request, char *result_name, + xmlNodePtr *result) +{ + xmlDocPtr doc; + xmlNodePtr env, body, cur, response; + xmlNsPtr ns; + xmlChar *xml_str, *errorCode, *errorString; + int xml_len, len, written; + chunk_t xml, http; + char buf[4096]; + status_t status; + + DBG2(DBG_TNC, "sending ifmap %s", request->name); + + /* Generate XML Document containing SOAP Envelope */ + doc = xmlNewDoc("1.0"); + env =xmlNewNode(NULL, "Envelope"); + ns = xmlNewNs(env, SOAP_NS, "env"); + xmlSetNs(env, ns); + xmlDocSetRootElement(doc, env); + + /* Add SOAP Body containing IF-MAP request */ + body = xmlNewNode(ns, "Body"); + xmlAddChild(body, request); + xmlAddChild(env, body); + + /* Convert XML Document into a character string */ + xmlDocDumpFormatMemory(doc, &xml_str, &xml_len, 1); + xmlFreeDoc(doc); + DBG3(DBG_TNC, "%.*s", xml_len, xml_str); + xml = chunk_create(xml_str, xml_len); + + /* Send SOAP-XML request via HTTPS POST */ + do + { + status = this->http->build(this->http, &xml, &http); + if (status == FAILED) + { + break; + } + written = this->tls->write(this->tls, http.ptr, http.len); + free(http.ptr); + if (written != http.len) + { + status = FAILED; + break; + } + } + while (status == NEED_MORE); + + xmlFree(xml_str); + if (status != SUCCESS) + { + return FALSE; + } + + /* Receive SOAP-XML response via [chunked] HTTPS */ + xml = chunk_empty; + do + { + len = this->tls->read(this->tls, buf, sizeof(buf), TRUE); + if (len <= 0) + { + return FALSE; + } + http = chunk_create(buf, len); + + status = this->http->process(this->http, &http, &xml); + if (status == FAILED) + { + free(xml.ptr); + return FALSE; + } + } + while (status == NEED_MORE); + + DBG3(DBG_TNC, "parsing XML message %B", &xml); + this->doc = xmlParseMemory(xml.ptr, xml.len); + free(xml.ptr); + + if (!this->doc) + { + DBG1(DBG_TNC, "failed to parse XML message"); + return FALSE; + } + + /* check out XML document */ + cur = xmlDocGetRootElement(this->doc); + if (!cur) + { + DBG1(DBG_TNC, "empty XML message"); + return FALSE; + } + + /* get XML Document type is a SOAP Envelope */ + if (xmlStrcmp(cur->name, "Envelope")) + { + DBG1(DBG_TNC, "XML message does not contain a SOAP Envelope"); + return FALSE; + } + + /* get SOAP Body */ + cur = find_child(cur, "Body"); + if (!cur) + { + return FALSE; + } + + /* get IF-MAP response */ + response = find_child(cur, "response"); + if (!response) + { + return FALSE; + } + + /* get IF-MAP result */ + cur = find_child(response, result_name); + if (!cur) + { + cur = find_child(response, "errorResult"); + if (cur) + { + DBG1(DBG_TNC, "received errorResult"); + + errorCode = xmlGetProp(cur, "errorCode"); + if (errorCode) + { + DBG1(DBG_TNC, " %s", errorCode); + xmlFree(errorCode); + } + + cur = find_child(cur, "errorString"); + if (cur) + { + errorString = xmlNodeGetContent(cur); + if (errorString) + { + DBG1(DBG_TNC, " %s", errorString); + xmlFree(errorString); + } + } + } + return FALSE; + } + + if (result) + { + *result = cur; + } + return TRUE; +} + +METHOD(tnc_ifmap_soap_msg_t, destroy, void, + private_tnc_ifmap_soap_msg_t *this) +{ + this->http->destroy(this->http); + if (this->doc) + { + xmlFreeDoc(this->doc); + } + free(this); +} + +/** + * See header + */ +tnc_ifmap_soap_msg_t *tnc_ifmap_soap_msg_create(char *uri, chunk_t user_pass, + tls_socket_t *tls) +{ + private_tnc_ifmap_soap_msg_t *this; + + INIT(this, + .public = { + .post = _post, + .destroy = _destroy, + }, + .http = tnc_ifmap_http_create(uri, user_pass), + .tls = tls, + ); + + return &this->public; +} + diff --git a/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap_msg.h b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap_msg.h new file mode 100644 index 000000000..4f809ba1a --- /dev/null +++ b/src/libcharon/plugins/tnc_ifmap/tnc_ifmap_soap_msg.h @@ -0,0 +1,62 @@ +/* + * Copyright (C) 2013 Andreas Steffen + * HSR 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 <http://www.fsf.org/copyleft/gpl.txt>. + * + * 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. + */ + +/** + * @defgroup tnc_ifmap_soap_msg tnc_ifmap_soap_msg + * @{ @ingroup tnc_ifmap + */ + +#ifndef TNC_IFMAP_SOAP_MSG_H_ +#define TNC_IFMAP_SOAP_MSG_H_ + +#include <library.h> +#include <tls_socket.h> + +#include <libxml/parser.h> + +typedef struct tnc_ifmap_soap_msg_t tnc_ifmap_soap_msg_t; + +/** + * Interface for sending and receiving SOAP-XML messages + */ +struct tnc_ifmap_soap_msg_t { + + /** + * Post an IF-MAP request in a SOAP-XML message and return a result + * + * @param request XML-encoded IF-MAP request + * @param result_name name of the IF-MAP result + * @param result XML-encoded IF-MAP result + */ + bool (*post)(tnc_ifmap_soap_msg_t *this, xmlNodePtr request, + char *result_name, xmlNodePtr* result); + + /** + * Destroy a tnc_ifmap_soap_msg_t object. + */ + void (*destroy)(tnc_ifmap_soap_msg_t *this); +}; + +/** + * Create a tnc_ifmap_soap_msg instance. + * + * @param uri HTTPS URI with https:// prefix removed + * @param user_pass Optional username:password for HTTP Basic Authentication + * @param tls TLS socket protecting the SOAP message + */ +tnc_ifmap_soap_msg_t *tnc_ifmap_soap_msg_create(char *uri, chunk_t user_pass, + tls_socket_t *tls); + +#endif /** TNC_IFMAP_SOAP_MSG_H_ @}*/ |
