android: Also request a virtual IPv6 address and propose IPv6 TS
authorTobias Brunner <tobias@strongswan.org>
Thu, 7 Mar 2013 17:16:56 +0000 (18:16 +0100)
committerTobias Brunner <tobias@strongswan.org>
Wed, 20 Mar 2013 14:24:26 +0000 (15:24 +0100)
This allows IPv6 over IPv4 but falls back nicely if we don't get a
virtual IPv6 (or IPv4) address.

src/frontends/android/jni/Android.mk
src/frontends/android/jni/libandroidbridge/backend/android_service.c
src/frontends/android/jni/libandroidbridge/vpnservice_builder.c

index ce544d2..164cae5 100644 (file)
@@ -35,6 +35,8 @@ strongswan_CFLAGS := \
        -DHAVE_STRUCT_SADB_X_POLICY_SADB_X_POLICY_PRIORITY \
        -DHAVE_IPSEC_MODE_BEET \
        -DHAVE_IPSEC_DIR_FWD \
+       -DHAVE_IN6ADDR_ANY \
+       -DHAVE_NETINET_IP6_H \
        -DOPENSSL_NO_CMS \
        -DOPENSSL_NO_ENGINE \
        -DCONFIG_H_INCLUDED \
@@ -51,10 +53,6 @@ strongswan_CFLAGS := \
        -DDEV_RANDOM=\"/dev/random\" \
        -DDEV_URANDOM=\"/dev/urandom\"
 
-# only for Android 2.0+
-strongswan_CFLAGS += \
-       -DHAVE_IN6ADDR_ANY
-
 include $(addprefix $(LOCAL_PATH)/,$(addsuffix /Android.mk, \
                vstr \
                openssl \
index 76c1398..302f732 100644 (file)
@@ -209,13 +209,20 @@ static bool add_route(vpnservice_builder_t *builder, host_t *net,
 {
        /* if route is 0.0.0.0/0, split it into two routes 0.0.0.0/1 and
         * 128.0.0.0/1 because otherwise it would conflict with the current default
-        * route */
+        * route.  likewise for IPv6 with ::/0. */
        if (net->is_anyaddr(net) && prefix == 0)
        {
                bool success;
 
                success = add_route(builder, net, 1);
-               net = host_create_from_string("128.0.0.0", 0);
+               if (net->get_family(net) == AF_INET)
+               {
+                       net = host_create_from_string("128.0.0.0", 0);
+               }
+               else
+               {
+                       net = host_create_from_string("8000::", 0);
+               }
                success = success && add_route(builder, net, 1);
                net->destroy(net);
                return success;
@@ -526,7 +533,8 @@ static job_requeue_t initiate(private_android_service_t *this)
                                                           TRUE, FALSE, /* mobike, aggressive */
                                                           0, 0, /* DPD delay, timeout */
                                                           FALSE, NULL, NULL); /* mediation */
-       peer_cfg->add_virtual_ip(peer_cfg, host_create_from_string("0.0.0.0", 0));
+       peer_cfg->add_virtual_ip(peer_cfg, host_create_any(AF_INET));
+       peer_cfg->add_virtual_ip(peer_cfg, host_create_any(AF_INET6));
 
        /* local auth config */
        if (streq("ikev2-cert", this->type) ||
@@ -561,11 +569,13 @@ static job_requeue_t initiate(private_android_service_t *this)
         * libipsec, no PFS for now */
        child_cfg->add_proposal(child_cfg, proposal_create_from_string(PROTO_ESP,
                                                        "aes128-aes192-aes256-sha1-sha256-sha384-sha512"));
-       ts = traffic_selector_create_from_string(0, TS_IPV4_ADDR_RANGE, "0.0.0.0",
-                                                                                        0, "255.255.255.255", 65535);
+       ts = traffic_selector_create_from_cidr("0.0.0.0/0", 0, 0, 65535);
+       child_cfg->add_traffic_selector(child_cfg, TRUE, ts);
+       ts = traffic_selector_create_from_cidr("0.0.0.0/0", 0, 0, 65535);
+       child_cfg->add_traffic_selector(child_cfg, FALSE, ts);
+       ts = traffic_selector_create_from_cidr("::/0", 0, 0, 65535);
        child_cfg->add_traffic_selector(child_cfg, TRUE, ts);
-       ts = traffic_selector_create_from_string(0, TS_IPV4_ADDR_RANGE, "0.0.0.0",
-                                                                                        0, "255.255.255.255", 65535);
+       ts = traffic_selector_create_from_cidr("::/0", 0, 0, 65535);
        child_cfg->add_traffic_selector(child_cfg, FALSE, ts);
        peer_cfg->add_child_cfg(peer_cfg, child_cfg);
 
index c95b335..5232bc4 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2012 Tobias Brunner
+ * Copyright (C) 2012-2013 Tobias Brunner
  * Copyright (C) 2012 Giuliano Grassi
  * Copyright (C) 2012 Ralf Sager
  * Hochschule fuer Technik Rapperswil
@@ -45,16 +45,14 @@ METHOD(vpnservice_builder_t, add_address, bool,
        JNIEnv *env;
        jmethodID method_id;
        jstring str;
-       char buf[INET_ADDRSTRLEN];
+       char buf[INET6_ADDRSTRLEN];
+       int prefix;
 
        androidjni_attach_thread(&env);
 
        DBG2(DBG_LIB, "builder: adding interface address %H", addr);
 
-       if (addr->get_family(addr) != AF_INET)
-       {
-               goto failed;
-       }
+       prefix = addr->get_family(addr) == AF_INET ? 32 : 128;
        if (snprintf(buf, sizeof(buf), "%H", addr) >= sizeof(buf))
        {
                goto failed;
@@ -71,7 +69,7 @@ METHOD(vpnservice_builder_t, add_address, bool,
        {
                goto failed;
        }
-       if (!(*env)->CallBooleanMethod(env, this->builder, method_id, str, 32))
+       if (!(*env)->CallBooleanMethod(env, this->builder, method_id, str, prefix))
        {
                goto failed;
        }
@@ -121,16 +119,12 @@ METHOD(vpnservice_builder_t, add_route, bool,
        JNIEnv *env;
        jmethodID method_id;
        jstring str;
-       char buf[INET_ADDRSTRLEN];
+       char buf[INET6_ADDRSTRLEN];
 
        androidjni_attach_thread(&env);
 
        DBG2(DBG_LIB, "builder: adding route %+H/%d", net, prefix);
 
-       if (net->get_family(net) != AF_INET)
-       {
-               goto failed;
-       }
        if (snprintf(buf, sizeof(buf), "%+H", net) >= sizeof(buf))
        {
                goto failed;