resetting manifest requested domain to floor
[platform/upstream/openconnect.git] / library.c
index 92b7c25..73e7c54 100644 (file)
--- a/library.c
+++ b/library.c
 #include <errno.h>
 #include <stdlib.h>
 
+#ifdef LIBSTOKEN_HDR
+#include LIBSTOKEN_HDR
+#endif
+
+#include <libxml/tree.h>
+
 #include "openconnect-internal.h"
 
 struct openconnect_info *openconnect_vpninfo_new (char *useragent,
@@ -37,7 +43,6 @@ struct openconnect_info *openconnect_vpninfo_new (char *useragent,
 {
        struct openconnect_info *vpninfo = calloc (sizeof(*vpninfo), 1);
 
-       vpninfo->mtu = 1406;
        vpninfo->ssl_fd = -1;
        vpninfo->cert_expire_warning = 60 * 86400;
        vpninfo->useragent = openconnect_create_useragent (useragent);
@@ -47,6 +52,7 @@ struct openconnect_info *openconnect_vpninfo_new (char *useragent,
        vpninfo->progress = progress;
        vpninfo->cbdata = privdata?:vpninfo;
        vpninfo->cancel_fd = -1;
+       openconnect_set_reported_os(vpninfo, NULL);
 
 #ifdef ENABLE_NLS
        bindtextdomain("openconnect", LOCALEDIR);
@@ -55,6 +61,30 @@ struct openconnect_info *openconnect_vpninfo_new (char *useragent,
        return vpninfo;
 }
 
+int openconnect_set_reported_os (struct openconnect_info *vpninfo, const char *os)
+{
+       if (!os) {
+#if defined(__APPLE__)
+               os = "mac";
+#else
+               os = sizeof(long) > 4 ? "linux-64" : "linux";
+#endif
+       }
+
+       /* FIXME: is there a special platname for 64-bit Windows? */
+       if (!strcmp(os, "mac"))
+               vpninfo->csd_xmltag = "csdMac";
+       else if (!strcmp(os, "linux") || !strcmp(os, "linux-64"))
+               vpninfo->csd_xmltag = "csdLinux";
+       else if (!strcmp(os, "win"))
+               vpninfo->csd_xmltag = "csd";
+       else
+               return -EINVAL;
+
+       vpninfo->platname = os;
+       return 0;
+}
+
 static void free_optlist (struct vpn_option *opt)
 {
        struct vpn_option *next;
@@ -69,7 +99,8 @@ static void free_optlist (struct vpn_option *opt)
 
 void openconnect_vpninfo_free (struct openconnect_info *vpninfo)
 {
-       openconnect_reset_ssl(vpninfo);
+       openconnect_close_https(vpninfo, 1);
+       free(vpninfo->peer_addr);
        free_optlist(vpninfo->cookies);
        free_optlist(vpninfo->cstp_options);
        free_optlist(vpninfo->dtls_options);
@@ -78,8 +109,20 @@ void openconnect_vpninfo_free (struct openconnect_info *vpninfo)
        free(vpninfo->redirect_url);
        free(vpninfo->proxy_type);
        free(vpninfo->proxy);
-       free(vpninfo->csd_scriptname);
+
+       if (vpninfo->csd_scriptname) {
+               unlink(vpninfo->csd_scriptname);
+               free(vpninfo->csd_scriptname);
+       }
+       free(vpninfo->csd_token);
+       free(vpninfo->csd_ticket);
        free(vpninfo->csd_stuburl);
+       free(vpninfo->csd_starturl);
+       free(vpninfo->csd_waiturl);
+       free(vpninfo->csd_preurl);
+       if (vpninfo->opaque_srvdata)
+               xmlFreeNode(vpninfo->opaque_srvdata);
+
        /* These are const in openconnect itself, but for consistency of
           the library API we do take ownership of the strings we're given,
           and thus we have to free them too. */
@@ -95,6 +138,13 @@ void openconnect_vpninfo_free (struct openconnect_info *vpninfo)
 #endif
                vpninfo->peer_cert = NULL;
        }
+       free(vpninfo->useragent);
+#ifdef LIBSTOKEN_HDR
+       if (vpninfo->stoken_pin)
+               free(vpninfo->stoken_pin);
+       if (vpninfo->stoken_ctx)
+               stoken_destroy(vpninfo->stoken_ctx);
+#endif
        /* No need to free deflate streams; they weren't initialised */
        free(vpninfo);
 }
@@ -171,7 +221,7 @@ void openconnect_clear_cookie (struct openconnect_info *vpninfo)
 
 void openconnect_reset_ssl (struct openconnect_info *vpninfo)
 {
-       openconnect_close_https(vpninfo, 1);
+       openconnect_close_https(vpninfo, 0);
        if (vpninfo->peer_addr) {
                free(vpninfo->peer_addr);
                vpninfo->peer_addr = NULL;
@@ -226,3 +276,84 @@ const char *openconnect_get_version (void)
 {
        return openconnect_version_str;
 }
+
+int openconnect_has_pkcs11_support(void)
+{
+#if defined (OPENCONNECT_GNUTLS) && defined (HAVE_P11KIT)
+       return 1;
+#else
+       return 0;
+#endif
+}
+
+#if defined (OPENCONNECT_OPENSSL) && defined (HAVE_ENGINE)
+#include <openssl/engine.h>
+#endif
+int openconnect_has_tss_blob_support(void)
+{
+#if defined (OPENCONNECT_OPENSSL) && defined (HAVE_ENGINE)
+       ENGINE *e;
+
+       ENGINE_load_builtin_engines();
+
+       e = ENGINE_by_id("tpm");
+       if (e) {
+               ENGINE_free(e);
+               return 1;
+       }
+#elif defined (OPENCONNECT_GNUTLS) && defined (HAVE_TROUSERS)
+       return 1;
+#endif
+       return 0;
+}
+
+int openconnect_has_stoken_support(void)
+{
+#ifdef LIBSTOKEN_HDR
+       return 1;
+#else
+       return 0;
+#endif
+}
+
+/*
+ * Enable software token generation if use_stoken == 1.
+ *
+ * If token_str is not NULL, try to parse the string.  Otherwise, try to read
+ * the token data from ~/.stokenrc
+ *
+ * Return value:
+ *  = -EOPNOTSUPP, if libstoken is not available
+ *  = -EINVAL, if the token string is invalid (token_str was provided)
+ *  = -ENOENT, if ~/.stokenrc is missing (token_str was NULL)
+ *  = -EIO, for other libstoken failures
+ *  = 0, on success
+ */
+int openconnect_set_stoken_mode (struct openconnect_info *vpninfo,
+                                int use_stoken, const char *token_str)
+{
+#ifdef LIBSTOKEN_HDR
+       int ret;
+
+       vpninfo->use_stoken = 0;
+       if (!use_stoken)
+               return 0;
+
+       if (!vpninfo->stoken_ctx) {
+               vpninfo->stoken_ctx = stoken_new();
+               if (!vpninfo->stoken_ctx)
+                       return -EIO;
+       }
+
+       ret = token_str ?
+             stoken_import_string(vpninfo->stoken_ctx, token_str) :
+             stoken_import_rcfile(vpninfo->stoken_ctx, NULL);
+       if (ret)
+               return ret;
+
+       vpninfo->use_stoken = 1;
+       return 0;
+#else
+       return -EOPNOTSUPP;
+#endif
+}