From 8d7bedaa40129ae809f3e1261228b00042872f62 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Parm=C3=A9nides=20GV?= Date: Wed, 31 Dec 2014 16:51:56 +0100 Subject: Don't remove vpn profiles if possible. --- .../main/java/se/leap/bitmaskclient/Dashboard.java | 4 +++- .../java/se/leap/bitmaskclient/EipFragment.java | 17 +++++-------- .../java/se/leap/bitmaskclient/OnBootReceiver.java | 28 ++++++++++++---------- .../main/java/se/leap/bitmaskclient/eip/EIP.java | 20 ++++++++++------ .../java/se/leap/bitmaskclient/eip/Gateway.java | 25 +++++++------------ 5 files changed, 47 insertions(+), 47 deletions(-) (limited to 'app/src/main/java/se/leap') diff --git a/app/src/main/java/se/leap/bitmaskclient/Dashboard.java b/app/src/main/java/se/leap/bitmaskclient/Dashboard.java index 659cd22c..4e6120ab 100644 --- a/app/src/main/java/se/leap/bitmaskclient/Dashboard.java +++ b/app/src/main/java/se/leap/bitmaskclient/Dashboard.java @@ -108,7 +108,9 @@ public class Dashboard extends Activity implements SessionDialog.SessionDialogIn try { provider = new Provider(new URL(preferences.getString(Provider.MAIN_URL, ""))); provider.define(new JSONObject(preferences.getString(Provider.KEY, ""))); - } catch (MalformedURLException | JSONException e) { + } catch (MalformedURLException e) { + e.printStackTrace(); + } catch (JSONException e) { e.printStackTrace(); } diff --git a/app/src/main/java/se/leap/bitmaskclient/EipFragment.java b/app/src/main/java/se/leap/bitmaskclient/EipFragment.java index 27c70c43..a21e0cd1 100644 --- a/app/src/main/java/se/leap/bitmaskclient/EipFragment.java +++ b/app/src/main/java/se/leap/bitmaskclient/EipFragment.java @@ -109,15 +109,10 @@ public class EipFragment extends Fragment implements Observer { super.onSaveInstanceState(outState); } - protected void saveEipStatus() { - boolean eip_is_on = false; - Log.d(TAG, "saveEipStatus"); - if(eip_switch.isChecked()) { - eip_is_on = true; - } - - if(parent_activity != null) - Dashboard.preferences.edit().putBoolean(Dashboard.START_ON_BOOT, eip_is_on).commit(); + protected void saveStatus() { + boolean is_on = eip_switch.isChecked(); + Log.d(TAG, "saveStatus: is_on = " + is_on); + Dashboard.preferences.edit().putBoolean(Dashboard.START_ON_BOOT, is_on).commit(); } @OnCheckedChanged(R.id.eipSwitch) @@ -127,7 +122,7 @@ public class EipFragment extends Fragment implements Observer { else handleSwitchOff(); - saveEipStatus(); + saveStatus(); } private void handleSwitchOn() { @@ -192,7 +187,7 @@ public class EipFragment extends Fragment implements Observer { if(!eip_switch.isChecked()) { eip_switch.setChecked(true); - saveEipStatus(); + saveStatus(); } eipCommand(Constants.ACTION_START_EIP); } diff --git a/app/src/main/java/se/leap/bitmaskclient/OnBootReceiver.java b/app/src/main/java/se/leap/bitmaskclient/OnBootReceiver.java index 07ed6c8f..3b1033bc 100644 --- a/app/src/main/java/se/leap/bitmaskclient/OnBootReceiver.java +++ b/app/src/main/java/se/leap/bitmaskclient/OnBootReceiver.java @@ -3,22 +3,26 @@ package se.leap.bitmaskclient; import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; +import android.content.SharedPreferences; import se.leap.bitmaskclient.eip.Constants; public class OnBootReceiver extends BroadcastReceiver { - // Debug: am broadcast -a android.intent.action.BOOT_COMPLETED - @Override - public void onReceive(Context context, Intent intent) { - if (Intent.ACTION_BOOT_COMPLETED.equals(intent.getAction())) { - if (!context.getSharedPreferences(Dashboard.SHARED_PREFERENCES, Context.MODE_PRIVATE).getString(Provider.KEY, "").isEmpty() && context.getSharedPreferences(Dashboard.SHARED_PREFERENCES, Context.MODE_PRIVATE).getBoolean(Dashboard.START_ON_BOOT, false)) { - Intent dashboard_intent = new Intent(context, Dashboard.class); - dashboard_intent.setAction(Constants.ACTION_START_EIP); - dashboard_intent.putExtra(Dashboard.ON_BOOT, true); - dashboard_intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); - context.startActivity(dashboard_intent); - } - } + SharedPreferences preferences; + + // Debug: am broadcast -a android.intent.action.BOOT_COMPLETED + @Override + public void onReceive(Context context, Intent intent) { + preferences = context.getSharedPreferences(Dashboard.SHARED_PREFERENCES, Context.MODE_PRIVATE); + boolean provider_configured = !preferences.getString(Provider.KEY, "").isEmpty(); + boolean start_on_boot = preferences.getBoolean(Dashboard.START_ON_BOOT, false); + if(provider_configured && start_on_boot) { + Intent dashboard_intent = new Intent(context, Dashboard.class); + dashboard_intent.setAction(Constants.ACTION_START_EIP); + dashboard_intent.putExtra(Dashboard.ON_BOOT, true); + dashboard_intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); + context.startActivity(dashboard_intent); } + } } diff --git a/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java b/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java index 3d3070c8..77d0cd82 100644 --- a/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java +++ b/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java @@ -101,7 +101,7 @@ public final class EIP extends IntentService { stopEIP(); else if (action.equals(ACTION_IS_EIP_RUNNING)) isRunning(); - else if (action.equals(ACTION_UPDATE_EIP_SERVICE)) + else if (action.equals(ACTION_UPDATE_EIP_SERVICE)) updateEIPService(); else if (action.equals(ACTION_CHECK_CERT_VALIDITY)) checkCertValidity(); @@ -174,8 +174,8 @@ public final class EIP extends IntentService { */ private void updateEIPService() { refreshEipDefinition(); - deleteAllVpnProfiles(); - updateGateways(); + if(eip_definition != null) + updateGateways(); tellToReceiver(ACTION_UPDATE_EIP_SERVICE, Activity.RESULT_OK); } @@ -204,15 +204,16 @@ public final class EIP extends IntentService { */ private void updateGateways(){ try { - if(eip_definition != null) { JSONArray gatewaysDefined = eip_definition.getJSONArray("gateways"); for (int i = 0; i < gatewaysDefined.length(); i++) { JSONObject gw = gatewaysDefined.getJSONObject(i); if (isOpenVpnGateway(gw)) { - addGateway(new Gateway(eip_definition, context, gw)); + Gateway gateway = new Gateway(eip_definition, context, gw); + if(!gateways.contains(gateway)) { + addGateway(gateway); + } } } - } } catch (JSONException e) { // TODO Auto-generated catch block e.printStackTrace(); @@ -229,8 +230,13 @@ public final class EIP extends IntentService { } private void addGateway(Gateway gateway) { - profile_manager.addProfile(gateway.getProfile()); + VpnProfile profile = gateway.getProfile(); + profile_manager.addProfile(profile); + profile_manager.saveProfile(context, profile); + profile_manager.saveProfileList(context); + gateways.add(gateway); + Log.d(TAG, "Gateway added: " + gateway.getProfile().getUUIDString()); } private void checkCertValidity() { diff --git a/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java b/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java index 3ee9443c..79239308 100644 --- a/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java +++ b/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java @@ -68,24 +68,8 @@ public class Gateway { timezone = getTimezone(eip_definition); mName = locationAsName(eip_definition); - // Currently deletes VpnProfile for host, if there already is one, and builds new - ProfileManager vpl = ProfileManager.getInstance(context); - Collection profiles = vpl.getProfiles(); - for (Iterator it = profiles.iterator(); it.hasNext(); ){ - VpnProfile p = it.next(); - - if ( p.mName.equalsIgnoreCase( mName ) ) { - it.remove(); - vpl.removeProfile(context, p); - } - } - mVpnProfile = createVPNProfile(); mVpnProfile.mName = mName; - - vpl.addProfile(mVpnProfile); - vpl.saveProfile(context, mVpnProfile); - vpl.saveProfileList(context); } private JSONObject getGeneralConfiguration(JSONObject eip_definition) { @@ -153,4 +137,13 @@ public class Gateway { public int getTimezone() { return timezone; } + + @Override + public boolean equals(Object o) { + if(o instanceof Gateway) { + return ((Gateway) o).getProfile().mConnections.equals(mVpnProfile.mConnections); + } + else + return super.equals(o); + } } -- cgit v1.2.3 From 56e05aecf8430ddad776776e536583686555443a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Parm=C3=A9nides=20GV?= Date: Wed, 31 Dec 2014 17:11:58 +0100 Subject: Update gateway also if credentials changed. --- app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) (limited to 'app/src/main/java/se/leap') diff --git a/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java b/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java index 79239308..e23f67c7 100644 --- a/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java +++ b/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java @@ -141,7 +141,10 @@ public class Gateway { @Override public boolean equals(Object o) { if(o instanceof Gateway) { - return ((Gateway) o).getProfile().mConnections.equals(mVpnProfile.mConnections); + VpnProfile compared_profile = ((Gateway) o).getProfile(); + return compared_profile.mConnections.equals(mVpnProfile.mConnections) + && compared_profile.mClientCertFilename != mVpnProfile.mClientCertFilename + && compared_profile.mClientKeyFilename != mVpnProfile.mClientKeyFilename; } else return super.equals(o); -- cgit v1.2.3 From d23ec1613855f6582b0e79c1a9fc1538d6099944 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Parm=C3=A9nides=20GV?= Date: Wed, 31 Dec 2014 20:50:51 +0100 Subject: Remove duplicated gateways when necessary. --- .../main/java/se/leap/bitmaskclient/eip/EIP.java | 71 +++++++++++++++++++--- 1 file changed, 64 insertions(+), 7 deletions(-) (limited to 'app/src/main/java/se/leap') diff --git a/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java b/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java index 77d0cd82..cf6006e5 100644 --- a/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java +++ b/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java @@ -31,10 +31,13 @@ import org.json.JSONObject; import java.util.ArrayList; import java.util.Collection; +import java.util.Iterator; import java.util.List; +import java.util.NoSuchElementException; import de.blinkt.openvpn.LaunchVPN; import de.blinkt.openvpn.VpnProfile; +import de.blinkt.openvpn.core.Connection; import de.blinkt.openvpn.core.ProfileManager; import se.leap.bitmaskclient.Dashboard; import se.leap.bitmaskclient.EipFragment; @@ -71,7 +74,7 @@ public final class EIP extends IntentService { private static SharedPreferences preferences; private static JSONObject eip_definition; - private static List gateways = new ArrayList(); + private static List gateways = new ArrayList<>(); private static ProfileManager profile_manager; private static Gateway gateway; @@ -190,12 +193,6 @@ public final class EIP extends IntentService { e.printStackTrace(); } } - - private void deleteAllVpnProfiles() { - Collection profiles = profile_manager.getProfiles(); - profiles.removeAll(profiles); - gateways.clear(); - } /** * Walk the list of gateways defined in eip-service.json and parse them into @@ -231,6 +228,8 @@ public final class EIP extends IntentService { private void addGateway(Gateway gateway) { VpnProfile profile = gateway.getProfile(); + removeGateway(gateway); + profile_manager.addProfile(profile); profile_manager.saveProfile(context, profile); profile_manager.saveProfileList(context); @@ -239,6 +238,64 @@ public final class EIP extends IntentService { Log.d(TAG, "Gateway added: " + gateway.getProfile().getUUIDString()); } + private void removeGateway(Gateway gateway) { + VpnProfile profile = gateway.getProfile(); + removeDuplicatedProfile(profile); + removeDuplicatedGateway(profile); + } + + private void removeDuplicatedProfile(VpnProfile remove) { + if(containsProfile(remove)) + profile_manager.removeProfile(context, duplicatedProfile(remove)); + if(containsProfile(remove)) removeDuplicatedProfile(remove); + } + + private boolean containsProfile(VpnProfile profile) { + Collection profiles = profile_manager.getProfiles(); + for(VpnProfile aux : profiles) { + if (sameConnections(profile.mConnections, aux.mConnections)) { + return true; + } + } + return false; + } + + private VpnProfile duplicatedProfile(VpnProfile profile) { + VpnProfile duplicated = null; + Collection profiles = profile_manager.getProfiles(); + for(VpnProfile aux : profiles) { + if (sameConnections(profile.mConnections, aux.mConnections)) { + duplicated = aux; + } + } + if(duplicated != null) return duplicated; + else throw new NoSuchElementException(profile.getName()); + } + + private boolean sameConnections(Connection[] c1, Connection[] c2) { + int same_connections = 0; + for(Connection c1_aux : c1) { + for(Connection c2_aux : c2) + if(c2_aux.mServerName.equals(c1_aux.mServerName)) { + same_connections++; + break; + } + } + return c1.length == c2.length && c1.length == same_connections; + + } + + private void removeDuplicatedGateway(VpnProfile profile) { + Iterator it = gateways.iterator(); + List gateways_to_remove = new ArrayList<>(); + while(it.hasNext()) { + Gateway aux = it.next(); + if(aux.getProfile().mConnections == profile.mConnections) + gateways_to_remove.add(aux); + } + gateways.removeAll(gateways_to_remove); + } + private void checkCertValidity() { VpnCertificateValidator validator = new VpnCertificateValidator(); int resultCode = validator.isValid(preferences.getString(CERTIFICATE, "")) ? -- cgit v1.2.3 From 407e3767744e39a59845423246a9ad427d933304 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Parm=C3=A9nides=20GV?= Date: Fri, 2 Jan 2015 01:32:22 +0100 Subject: Update vpn profiles correctly. Before we add a new profile, we check if there are any duplicated ones with the same server IPs and ports. If they've the same credentials of the new one, we don't add anything; if not, we remove the old ones and add the new. --- .../main/java/se/leap/bitmaskclient/eip/EIP.java | 22 ++++++++++++++++++---- .../java/se/leap/bitmaskclient/eip/Gateway.java | 15 ++------------- 2 files changed, 20 insertions(+), 17 deletions(-) (limited to 'app/src/main/java/se/leap') diff --git a/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java b/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java index cf6006e5..10d222c2 100644 --- a/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java +++ b/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java @@ -125,8 +125,9 @@ public final class EIP extends IntentService { if(gateway != null && gateway.getProfile() != null) { mReceiver = EipFragment.getReceiver(); launchActiveGateway(); - } - tellToReceiver(ACTION_START_EIP, Activity.RESULT_OK); + tellToReceiver(ACTION_START_EIP, Activity.RESULT_OK); + } else + tellToReceiver(ACTION_START_EIP, Activity.RESULT_CANCELED); } /** @@ -144,6 +145,8 @@ public final class EIP extends IntentService { intent.setAction(Intent.ACTION_MAIN); intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); intent.putExtra(LaunchVPN.EXTRA_NAME, gateway.getProfile().getName()); + Log.d(TAG, gateway.getProfile().mClientCertFilename); + Log.d(TAG, gateway.getProfile().mClientKeyFilename); intent.putExtra(LaunchVPN.EXTRA_HIDELOG, true); startActivity(intent); } @@ -206,7 +209,7 @@ public final class EIP extends IntentService { JSONObject gw = gatewaysDefined.getJSONObject(i); if (isOpenVpnGateway(gw)) { Gateway gateway = new Gateway(eip_definition, context, gw); - if(!gateways.contains(gateway)) { + if(!containsProfileWithSecrets(gateway.getProfile())) { addGateway(gateway); } } @@ -260,6 +263,17 @@ public final class EIP extends IntentService { return false; } + private boolean containsProfileWithSecrets(VpnProfile profile) { + if(!containsProfile(profile)) return false; + + Collection profiles = profile_manager.getProfiles(); + for(VpnProfile aux : profiles) { + return profile.mClientCertFilename.equalsIgnoreCase(aux.mClientCertFilename) + && profile.mClientKeyFilename.equalsIgnoreCase(aux.mClientKeyFilename); + } + + return false; + } private VpnProfile duplicatedProfile(VpnProfile profile) { VpnProfile duplicated = null; Collection profiles = profile_manager.getProfiles(); @@ -290,7 +304,7 @@ public final class EIP extends IntentService { List gateways_to_remove = new ArrayList<>(); while(it.hasNext()) { Gateway aux = it.next(); - if(aux.getProfile().mConnections == profile.mConnections) + if(sameConnections(aux.getProfile().mConnections, profile.mConnections)) gateways_to_remove.add(aux); } gateways.removeAll(gateways_to_remove); diff --git a/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java b/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java index e23f67c7..005d0eec 100644 --- a/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java +++ b/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java @@ -25,6 +25,7 @@ import org.json.JSONException; import org.json.JSONObject; import java.io.IOException; +import java.io.Serializable; import java.io.StringReader; import java.util.Collection; import java.util.Iterator; @@ -42,7 +43,7 @@ import se.leap.bitmaskclient.Dashboard; * @author Sean Leonard * @author Parménides GV */ -public class Gateway { +public class Gateway implements Serializable { private String TAG = Gateway.class.getSimpleName(); @@ -137,16 +138,4 @@ public class Gateway { public int getTimezone() { return timezone; } - - @Override - public boolean equals(Object o) { - if(o instanceof Gateway) { - VpnProfile compared_profile = ((Gateway) o).getProfile(); - return compared_profile.mConnections.equals(mVpnProfile.mConnections) - && compared_profile.mClientCertFilename != mVpnProfile.mClientCertFilename - && compared_profile.mClientKeyFilename != mVpnProfile.mClientKeyFilename; - } - else - return super.equals(o); - } } -- cgit v1.2.3 From 38fdfbdacf414ab85fffd833f57e5fc93b03ad4f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Parm=C3=A9nides=20GV?= Date: Fri, 2 Jan 2015 13:45:31 +0100 Subject: Serialized gateways and correctly updating profiles --- .../java/se/leap/bitmaskclient/EipFragment.java | 2 +- .../java/se/leap/bitmaskclient/OnBootReceiver.java | 3 + .../main/java/se/leap/bitmaskclient/eip/EIP.java | 104 ++++++++++++++++----- .../java/se/leap/bitmaskclient/eip/Gateway.java | 34 +++---- .../leap/bitmaskclient/eip/VpnConfigGenerator.java | 56 +++++------ 5 files changed, 126 insertions(+), 73 deletions(-) (limited to 'app/src/main/java/se/leap') diff --git a/app/src/main/java/se/leap/bitmaskclient/EipFragment.java b/app/src/main/java/se/leap/bitmaskclient/EipFragment.java index a21e0cd1..54432033 100644 --- a/app/src/main/java/se/leap/bitmaskclient/EipFragment.java +++ b/app/src/main/java/se/leap/bitmaskclient/EipFragment.java @@ -187,8 +187,8 @@ public class EipFragment extends Fragment implements Observer { if(!eip_switch.isChecked()) { eip_switch.setChecked(true); - saveStatus(); } + saveStatus(); eipCommand(Constants.ACTION_START_EIP); } diff --git a/app/src/main/java/se/leap/bitmaskclient/OnBootReceiver.java b/app/src/main/java/se/leap/bitmaskclient/OnBootReceiver.java index 3b1033bc..96b87085 100644 --- a/app/src/main/java/se/leap/bitmaskclient/OnBootReceiver.java +++ b/app/src/main/java/se/leap/bitmaskclient/OnBootReceiver.java @@ -4,6 +4,7 @@ import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; import android.content.SharedPreferences; +import android.util.Log; import se.leap.bitmaskclient.eip.Constants; @@ -17,6 +18,8 @@ public class OnBootReceiver extends BroadcastReceiver { preferences = context.getSharedPreferences(Dashboard.SHARED_PREFERENCES, Context.MODE_PRIVATE); boolean provider_configured = !preferences.getString(Provider.KEY, "").isEmpty(); boolean start_on_boot = preferences.getBoolean(Dashboard.START_ON_BOOT, false); + Log.d("OnBootReceiver", "Provider configured " + String.valueOf(provider_configured)); + Log.d("OnBootReceiver", "Start on boot " + String.valueOf(start_on_boot)); if(provider_configured && start_on_boot) { Intent dashboard_intent = new Intent(context, Dashboard.class); dashboard_intent.setAction(Constants.ACTION_START_EIP); diff --git a/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java b/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java index 10d222c2..dcf36a82 100644 --- a/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java +++ b/app/src/main/java/se/leap/bitmaskclient/eip/EIP.java @@ -25,10 +25,14 @@ import android.os.Bundle; import android.os.ResultReceiver; import android.util.Log; +import com.google.gson.Gson; +import com.google.gson.reflect.TypeToken; + import org.json.JSONArray; import org.json.JSONException; import org.json.JSONObject; +import java.lang.reflect.Type; import java.util.ArrayList; import java.util.Collection; import java.util.Iterator; @@ -41,6 +45,7 @@ import de.blinkt.openvpn.core.Connection; import de.blinkt.openvpn.core.ProfileManager; import se.leap.bitmaskclient.Dashboard; import se.leap.bitmaskclient.EipFragment; +import se.leap.bitmaskclient.Provider; import static se.leap.bitmaskclient.eip.Constants.ACTION_CHECK_CERT_VALIDITY; import static se.leap.bitmaskclient.eip.Constants.ACTION_IS_EIP_RUNNING; @@ -87,12 +92,14 @@ public final class EIP extends IntentService { super.onCreate(); context = getApplicationContext(); - profile_manager = ProfileManager.getInstance(context); + preferences = getSharedPreferences(Dashboard.SHARED_PREFERENCES, MODE_PRIVATE); - preferences = getSharedPreferences(Dashboard.SHARED_PREFERENCES, MODE_PRIVATE); - refreshEipDefinition(); + profile_manager = ProfileManager.getInstance(context); + eip_definition = eipDefinitionFromPreferences(); + if(gateways.isEmpty()) + gateways = gatewaysFromPreferences(); } - + @Override protected void onHandleIntent(Intent intent) { String action = intent.getAction(); @@ -122,6 +129,7 @@ public final class EIP extends IntentService { GatewaySelector gateway_selector = new GatewaySelector(gateways); gateway = gateway_selector.select(); + Log.d(TAG, "Connecting to " + gateway.getProfile().getUUIDString()); if(gateway != null && gateway.getProfile() != null) { mReceiver = EipFragment.getReceiver(); launchActiveGateway(); @@ -179,28 +187,42 @@ public final class EIP extends IntentService { * TODO Implement API call to refresh eip-service.json from the provider */ private void updateEIPService() { - refreshEipDefinition(); + eip_definition = eipDefinitionFromPreferences(); if(eip_definition != null) updateGateways(); tellToReceiver(ACTION_UPDATE_EIP_SERVICE, Activity.RESULT_OK); } - private void refreshEipDefinition() { + private JSONObject eipDefinitionFromPreferences() { try { String eip_definition_string = preferences.getString(KEY, ""); if(!eip_definition_string.isEmpty()) { - eip_definition = new JSONObject(eip_definition_string); + return new JSONObject(eip_definition_string); } } catch (JSONException e) { // TODO Auto-generated catch block e.printStackTrace(); } + return null; + } + + private List gatewaysFromPreferences() { + List result; + + String gateways_string = preferences.getString(Gateway.TAG, ""); + Log.d(TAG, "Recovering gateways: " + gateways_string); + Type type_list_gateways = new TypeToken>() {}.getType(); + result = gateways_string.isEmpty() ? + new ArrayList() + : (List) new Gson().fromJson(gateways_string, type_list_gateways); + Log.d(TAG, "Gateways from preferences = " + result.size()); + preferences.edit().remove(Gateway.TAG); + return result; } /** * Walk the list of gateways defined in eip-service.json and parse them into * Gateway objects. - * TODO Store the Gateways (as Serializable) in SharedPreferences */ private void updateGateways(){ try { @@ -208,12 +230,15 @@ public final class EIP extends IntentService { for (int i = 0; i < gatewaysDefined.length(); i++) { JSONObject gw = gatewaysDefined.getJSONObject(i); if (isOpenVpnGateway(gw)) { - Gateway gateway = new Gateway(eip_definition, context, gw); - if(!containsProfileWithSecrets(gateway.getProfile())) { - addGateway(gateway); + JSONObject secrets = secretsConfiguration(); + Gateway aux = new Gateway(eip_definition, secrets, gw); + Log.d(TAG, "Possible new gateway: " + aux.getProfile().getUUIDString()); + if(!containsProfileWithSecrets(aux.getProfile())) { + addGateway(aux); } } } + gatewaysToPreferences(); } catch (JSONException e) { // TODO Auto-generated catch block e.printStackTrace(); @@ -229,6 +254,19 @@ public final class EIP extends IntentService { } } + + private JSONObject secretsConfiguration() { + JSONObject result = new JSONObject(); + try { + result.put(Provider.CA_CERT, preferences.getString(Provider.CA_CERT, "")); + result.put(Constants.PRIVATE_KEY, preferences.getString(Constants.PRIVATE_KEY, "")); + result.put(Constants.CERTIFICATE, preferences.getString(Constants.CERTIFICATE, "")); + } catch (JSONException e) { + e.printStackTrace(); + } + return result; + } + private void addGateway(Gateway gateway) { VpnProfile profile = gateway.getProfile(); removeGateway(gateway); @@ -247,10 +285,12 @@ public final class EIP extends IntentService { removeDuplicatedGateway(profile); } - private void removeDuplicatedProfile(VpnProfile remove) { - if(containsProfile(remove)) - profile_manager.removeProfile(context, duplicatedProfile(remove)); - if(containsProfile(remove)) removeDuplicatedProfile(remove); + private void removeDuplicatedProfile(VpnProfile original) { + if(containsProfile(original)) { + VpnProfile remove = duplicatedProfile(original); + profile_manager.removeProfile(context, remove); + Log.d(TAG, "Removing profile " + remove.getUUIDString()); + }if(containsProfile(original)) removeDuplicatedProfile(original); } private boolean containsProfile(VpnProfile profile) { @@ -264,16 +304,21 @@ public final class EIP extends IntentService { } private boolean containsProfileWithSecrets(VpnProfile profile) { - if(!containsProfile(profile)) return false; - - Collection profiles = profile_manager.getProfiles(); - for(VpnProfile aux : profiles) { - return profile.mClientCertFilename.equalsIgnoreCase(aux.mClientCertFilename) - && profile.mClientKeyFilename.equalsIgnoreCase(aux.mClientKeyFilename); - } - - return false; + boolean result = false; + + if(containsProfile(profile)) { + Collection profiles = profile_manager.getProfiles(); + for(VpnProfile aux : profiles) { + result = result == false ? + sameConnections(profile.mConnections, aux.mConnections) + && profile.mClientCertFilename.equalsIgnoreCase(aux.mClientCertFilename) + && profile.mClientKeyFilename.equalsIgnoreCase(aux.mClientKeyFilename) + : true; + } + } + return result; } + private VpnProfile duplicatedProfile(VpnProfile profile) { VpnProfile duplicated = null; Collection profiles = profile_manager.getProfiles(); @@ -304,12 +349,21 @@ public final class EIP extends IntentService { List gateways_to_remove = new ArrayList<>(); while(it.hasNext()) { Gateway aux = it.next(); - if(sameConnections(aux.getProfile().mConnections, profile.mConnections)) + if(sameConnections(aux.getProfile().mConnections, profile.mConnections)) { gateways_to_remove.add(aux); + Log.d(TAG, "Removing gateway " + aux.getProfile().getUUIDString()); + } } gateways.removeAll(gateways_to_remove); } + private void gatewaysToPreferences() { + Type type_list_gateways = new TypeToken>() {}.getType(); + String gateways_string = new Gson().toJson(gateways, type_list_gateways); + Log.d(TAG, "Saving gateways: " + gateways_string); + preferences.edit().putString(Gateway.TAG, gateways_string).apply(); + } + private void checkCertValidity() { VpnCertificateValidator validator = new VpnCertificateValidator(); int resultCode = validator.isValid(preferences.getString(CERTIFICATE, "")) ? diff --git a/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java b/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java index 005d0eec..daf7d4a7 100644 --- a/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java +++ b/app/src/main/java/se/leap/bitmaskclient/eip/Gateway.java @@ -17,7 +17,6 @@ package se.leap.bitmaskclient.eip; import android.app.Activity; -import android.content.Context; import android.content.SharedPreferences; import android.util.Log; @@ -25,14 +24,10 @@ import org.json.JSONException; import org.json.JSONObject; import java.io.IOException; -import java.io.Serializable; import java.io.StringReader; -import java.util.Collection; -import java.util.Iterator; import de.blinkt.openvpn.VpnProfile; import de.blinkt.openvpn.core.ConfigParser; -import de.blinkt.openvpn.core.ProfileManager; import se.leap.bitmaskclient.Dashboard; /** @@ -43,28 +38,26 @@ import se.leap.bitmaskclient.Dashboard; * @author Sean Leonard * @author Parménides GV */ -public class Gateway implements Serializable { - - private String TAG = Gateway.class.getSimpleName(); +public class Gateway { + public static String TAG = Gateway.class.getSimpleName(); + + private JSONObject general_configuration; + private JSONObject secrets; + private JSONObject gateway; + private String mName; private int timezone; - private JSONObject general_configuration; - private Context context; private VpnProfile mVpnProfile; - private JSONObject mGateway; - /** * Build a gateway object from a JSON OpenVPN gateway definition in eip-service.json * and create a VpnProfile belonging to it. - * - * @param gateway The JSON OpenVPN gateway definition to parse */ - protected Gateway(JSONObject eip_definition, Context context, JSONObject gateway){ + protected Gateway(JSONObject eip_definition, JSONObject secrets, JSONObject gateway){ + + this.gateway = gateway; + this.secrets = secrets; - mGateway = gateway; - - this.context = context; general_configuration = getGeneralConfiguration(eip_definition); timezone = getTimezone(eip_definition); mName = locationAsName(eip_definition); @@ -95,7 +88,7 @@ public class Gateway implements Serializable { try { JSONObject locations = eip_definition.getJSONObject("locations"); - return locations.getJSONObject(mGateway.getString("location")); + return locations.getJSONObject(gateway.getString("location")); } catch (JSONException e) { return new JSONObject(); } @@ -108,8 +101,7 @@ public class Gateway implements Serializable { try { ConfigParser cp = new ConfigParser(); - SharedPreferences preferences = context.getSharedPreferences(Dashboard.SHARED_PREFERENCES, Activity.MODE_PRIVATE); - VpnConfigGenerator vpn_configuration_generator = new VpnConfigGenerator(preferences, general_configuration, mGateway); + VpnConfigGenerator vpn_configuration_generator = new VpnConfigGenerator(general_configuration, secrets, gateway); String configuration = vpn_configuration_generator.generate(); cp.parseConfig(new StringReader(configuration)); diff --git a/app/src/main/java/se/leap/bitmaskclient/eip/VpnConfigGenerator.java b/app/src/main/java/se/leap/bitmaskclient/eip/VpnConfigGenerator.java index a320bee5..6f260f55 100644 --- a/app/src/main/java/se/leap/bitmaskclient/eip/VpnConfigGenerator.java +++ b/app/src/main/java/se/leap/bitmaskclient/eip/VpnConfigGenerator.java @@ -31,15 +31,15 @@ public class VpnConfigGenerator { private JSONObject general_configuration; private JSONObject gateway; - - private static SharedPreferences preferences; + private JSONObject secrets; + public final static String TAG = VpnConfigGenerator.class.getSimpleName(); private final String new_line = System.getProperty("line.separator"); // Platform new line - public VpnConfigGenerator(SharedPreferences preferences, JSONObject general_configuration, JSONObject gateway) { + public VpnConfigGenerator(JSONObject general_configuration, JSONObject secrets, JSONObject gateway) { this.general_configuration = general_configuration; this.gateway = gateway; - VpnConfigGenerator.preferences = preferences; + this.secrets = secrets; } public String generate() { @@ -113,29 +113,33 @@ public class VpnConfigGenerator { } private String secretsConfiguration() { - - String ca = - "" - + new_line - + preferences.getString(Provider.CA_CERT, "") - + new_line - + ""; - - String key = - "" - + new_line - + preferences.getString(Constants.PRIVATE_KEY, "") - + new_line - + ""; - - String openvpn_cert = - "" - + new_line - + preferences.getString(Constants.CERTIFICATE, "") - + new_line - + ""; + try { + String ca = + "" + + new_line + + secrets.getString(Provider.CA_CERT) + + new_line + + ""; + + String key = + "" + + new_line + + secrets.getString(Constants.PRIVATE_KEY) + + new_line + + ""; + + String openvpn_cert = + "" + + new_line + + secrets.getString(Constants.CERTIFICATE) + + new_line + + ""; - return ca + new_line + key + new_line + openvpn_cert; + return ca + new_line + key + new_line + openvpn_cert; + } catch(JSONException e) { + e.printStackTrace(); + return ""; + } } private String androidCustomizations() { -- cgit v1.2.3