diff options
Diffstat (limited to 'app/src/fil/libre/repwifiapp/activities')
11 files changed, 782 insertions, 56 deletions
diff --git a/app/src/fil/libre/repwifiapp/activities/InputPasswordActivity.java b/app/src/fil/libre/repwifiapp/activities/InputPasswordActivity.java index 6f04d1c..32922c6 100644 --- a/app/src/fil/libre/repwifiapp/activities/InputPasswordActivity.java +++ b/app/src/fil/libre/repwifiapp/activities/InputPasswordActivity.java @@ -49,7 +49,7 @@ public class InputPasswordActivity extends Activity implements OnCheckedChangeLi CheckBox c = (CheckBox) findViewById(R.id.chk_show_pass); c.setOnCheckedChangeListener(this); - setTitle("Input password"); + setTitle(getResources().getString(R.string.title_input_password)); TextView v = (TextView) findViewById(R.id.txt_insert_pass); @@ -81,7 +81,7 @@ public class InputPasswordActivity extends Activity implements OnCheckedChangeLi String pass = txpass.getText().toString(); if (pass.length() == 0) { - Commons.showMessage("Password can't be empty!", this); + Commons.showMessage(getString(R.string.msg_password_empty), this); } this.apinfo.setPassword(pass); diff --git a/app/src/fil/libre/repwifiapp/activities/InputSsidActivity.java b/app/src/fil/libre/repwifiapp/activities/InputSsidActivity.java index 4f3f74c..8b7c60c 100644 --- a/app/src/fil/libre/repwifiapp/activities/InputSsidActivity.java +++ b/app/src/fil/libre/repwifiapp/activities/InputSsidActivity.java @@ -39,7 +39,7 @@ public class InputSsidActivity extends Activity { super.onCreate(icicle); setContentView(R.layout.activity_input_ssid); - setTitle("Insert Network's parameters"); + setTitle(getString(R.string.title_input_ssid)); } @@ -85,7 +85,7 @@ public class InputSsidActivity extends Activity { String ssid = txssid.getText().toString(); if (ssid.length() == 0) { - Commons.showMessage("Network name can't be empty!", this); + Commons.showMessage(getString(R.string.msg_network_name_empty), this); return; } diff --git a/app/src/fil/libre/repwifiapp/activities/Ipv4SettingsActivity.java b/app/src/fil/libre/repwifiapp/activities/Ipv4SettingsActivity.java new file mode 100644 index 0000000..1f15252 --- /dev/null +++ b/app/src/fil/libre/repwifiapp/activities/Ipv4SettingsActivity.java @@ -0,0 +1,181 @@ +// +// Copyright 2017 Filippo "Fil" Bergamo <fil.bergamo@riseup.net> +// +// This file is part of RepWifiApp. +// +// RepWifiApp 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 3 of the License, or +// (at your option) any later version. +// +// RepWifiApp 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. +// +// You should have received a copy of the GNU General Public License +// along with RepWifiApp. If not, see <http://www.gnu.org/licenses/>. +// +// ******************************************************************** + +package fil.libre.repwifiapp.activities; + +import fil.libre.repwifiapp.ActivityLauncher; +import fil.libre.repwifiapp.Commons; +import fil.libre.repwifiapp.R; +import fil.libre.repwifiapp.helpers.AccessPointInfo; +import fil.libre.repwifiapp.helpers.DhcpSettings; +import android.nfc.FormatException; +import android.os.Bundle; +import android.app.Activity; +import android.content.Intent; +import android.view.Menu; +import android.view.View; +import android.widget.CheckBox; +import android.widget.CompoundButton; +import android.widget.EditText; +import android.widget.CompoundButton.OnCheckedChangeListener; + +public class Ipv4SettingsActivity extends Activity implements OnCheckedChangeListener { + + private AccessPointInfo currentNetwork; + private DhcpSettings currentSettings; + + private EditText txtIp; + private EditText txtGw; + private EditText txtMask; + private CheckBox chkDhcp; + + @Override + public void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_ipv4_settings); + + chkDhcp = (CheckBox) findViewById(R.id.chk_use_dhcp); + txtIp = (EditText) findViewById(R.id.txt_static_ip); + txtMask = (EditText) findViewById(R.id.txt_netmask); + txtGw = (EditText) findViewById(R.id.txt_gateway); + + chkDhcp.setOnCheckedChangeListener(this); + + Intent intent = getIntent(); + if (!intent.hasExtra(ActivityLauncher.EXTRA_APINFO)) { + this.setResult(RESULT_CANCELED); + this.finish(); + return; + } + + this.currentNetwork = (AccessPointInfo) intent.getExtras().getSerializable( + ActivityLauncher.EXTRA_APINFO); + if (this.currentNetwork == null) { + this.setResult(RESULT_CANCELED); + this.finish(); + return; + } + + this.currentNetwork = Commons.storage.getSavedNetwork(currentNetwork); + + loadNetwork(); + + } + + @Override + public boolean onCreateOptionsMenu(Menu menu) { + // Inflate the menu; this adds items to the action bar if it is present. + // getMenuInflater().inflate(R.menu.activity_manage_networks, menu); + return true; + } + + private void loadNetwork() { + + setTitle(this.currentNetwork.getSsid()); + currentSettings = this.currentNetwork.getDhcpConfiguration(); + loadSettings(); + + } + + private void loadSettings() { + + if (currentSettings.useDhcp) { + + chkDhcp.setChecked(true); + + txtIp.setText(""); + txtIp.setEnabled(false); + + txtMask.setText(""); + txtMask.setEnabled(false); + + txtGw.setText(""); + txtGw.setEnabled(false); + + } else { + chkDhcp.setChecked(false); + + txtIp.setText(currentSettings.getStaticIP()); + txtIp.setEnabled(true); + + txtMask.setText(currentSettings.getSubnetMaskString()); + txtMask.setEnabled(true); + + txtGw.setText(currentSettings.getDefaultGateway()); + txtGw.setEnabled(true); + } + + } + + @Override + public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) { + + if (buttonView == findViewById(R.id.chk_use_dhcp)) { + currentSettings.useDhcp = isChecked; + loadSettings(); + + } + + } + + public void btnSaveClick(View v) throws FormatException { + + if (chkDhcp.isChecked()) { + currentSettings.useDhcp = true; + + } else { + + String ip = txtIp.getText().toString(); + String mask = txtMask.getText().toString(); + String gw = txtGw.getText().toString(); + + if (!DhcpSettings.isValidAddress(ip)) { + Commons.showMessage(getString(R.string.msg_invalid_ip),this); + return; + } + + if (!DhcpSettings.isValidMaks(mask)) { + Commons.showMessage(getString(R.string.msg_invalid_netmask),this); + return; + } + + if (!DhcpSettings.isValidAddress(gw)) { + Commons.showMessage(getString(R.string.msg_invalid_gateway),this); + return; + } + + currentSettings = new DhcpSettings(chkDhcp.isChecked(), ip, mask, gw); + + } + + currentNetwork.setDhcpConfiguration(currentSettings); + if (Commons.storage.save(currentNetwork)) { + Commons.showMessage(getString(R.string.msg_network_saved),this); + } else { + Commons.showMessage(getString(R.string.msg_network_save_fail),this); + } + + } + + public void btnBackClick(View v) { + finish(); + } + +} diff --git a/app/src/fil/libre/repwifiapp/activities/LongTaskActivity.java b/app/src/fil/libre/repwifiapp/activities/LongTaskActivity.java index e0b4184..a5292d2 100644 --- a/app/src/fil/libre/repwifiapp/activities/LongTaskActivity.java +++ b/app/src/fil/libre/repwifiapp/activities/LongTaskActivity.java @@ -1,3 +1,24 @@ +// +// Copyright 2017 Filippo "Fil" Bergamo <fil.bergamo@riseup.net> +// +// This file is part of RepWifiApp. +// +// RepWifiApp 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 3 of the License, or +// (at your option) any later version. +// +// RepWifiApp 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. +// +// You should have received a copy of the GNU General Public License +// along with RepWifiApp. If not, see <http://www.gnu.org/licenses/>. +// +// ******************************************************************** + + package fil.libre.repwifiapp.activities; import fil.libre.repwifiapp.ActivityLauncher; @@ -99,21 +120,21 @@ public class LongTaskActivity extends Activity { // Extract AccessPointInfo input = intent.getExtras().getSerializable(ActivityLauncher.EXTRA_APINFO); currentNetwork = (AccessPointInfo) input; - setTitle("Connecting to " + currentNetwork.getSsid() + "..."); - setMessage("Connecting to " + currentNetwork.getSsid() + "..."); + setTitle(getString(R.string.msg_connecting_to) + " " + currentNetwork.getSsid() + "..."); + setMessage(getString(R.string.msg_connecting_to) + " " + currentNetwork.getSsid() + "..."); break; case ActivityLauncher.RequestCode.NETWORKS_GET: - setTitle("Scanning..."); - setMessage("Scanning for Networks..."); + setTitle(getString(R.string.title_scanning)); + setMessage(getString(R.string.msg_scanning_for_nets)); case ActivityLauncher.RequestCode.STATUS_GET: - setTitle("Checking status..."); - setMessage("Checking status..."); + setTitle(getString(R.string.msg_checking_status)); + setMessage(getString(R.string.msg_checking_status)); default: - setTitle("Please wait..."); - setMessage("Please wait..."); + setTitle(getString(R.string.msg_please_wait)); + setMessage(getString(R.string.msg_please_wait)); break; } diff --git a/app/src/fil/libre/repwifiapp/activities/MainActivity.java b/app/src/fil/libre/repwifiapp/activities/MainActivity.java index 6e667bf..7a22416 100644 --- a/app/src/fil/libre/repwifiapp/activities/MainActivity.java +++ b/app/src/fil/libre/repwifiapp/activities/MainActivity.java @@ -20,7 +20,6 @@ package fil.libre.repwifiapp.activities; -import java.io.IOException; import java.net.SocketException; import fil.libre.repwifiapp.ActivityLauncher; import fil.libre.repwifiapp.Commons; @@ -29,8 +28,10 @@ import fil.libre.repwifiapp.ActivityLauncher.RequestCode; import fil.libre.repwifiapp.helpers.AccessPointInfo; import fil.libre.repwifiapp.helpers.ConnectionStatus; import fil.libre.repwifiapp.helpers.NetworkManager; +import fil.libre.repwifiapp.helpers.OpenVpnManager; import fil.libre.repwifiapp.helpers.RootCommand; import fil.libre.repwifiapp.helpers.Utils; +import fil.libre.repwifiapp.helpers.WpaSupplicant; import android.os.Bundle; import android.content.BroadcastReceiver; import android.content.Context; @@ -59,8 +60,16 @@ public class MainActivity extends MenuEnabledActivity { return; } + if (! Commons.storage.updateStorageVersion()){ + Utils.logError("Failed to convert storage file to new version!"); + } + setImage(); setUsbDeviceMonitor(); + setVersionOnTitle(); + + OpenVpnManager.initialize(this); + } @Override @@ -149,11 +158,6 @@ public class MainActivity extends MenuEnabledActivity { handleFinishedConnecting(conres, i); break; - case RequestCode.STATUS_GET: - ConnectionStatus status = (ConnectionStatus) intent.getExtras().getSerializable( - ActivityLauncher.EXTRA_CONSTATUS); - handleResultGetStatus(status); - break; case RequestCode.NETWORKS_GET: AccessPointInfo[] nets = (AccessPointInfo[]) intent.getExtras().getSerializable( @@ -182,6 +186,7 @@ public class MainActivity extends MenuEnabledActivity { } break; + default: break; @@ -190,6 +195,23 @@ public class MainActivity extends MenuEnabledActivity { } + private void setVersionOnTitle() { + + try { + + String vers = getPackageManager().getPackageInfo(getPackageName(), 0).versionName; + if (vers == null) { + return; + } + + setTitle(getTitle() + " - v." + vers); + + } catch (Exception e) { + Utils.logError("Error while setting version on MainActivity's title.", e); + } + + } + private void setImage() { ImageView img = (ImageView) findViewById(R.id.img_logo); @@ -197,7 +219,7 @@ public class MainActivity extends MenuEnabledActivity { try { Drawable d = Drawable.createFromStream(getAssets().open("repwifi-logo-0.png"), null); img.setImageDrawable(d); - } catch (IOException e) { + } catch (Exception e) { Utils.logError("Error while loading logo image", e); } @@ -224,6 +246,7 @@ public class MainActivity extends MenuEnabledActivity { } private boolean checkConditions() { + return (checkRootEnabled() && checkInterface(true)); } @@ -233,7 +256,7 @@ public class MainActivity extends MenuEnabledActivity { String msg = ""; try { - res = Commons.connectionEngine.isInterfaceAvailable(Commons.INTERFACE_NAME); + res = Commons.connectionEngine.isInterfaceAvailable(WpaSupplicant.INTERFACE_NAME); } catch (SocketException e) { Utils.logError("SocketException during isInterfaceAvailable()", e); msg = "Error while retrieving interface list!"; @@ -258,7 +281,7 @@ public class MainActivity extends MenuEnabledActivity { int excode = -1; try { - excode = su.execute(); + excode = su.testRootAccess(); } catch (Exception e) { Utils.logError("Error while trying to get first Super User access.", e); excode = -1; @@ -304,7 +327,7 @@ public class MainActivity extends MenuEnabledActivity { if (i.needsPassword()) { - // try to fetch network's password from storage + // try to fetch network's configuration from storage AccessPointInfo fromStorage = Commons.storage.getSavedNetwork(i); if (fromStorage == null) { @@ -327,12 +350,6 @@ public class MainActivity extends MenuEnabledActivity { launcher.launchLongTaskActivityConnect(i); } - private void handleResultGetStatus(ConnectionStatus status) { - if (status != null && status.isConnected()) { - launcher.launchStatusActivity(status); - } - } - private void handleFinishedConnecting(boolean connectionResult, AccessPointInfo info) { if (connectionResult && info.needsPassword()) { @@ -345,13 +362,13 @@ public class MainActivity extends MenuEnabledActivity { // Save network if (Commons.storage.save(info)) { - Toast toast2 = Toast.makeText(getApplicationContext(), "Network Saved!", - Toast.LENGTH_LONG); + Toast toast2 = Toast.makeText(getApplicationContext(), + getString(R.string.msg_network_saved), Toast.LENGTH_LONG); toast2.show(); } else { - Toast toast2 = Toast.makeText(getApplicationContext(), "FAILED to save network!", - Toast.LENGTH_LONG); + Toast toast2 = Toast.makeText(getApplicationContext(), + getString(R.string.msg_network_save_fail), Toast.LENGTH_LONG); toast2.show(); } @@ -360,8 +377,8 @@ public class MainActivity extends MenuEnabledActivity { } else { // alert that connection failed - Toast toast = Toast.makeText(getApplicationContext(), "FAILED to connect!", - Toast.LENGTH_LONG); + Toast toast = Toast.makeText(getApplicationContext(), + getString(R.string.msg_connect_fail), Toast.LENGTH_LONG); toast.show(); } } @@ -371,9 +388,9 @@ public class MainActivity extends MenuEnabledActivity { NetworkManager manager = new NetworkManager(Commons.getNetworkStorageFile()); String msg = ""; if (manager.remove(info)) { - msg = "Network info deleted!"; + msg = getString(R.string.msg_netinfo_deleted); } else { - msg = "FAILED to delete network info!"; + msg = getString(R.string.msg_netinfo_delete_fail); } Toast toast = Toast.makeText(this, msg, Toast.LENGTH_LONG); @@ -437,7 +454,7 @@ public class MainActivity extends MenuEnabledActivity { } catch (Exception e) { Utils.logError("Error while autoconnecting", e); - Commons.showMessage("An error occured while trying to auto-connect", this); + Commons.showMessage(getString(R.string.msg_autoconnect_error), this); } } diff --git a/app/src/fil/libre/repwifiapp/activities/MenuEnabledActivity.java b/app/src/fil/libre/repwifiapp/activities/MenuEnabledActivity.java index 0edfcf0..f5c8516 100644 --- a/app/src/fil/libre/repwifiapp/activities/MenuEnabledActivity.java +++ b/app/src/fil/libre/repwifiapp/activities/MenuEnabledActivity.java @@ -1,20 +1,60 @@ +// +// Copyright 2017 Filippo "Fil" Bergamo <fil.bergamo@riseup.net> +// +// This file is part of RepWifiApp. +// +// RepWifiApp 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 3 of the License, or +// (at your option) any later version. +// +// RepWifiApp 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. +// +// You should have received a copy of the GNU General Public License +// along with RepWifiApp. If not, see <http://www.gnu.org/licenses/>. +// +// ******************************************************************** + package fil.libre.repwifiapp.activities; +import java.lang.reflect.Field; +import fil.libre.repwifiapp.Commons; import fil.libre.repwifiapp.R; +import fil.libre.repwifiapp.helpers.RootCommand; import android.app.Activity; +import android.app.AlertDialog; +import android.content.DialogInterface; import android.content.Intent; import android.view.Menu; import android.view.MenuItem; +import android.view.ViewConfiguration; public class MenuEnabledActivity extends Activity { @Override + protected void onCreate(android.os.Bundle savedInstanceState) { + try { + ViewConfiguration config = ViewConfiguration.get(this); + Field menuKeyField = ViewConfiguration.class.getDeclaredField("sHasPermanentMenuKey"); + if (menuKeyField != null) { + menuKeyField.setAccessible(true); + menuKeyField.setBoolean(config, false); + } + } catch (Exception ignored) { + } + super.onCreate(savedInstanceState); + }; + + @Override public boolean onCreateOptionsMenu(Menu menu) { // Inflate the menu; this adds items to the action bar if it is present. getMenuInflater().inflate(R.menu.activity_main, menu); return true; } - + @Override public boolean onOptionsItemSelected(MenuItem item) { // Handle item selection @@ -27,6 +67,10 @@ public class MenuEnabledActivity extends Activity { case R.id.menu_config: launchSettingsActivity(); break; + + case R.id.menu_btn_closeapp: + CloseApplication(false); + break; default: break; @@ -46,4 +90,46 @@ public class MenuEnabledActivity extends Activity { // intent.setFlags(Intent.FLAG_ACTIVITY_NO_HISTORY); startActivity(intent); } + + protected void CloseApplication(boolean silent) { + + if (silent) { + + Commons.connectionEngine.disconnect(); + Commons.killBackEnd(this, true); + super.onDestroy(); + RootCommand.executeRootCmd("am force-stop " + getPackageName()); + + } else { + + String msg = getString(R.string.confirm_exit_app); + AlertDialog.Builder dlgAlert = new AlertDialog.Builder(this, + R.style.Theme_RepWifiDialogTheme); + dlgAlert.setMessage(msg); + dlgAlert.setPositiveButton(this.getString(android.R.string.ok), + new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int whichButton) { + CloseApplication(true); + return; + } + }); + dlgAlert.setNegativeButton(getString(android.R.string.cancel), + new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int whichButton) { + return; + } + }); + + dlgAlert.setCancelable(false); + AlertDialog diag = dlgAlert.create(); + + diag.show(); + return; + + } + + } + } diff --git a/app/src/fil/libre/repwifiapp/activities/NetworkDetailsActivity.java b/app/src/fil/libre/repwifiapp/activities/NetworkDetailsActivity.java index 325d546..f2a8944 100644 --- a/app/src/fil/libre/repwifiapp/activities/NetworkDetailsActivity.java +++ b/app/src/fil/libre/repwifiapp/activities/NetworkDetailsActivity.java @@ -22,6 +22,7 @@ package fil.libre.repwifiapp.activities; import java.util.Date; import fil.libre.repwifiapp.ActivityLauncher; +import fil.libre.repwifiapp.Commons; import fil.libre.repwifiapp.R; import fil.libre.repwifiapp.helpers.AccessPointInfo; import android.os.Bundle; @@ -69,6 +70,12 @@ public class NetworkDetailsActivity extends Activity implements OnCheckedChangeL } @Override + protected void onStart() { + super.onStart(); + currentNetwork = Commons.storage.getSavedNetwork(currentNetwork); + }; + + @Override public boolean onCreateOptionsMenu(Menu menu) { // Inflate the menu; this adds items to the action bar if it is present. // getMenuInflater().inflate(R.menu.activity_manage_networks, menu); @@ -88,17 +95,26 @@ public class NetworkDetailsActivity extends Activity implements OnCheckedChangeL if (lastused > 0) { Date ts = new Date(lastused); String formstring = "dd-MMM-yyyy kk:mm:ss"; - v.append("\nLast Used: " + DateFormat.format(formstring, ts)); + v.append("\n" + getString(R.string.text_netinfo_last_used) + ": " + + DateFormat.format(formstring, ts)); } if (showPassword) { - v.append("\n\nPassword:\n" + this.currentNetwork.getPassword()); + v.append("\n\n" + getString(R.string.text_password) + ":\n" + this.currentNetwork.getPassword()); } else { v.append("\n\n\n"); } } + public void btnIpSettingsClick(View v){ + new ActivityLauncher(this).launchIpSettingsActivity(currentNetwork); + } + + public void btnVpnSettingsClick(View v){ + new ActivityLauncher(this).launchVpnSettingsActivity(currentNetwork); + } + public void btnDeleteClick(View v) { String msg = getResources().getString(R.string.msg_confirm_delete_network); diff --git a/app/src/fil/libre/repwifiapp/activities/SelectNetworkActivity.java b/app/src/fil/libre/repwifiapp/activities/SelectNetworkActivity.java index 341fb68..51baed8 100644 --- a/app/src/fil/libre/repwifiapp/activities/SelectNetworkActivity.java +++ b/app/src/fil/libre/repwifiapp/activities/SelectNetworkActivity.java @@ -48,7 +48,7 @@ public class SelectNetworkActivity extends Activity implements OnClickListener { super.onCreate(savedInstanceState); setContentView(R.layout.activity_select_network); - setTitle("Select network"); + setTitle(getString(R.string.title_activity_select_network)); getNetworks(); @@ -135,17 +135,17 @@ public class SelectNetworkActivity extends Activity implements OnClickListener { if (info == null) { Utils.logError("Unable to retrieve network list!"); - writeOut("Unable to retrieve network list!"); + writeOut(getString(R.string.msg_network_list_fail)); return; } if (info.length == 0) { - writeOut("No network found."); + writeOut(getString(R.string.msg_no_network)); toggleBtnRescan(true); return; } - writeOut("Select the network you want to connect to:"); + writeOut(getString(R.string.msg_select_network_connect)); toggleBtnRescan(false); for (AccessPointInfo i : info) { @@ -162,7 +162,7 @@ public class SelectNetworkActivity extends Activity implements OnClickListener { return; } - writeOut("Select network info to manage:"); + writeOut(getString(R.string.msg_select_network_manage)); toggleBtnRescan(false); for (AccessPointInfo i : info) { diff --git a/app/src/fil/libre/repwifiapp/activities/SettingsActivity.java b/app/src/fil/libre/repwifiapp/activities/SettingsActivity.java index 6f14748..36e0e1f 100644 --- a/app/src/fil/libre/repwifiapp/activities/SettingsActivity.java +++ b/app/src/fil/libre/repwifiapp/activities/SettingsActivity.java @@ -1,9 +1,31 @@ +// +// Copyright 2017 Filippo "Fil" Bergamo <fil.bergamo@riseup.net> +// +// This file is part of RepWifiApp. +// +// RepWifiApp 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 3 of the License, or +// (at your option) any later version. +// +// RepWifiApp 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. +// +// You should have received a copy of the GNU General Public License +// along with RepWifiApp. If not, see <http://www.gnu.org/licenses/>. +// +// ******************************************************************** + + package fil.libre.repwifiapp.activities; import org.apache.http.conn.util.InetAddressUtils; import java.util.List; import fil.libre.repwifiapp.Commons; import fil.libre.repwifiapp.R; +import fil.libre.repwifiapp.helpers.Utils; import android.os.Bundle; import android.preference.EditTextPreference; import android.preference.Preference; @@ -31,6 +53,7 @@ public class SettingsActivity extends PreferenceActivity { addPreferencesFromResource(R.xml.debug_settings); setConfirmKillBackend(); + setDumpFileClick(); } @@ -48,6 +71,24 @@ public class SettingsActivity extends PreferenceActivity { } + private void setDumpFileClick() { + Preference pref = getPreferenceScreen().findPreference("pref_dump_log"); + pref.setOnPreferenceClickListener(new Preference.OnPreferenceClickListener() { + + @Override + public boolean onPreferenceClick(Preference p) { + if (Utils.dumpLogcatToFile(Commons.getLogDumpFile())) { + Commons.showMessage(getString(R.string.msg_log_saved) + ": \n" + Commons.getLogDumpFile(), + getActivity()); + + } else { + Commons.showMessage(getString(R.string.msg_log_save_fail), getActivity()); + } + return true; + } + }); + } + } public static class GeneralSettingFragment extends PreferenceFragment { @@ -76,7 +117,7 @@ public class SettingsActivity extends PreferenceActivity { || InetAddressUtils.isIPv4Address((String) newValue)) { return true; } else { - Commons.showMessage("ERROR:\nWrong IP format!", getActivity()); + Commons.showMessage(getString(R.string.msg_error_ip_format), getActivity()); return false; } } diff --git a/app/src/fil/libre/repwifiapp/activities/ShowStatusActivity.java b/app/src/fil/libre/repwifiapp/activities/ShowStatusActivity.java index 0fb8992..21bfc4c 100644 --- a/app/src/fil/libre/repwifiapp/activities/ShowStatusActivity.java +++ b/app/src/fil/libre/repwifiapp/activities/ShowStatusActivity.java @@ -23,9 +23,14 @@ package fil.libre.repwifiapp.activities; import fil.libre.repwifiapp.ActivityLauncher; import fil.libre.repwifiapp.Commons; import fil.libre.repwifiapp.R; +import fil.libre.repwifiapp.ActivityLauncher.RequestCode; +import fil.libre.repwifiapp.helpers.AccessPointInfo; import fil.libre.repwifiapp.helpers.ConnectionStatus; +import fil.libre.repwifiapp.helpers.OpenVpnManager; import fil.libre.repwifiapp.helpers.Utils; +import android.content.Intent; import android.os.Bundle; +import android.os.RemoteException; import android.view.View; import android.widget.Button; import android.widget.TextView; @@ -35,6 +40,8 @@ public class ShowStatusActivity extends MenuEnabledActivity { private ConnectionStatus status; + // private AccessPointInfo info; + @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); @@ -45,14 +52,45 @@ public class ShowStatusActivity extends MenuEnabledActivity { ActivityLauncher.EXTRA_CONSTATUS); } - showStatus(false); + try { + showStatus(false); + } catch (Exception e) { + Utils.logError("Exception on showStatus", e); + } } @Override public void onRestart() { super.onRestart(); - showStatus(true); + try { + showStatus(true); + } catch (Exception e) { + Utils.logError("Exception on showStatus", e); + } + } + + @Override + public void onActivityResult(int requestCode, int resultCode, Intent intent) { + + switch (requestCode) { + + case RequestCode.VPN_PERMISSION: + + if (resultCode == RESULT_OK) { + endLaunchVpn(true); + } else { + endLaunchVpn(false); + } + + break; + + default: + + break; + + } + } private void setMessage(String msg) { @@ -60,7 +98,7 @@ public class ShowStatusActivity extends MenuEnabledActivity { view.setText(msg); } - private void showStatus(boolean refresh) { + private void showStatus(boolean refresh) throws Exception { if (refresh || status == null) { this.status = Commons.connectionEngine.getConnectionStatus(); @@ -71,12 +109,14 @@ public class ShowStatusActivity extends MenuEnabledActivity { } else if (this.status.isConnected()) { Utils.logDebug("StatusActivity isConnected,showing buttons"); - setMessage("Connected to " + status.SSID + "\n\n" + "IP Address: " + status.IP + "\n"); + setMessage(getString(R.string.msg_connected_to) + " " + status.SSID + "\n\n" + + getString(R.string.text_ip_address) + ": " + status.IP + "\n"); toggleBtnDisconnect(true); - + beginLauncVpn(); + } else { Utils.logDebug("StatusActivity status Else"); - setMessage("Status:\n" + status.status); + setMessage(getString(R.string.text_status) + ":\n" + status.status); toggleBtnDisconnect(false); } @@ -103,21 +143,144 @@ public class ShowStatusActivity extends MenuEnabledActivity { public void onBtnDisconnectClick(View v) { + disconnectVpn(); + boolean res = Commons.connectionEngine.disconnect(); String msg = ""; if (res) { - msg = "Disconnected."; + msg = getString(R.string.msg_disconnected); } else { - msg = "FAILED to disconnect!"; + msg = getString(R.string.msg_disconnect_fail); } Toast toast = Toast.makeText(getApplicationContext(), msg, Toast.LENGTH_SHORT); toast.show(); - showStatus(true); + try { + showStatus(true); + } catch (Exception e) { + Utils.logError("Exception on showStatus", e); + } + + } + + private void disconnectVpn() { + + if (! OpenVpnManager.isVpnConnected()){ + return; + } + + if (OpenVpnManager.disconnect()) { + Toast t = Toast.makeText(this, getString(R.string.msg_vpn_disconnect), + Toast.LENGTH_LONG); + t.show(); + + } else { + Commons.showMessage(getString(R.string.msg_vpn_disconnect_error), this); + } + + } + + private void beginLauncVpn() throws Exception { + + if (OpenVpnManager.isVpnConnected()){ + // already connected; + return; + } + + if (!OpenVpnManager.isExternalAppInstalled(this)) { + Utils.logDebug("External VPN app not installed."); + return; + } + + if (getVpnNameIfAny() == null){ + Utils.logDebug("No vpn profile set. Exiting beginLaunchVpn()"); + return; + } + + // first, we make sure we have permission to use the vpn service. + Intent pi; + + try { + pi = OpenVpnManager.askApiPermissionsGetIntent(); + } catch (RemoteException e) { + Utils.logError("Exception while asking for VPN permission", e); + Toast t = Toast.makeText(getApplicationContext(), getString(R.string.msg_vpn_connect_error), Toast.LENGTH_LONG); + t.show(); + return; + + } + + if (pi == null){ + // no need to ask for permission + Utils.logDebug("No need for vpn permission: going to endLaunchVpn."); + endLaunchVpn(true); + + } else{ + // launch the intent to ask permission + Utils.logDebug("Need to ask for vpn permission. Starting intent.."); + startActivityForResult(pi, ActivityLauncher.RequestCode.VPN_PERMISSION); + } } + private void endLaunchVpn(boolean permissionGranted) { + + try { + + if (!permissionGranted) { + // warn user that permission must be granted + Utils.logDebug("User rejected vpn permission."); + String msg = getString(R.string.msg_vpn_no_permission).replace( + OpenVpnManager.PLACEHOLDER_APPNAME, OpenVpnManager.APP_COMMON_NAME); + Commons.showMessage(msg, this); + return; + } + + String profname = getVpnNameIfAny(); + + // check if profile exists + String profUuid = OpenVpnManager.getUuidFromName(profname); + if (profUuid == null){ + // warn user that selected profile doesn't exist + Commons.showMessage(getString(R.string.msg_vpn_wrong_profile), this); + return; + } + + if (OpenVpnManager.startVpn(profUuid)){ + Toast t = Toast.makeText(this, getString(R.string.msg_vpn_launched), Toast.LENGTH_LONG); + t.show(); + } else { + Commons.showMessage(getString(R.string.msg_vpn_connect_error),this); + } + + } catch (Exception e) { + Utils.logError("Exception while endLaunchVpn", e); + + } + + } + + private String getVpnNameIfAny(){ + + if (status == null) { + return null; + } + + AccessPointInfo i = status.getNetworkDetails(); + if (i == null) { + return null; + } + + String profname = i.getVpnProfileName(); + if (profname == null || profname.isEmpty()) { + return null; + } else { + return profname; + } + + } + public void onBtnMainClick(View v) { finish(); } @@ -126,5 +289,5 @@ public class ShowStatusActivity extends MenuEnabledActivity { public void onBackPressed() { moveTaskToBack(true); } - + } diff --git a/app/src/fil/libre/repwifiapp/activities/VpnSettingsActivity.java b/app/src/fil/libre/repwifiapp/activities/VpnSettingsActivity.java new file mode 100644 index 0000000..b9dab93 --- /dev/null +++ b/app/src/fil/libre/repwifiapp/activities/VpnSettingsActivity.java @@ -0,0 +1,201 @@ +// +// Copyright 2017 Filippo "Fil" Bergamo <fil.bergamo@riseup.net> +// +// This file is part of RepWifiApp. +// +// RepWifiApp 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 3 of the License, or +// (at your option) any later version. +// +// RepWifiApp 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. +// +// You should have received a copy of the GNU General Public License +// along with RepWifiApp. If not, see <http://www.gnu.org/licenses/>. +// +// ******************************************************************** + +package fil.libre.repwifiapp.activities; + +import java.util.List; +import fil.libre.repwifiapp.ActivityLauncher; +import fil.libre.repwifiapp.Commons; +import fil.libre.repwifiapp.R; +import fil.libre.repwifiapp.ActivityLauncher.RequestCode; +import fil.libre.repwifiapp.helpers.AccessPointInfo; +import fil.libre.repwifiapp.helpers.OpenVpnManager; +import fil.libre.repwifiapp.helpers.Utils; +import android.os.Bundle; +import android.app.Activity; +import android.content.Intent; +import android.view.Menu; +import android.view.View; +import android.widget.ArrayAdapter; +import android.widget.Button; +import android.widget.Spinner; +import android.widget.TextView; + +public class VpnSettingsActivity extends Activity { + + private AccessPointInfo currentNetwork; + private Spinner spinProfile; + private TextView summaryView; + + @Override + public void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_vpn_settings); + + String title = getString(R.string.title_activity_vpn_settings); + + Intent intent = getIntent(); + if (!intent.hasExtra(ActivityLauncher.EXTRA_APINFO)) { + this.setResult(RESULT_CANCELED); + this.finish(); + return; + } + + this.currentNetwork = (AccessPointInfo) intent.getExtras().getSerializable( + ActivityLauncher.EXTRA_APINFO); + if (this.currentNetwork == null) { + this.setResult(RESULT_CANCELED); + this.finish(); + return; + } + + this.currentNetwork = Commons.storage.getSavedNetwork(currentNetwork); + this.spinProfile = (Spinner)findViewById(R.id.spin_vpn_profile); + this.summaryView = (TextView)findViewById(R.id.lbl_vpn_settings); + String summary = getString(R.string.summary_vpn_settings).replace(OpenVpnManager.PLACEHOLDER_APPNAME, OpenVpnManager.APP_COMMON_NAME); + summaryView.setText(summary); + + title += " " + currentNetwork.getSsid(); + this.setTitle(title); + + if (!checkExternalApp()){ + toggleSettingsEnabled(false); + } else { + initVpnManager(); + } + + } + + + @Override + public void onActivityResult(int requestCode, int resultCode, Intent intent) { + + switch (requestCode) { + + case RequestCode.VPN_PERMISSION: + + if (resultCode != RESULT_OK) { + toggleSettingsEnabled(false); + Utils.logDebug("User rejected vpn permission."); + String msg = getString(R.string.msg_vpn_no_permission).replace( + OpenVpnManager.PLACEHOLDER_APPNAME, OpenVpnManager.APP_COMMON_NAME); + Commons.showMessage(msg, this); + return; + } + + break; + + default: + + break; + + } + + } + + + @Override + public boolean onCreateOptionsMenu(Menu menu) { + return true; + } + + private void initVpnManager(){ + + try { + + Intent intentAllow = OpenVpnManager.askApiPermissionsGetIntent(); + if (intentAllow != null){ + startActivityForResult(intentAllow, ActivityLauncher.RequestCode.VPN_PERMISSION); + } + + List<String> profiles = OpenVpnManager.getExistingProfiles(); + if (profiles.size() == 0){ + String msg = getString(R.string.msg_vpn_no_profile).replace(OpenVpnManager.PLACEHOLDER_APPNAME, OpenVpnManager.APP_COMMON_NAME); + Commons.showMessage(msg, this); + toggleSettingsEnabled(false); + return; + } + Spinner spin = (Spinner)findViewById(R.id.spin_vpn_profile); + + ArrayAdapter<String> adapter = new ArrayAdapter<String>(this,android.R.layout.simple_spinner_dropdown_item,profiles); + adapter.insert("",0); + spin.setAdapter(adapter); + spin.setSelection(adapter.getPosition(currentNetwork.getVpnProfileName())); + + } catch (Exception e) { + Utils.logError("Exception while creating openvpnmanager",e); + Commons.showMessage(getString(R.string.msg_vpn_connect_error)); + toggleSettingsEnabled(false); + } + + } + + private boolean checkExternalApp(){ + + if (! OpenVpnManager.isExternalAppInstalled(this)){ + String msg = getString(R.string.text_vpn_package_missing).replace(OpenVpnManager.PLACEHOLDER_APPNAME, OpenVpnManager.APP_COMMON_NAME); + Commons.showMessage(msg, this); + toggleSettingsEnabled(false); + return false; + } else { + return true; + } + + } + + private void toggleSettingsEnabled(boolean enabled){ + + spinProfile.setEnabled(enabled); + + Button b = (Button)findViewById(R.id.btn_save_vpn_settings); + b.setEnabled(enabled); + + } + + public void btnSaveClick(View v){ + + String vpnProf = (String)spinProfile.getSelectedItem(); + + /*if (! vpnProf.isEmpty()){ + // check if profile name exists + if( OpenVpnManager.getUuidFromName(vpnProf) == null){ + Commons.showMessage(getString(R.string.msg_vpn_wrong_profile), this); + return; + } + + }*/ + + // save profile + currentNetwork.setVpnProfileName(vpnProf); + Commons.storage.save(currentNetwork); + + terminate(); + + } + + public void btnBackClick(View v){ + terminate(); + } + + private void terminate(){ + finish(); + } + +} |