android: Encode connection settings as single Java string argument

This makes adding new configuration settings easier.
This commit is contained in:
Tobias Brunner
2015-07-28 13:27:32 +02:00
parent fd16adb765
commit 79af70c66e
4 changed files with 54 additions and 78 deletions
@@ -1,5 +1,5 @@
/*
* Copyright (C) 2010-2014 Tobias Brunner
* Copyright (C) 2010-2015 Tobias Brunner
* Copyright (C) 2012 Giuliano Grassi
* Copyright (C) 2012 Ralf Sager
* Hochschule fuer Technik Rapperswil
@@ -55,24 +55,9 @@ struct private_android_service_t {
ike_sa_t *ike_sa;
/**
* the type of VPN
* configuration setttings
*/
char *type;
/**
* gateway
*/
char *gateway;
/**
* username
*/
char *username;
/**
* password
*/
char *password;
settings_t *settings;
/**
* lock to safely access the TUN device fd
@@ -621,6 +606,7 @@ static void add_auth_cfg_pw(private_android_service_t *this,
{
identification_t *user;
auth_cfg_t *auth;
char *username, *password;
auth = auth_cfg_create();
auth->add(auth, AUTH_RULE_AUTH_CLASS, AUTH_CLASS_EAP);
@@ -629,12 +615,14 @@ static void add_auth_cfg_pw(private_android_service_t *this,
auth->add(auth, AUTH_RULE_EAP_TYPE, EAP_TTLS);
}
user = identification_create_from_string(this->username);
username = this->settings->get_str(this->settings, "connection.username",
NULL);
password = this->settings->get_str(this->settings, "connection.password",
NULL);
user = identification_create_from_string(username);
auth->add(auth, AUTH_RULE_IDENTITY, user);
this->creds->add_username_password(this->creds, this->username,
this->password);
memwipe(this->password, strlen(this->password));
this->creds->add_username_password(this->creds, username, password);
peer_cfg->add_auth_cfg(peer_cfg, auth, TRUE);
}
@@ -644,6 +632,7 @@ static bool add_auth_cfg_cert(private_android_service_t *this,
certificate_t *cert;
identification_t *id;
auth_cfg_t *auth;
char *type;
cert = this->creds->load_user_certificate(this->creds);
if (!cert)
@@ -651,8 +640,9 @@ static bool add_auth_cfg_cert(private_android_service_t *this,
return FALSE;
}
type = this->settings->get_str(this->settings, "connection.type", NULL);
auth = auth_cfg_create();
if (strpfx("ikev2-eap-tls", this->type))
if (strpfx("ikev2-eap-tls", type))
{
auth->add(auth, AUTH_RULE_AUTH_CLASS, AUTH_CLASS_EAP);
auth->add(auth, AUTH_RULE_EAP_TYPE, EAP_TLS);
@@ -687,11 +677,12 @@ static job_requeue_t initiate(private_android_service_t *this)
.jitter = 300 /* 5min */
}
};
char *type, *server;
server = this->settings->get_str(this->settings, "connection.server", NULL);
ike_cfg = ike_cfg_create(IKEV2, TRUE, TRUE, "0.0.0.0",
charon->socket->get_port(charon->socket, FALSE),
this->gateway, IKEV2_UDP_PORT,
FRAGMENTATION_YES, 0);
server, IKEV2_UDP_PORT, FRAGMENTATION_YES, 0);
ike_cfg->add_proposal(ike_cfg, proposal_create_default(PROTO_IKE));
ike_cfg->add_proposal(ike_cfg, proposal_create_default_aead(PROTO_IKE));
@@ -705,10 +696,11 @@ static job_requeue_t initiate(private_android_service_t *this)
peer_cfg->add_virtual_ip(peer_cfg, host_create_any(AF_INET));
peer_cfg->add_virtual_ip(peer_cfg, host_create_any(AF_INET6));
type = this->settings->get_str(this->settings, "connection.type", NULL);
/* local auth config */
if (streq("ikev2-cert", this->type) ||
streq("ikev2-cert-eap", this->type) ||
streq("ikev2-eap-tls", this->type))
if (streq("ikev2-cert", type) ||
streq("ikev2-cert-eap", type) ||
streq("ikev2-eap-tls", type))
{
if (!add_auth_cfg_cert(this, peer_cfg))
{
@@ -718,16 +710,16 @@ static job_requeue_t initiate(private_android_service_t *this)
return JOB_REQUEUE_NONE;
}
}
if (streq("ikev2-eap", this->type) ||
streq("ikev2-cert-eap", this->type) ||
streq("ikev2-byod-eap", this->type))
if (streq("ikev2-eap", type) ||
streq("ikev2-cert-eap", type) ||
streq("ikev2-byod-eap", type))
{
add_auth_cfg_pw(this, peer_cfg, strpfx(this->type, "ikev2-byod"));
add_auth_cfg_pw(this, peer_cfg, strpfx(type, "ikev2-byod"));
}
/* remote auth config */
auth = auth_cfg_create();
gateway = identification_create_from_string(this->gateway);
gateway = identification_create_from_string(server);
auth->add(auth, AUTH_RULE_IDENTITY, gateway);
auth->add(auth, AUTH_RULE_IDENTITY_LOOSE, TRUE);
auth->add(auth, AUTH_RULE_AUTH_CLASS, AUTH_CLASS_PUBKEY);
@@ -806,23 +798,15 @@ METHOD(android_service_t, destroy, void,
close_tun_device(this);
this->dns_proxy->destroy(this->dns_proxy);
this->lock->destroy(this->lock);
free(this->type);
free(this->gateway);
free(this->username);
if (this->password)
{
memwipe(this->password, strlen(this->password));
free(this->password);
}
this->settings->destroy(this->settings);
free(this);
}
/**
* See header
*/
android_service_t *android_service_create(android_creds_t *creds, char *type,
char *gateway, char *username,
char *password)
android_service_t *android_service_create(android_creds_t *creds,
settings_t *settings)
{
private_android_service_t *this;
@@ -840,15 +824,13 @@ android_service_t *android_service_create(android_creds_t *creds, char *type,
},
.lock = rwlock_create(RWLOCK_TYPE_DEFAULT),
.dns_proxy = android_dns_proxy_create(),
.username = username,
.password = password,
.gateway = gateway,
.settings = settings,
.creds = creds,
.type = type,
.tunfd = -1,
);
/* only allow queries for the VPN gateway */
this->dns_proxy->add_hostname(this->dns_proxy, gateway);
this->dns_proxy->add_hostname(this->dns_proxy,
this->settings->get_str(this->settings, "connection.server", NULL));
charon->bus->add_listener(charon->bus, &this->public.listener);
@@ -1,5 +1,5 @@
/*
* Copyright (C) 2010-2012 Tobias Brunner
* Copyright (C) 2010-2015 Tobias Brunner
* Copyright (C) 2012 Giuliano Grassi
* Copyright (C) 2012 Ralf Sager
* Hochschule fuer Technik Rapperswil
@@ -52,13 +52,9 @@ struct android_service_t {
* new IKE SA.
*
* @param creds Android specific credential set
* @param type VPN type (see VpnType.java)
* @param gateway gateway address
* @param username user name (local identity)
* @param password password (if any)
* @param settings configuration settings (gets adopted)
*/
android_service_t *android_service_create(android_creds_t *creds, char *type,
char *gateway, char *username,
char *password);
android_service_t *android_service_create(android_creds_t *creds,
settings_t *settings);
#endif /** ANDROID_SERVICE_H_ @}*/
@@ -1,5 +1,5 @@
/*
* Copyright (C) 2012-2013 Tobias Brunner
* Copyright (C) 2012-2015 Tobias Brunner
* Copyright (C) 2012 Giuliano Grassi
* Copyright (C) 2012 Ralf Sager
* Hochschule fuer Technik Rapperswil
@@ -400,18 +400,15 @@ METHOD(charonservice_t, get_network_manager, network_manager_t*,
/**
* Initiate a new connection
*
* @param gateway gateway address (gets owned)
* @param username username (gets owned)
* @param password password (gets owned)
* @param settings configuration settings (gets owned)
*/
static void initiate(char *type, char *gateway, char *username, char *password)
static void initiate(settings_t *settings)
{
private_charonservice_t *this = (private_charonservice_t*)charonservice;
this->creds->clear(this->creds);
DESTROY_IF(this->service);
this->service = android_service_create(this->creds, type, gateway,
username, password);
this->service = android_service_create(this->creds, settings);
}
/**
@@ -707,14 +704,12 @@ JNI_METHOD(CharonVpnService, deinitializeCharon, void)
* Initiate SA
*/
JNI_METHOD(CharonVpnService, initiate, void,
jstring jtype, jstring jgateway, jstring jusername, jstring jpassword)
jstring jconfig)
{
char *type, *gateway, *username, *password;
settings_t *settings;
char *config;
type = androidjni_convert_jstring(env, jtype);
gateway = androidjni_convert_jstring(env, jgateway);
username = androidjni_convert_jstring(env, jusername);
password = androidjni_convert_jstring(env, jpassword);
initiate(type, gateway, username, password);
config = androidjni_convert_jstring(env, jconfig);
settings = settings_create_string(config);
initiate(settings);
}
@@ -1,5 +1,5 @@
/*
* Copyright (C) 2012-2013 Tobias Brunner
* Copyright (C) 2012-2015 Tobias Brunner
* Copyright (C) 2012 Giuliano Grassi
* Copyright (C) 2012 Ralf Sager
* Hochschule fuer Technik Rapperswil
@@ -32,6 +32,7 @@ import org.strongswan.android.logic.VpnStateService.State;
import org.strongswan.android.logic.imc.ImcState;
import org.strongswan.android.logic.imc.RemediationInstruction;
import org.strongswan.android.ui.MainActivity;
import org.strongswan.android.utils.SettingsWriter;
import android.app.PendingIntent;
import android.app.Service;
@@ -215,9 +216,12 @@ public class CharonVpnService extends VpnService implements Runnable
if (initializeCharon(builder, mLogFile, mCurrentProfile.getVpnType().has(VpnTypeFeature.BYOD)))
{
Log.i(TAG, "charon started");
initiate(mCurrentProfile.getVpnType().getIdentifier(),
mCurrentProfile.getGateway(), mCurrentProfile.getUsername(),
mCurrentProfile.getPassword());
SettingsWriter writer = new SettingsWriter();
writer.setValue("connection.type", mCurrentProfile.getVpnType().getIdentifier());
writer.setValue("connection.server", mCurrentProfile.getGateway());
writer.setValue("connection.username", mCurrentProfile.getUsername());
writer.setValue("connection.password", mCurrentProfile.getPassword());
initiate(writer.serialize());
}
else
{
@@ -497,7 +501,6 @@ public class CharonVpnService extends VpnService implements Runnable
private PrivateKey getUserKey() throws KeyChainException, InterruptedException
{
return KeyChain.getPrivateKey(getApplicationContext(), mCurrentUserCertificateAlias);
}
/**
@@ -518,7 +521,7 @@ public class CharonVpnService extends VpnService implements Runnable
/**
* Initiate VPN, provided by libandroidbridge.so
*/
public native void initiate(String type, String gateway, String username, String password);
public native void initiate(String config);
/**
* Adapter for VpnService.Builder which is used to access it safely via JNI.