commit d38e9e1a819f39fcef9b7ff7ca217f006cd722f9 Author: n8fr8 nathan@guardianproject.info Date: Tue Jan 28 14:30:29 2020 -0500
improve killing of orphaned tor process --- .../torproject/android/service/OrbotService.java | 21 +++++- .../android/service/TorEventHandler.java | 2 +- .../android/service/TorServiceConstants.java | 1 + .../android/service/util/ExternalIPFetcher.java | 6 +- .../torproject/android/service/vpn/VpnUtils.java | 74 +++++++++++++--------- 5 files changed, 69 insertions(+), 35 deletions(-)
diff --git a/orbotservice/src/main/java/org/torproject/android/service/OrbotService.java b/orbotservice/src/main/java/org/torproject/android/service/OrbotService.java index afe8b008..f806e42a 100644 --- a/orbotservice/src/main/java/org/torproject/android/service/OrbotService.java +++ b/orbotservice/src/main/java/org/torproject/android/service/OrbotService.java @@ -44,6 +44,7 @@ import com.jaredrummler.android.shell.CommandResult; import net.freehaven.tor.control.ConfigEntry; import net.freehaven.tor.control.TorControlConnection;
+import org.apache.commons.io.IOUtils; import org.torproject.android.service.util.CustomShell; import org.torproject.android.service.util.CustomTorResourceInstaller; import org.torproject.android.service.util.DummyActivity; @@ -109,7 +110,7 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC private ArrayList<String> configBuffer = null; private ArrayList<String> resetBuffer = null;
- private File fileControlPort; + private File fileControlPort, filePid;
private boolean mConnectivity = true;
@@ -456,6 +457,7 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
private void killAllDaemons() throws Exception { + if (conn != null) { logNotice("Using control port to shutdown Tor");
@@ -470,6 +472,18 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC conn = null; }
+ if (mLastProcessId != -1) + killProcess(mLastProcessId + "", "-9"); + + if (filePid != null && filePid.exists()) + { + List<String> lines = IOUtils.readLines(new FileReader(filePid)); + String torPid = lines.get(0); + killProcess(torPid,"-9"); + + } + + // if that fails, try again using native utils try { killProcess(fileTor, "-9"); // this is -HUP @@ -523,6 +537,7 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
fileTorRc = new File(appBinHome, TORRC_ASSET_KEY); fileControlPort = new File(getFilesDir(), TOR_CONTROL_PORT_FILE); + filePid = new File(getFilesDir(), TOR_PID_FILE);
mHSBasePath = new File( getFilesDir().getAbsolutePath(), @@ -646,6 +661,8 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC extraLines.append("\n"); extraLines.append("ControlPortWriteToFile").append(' ').append(fileControlPort.getCanonicalPath()).append('\n');
+ extraLines.append("PidFile").append(' ').append(filePid.getCanonicalPath()).append('\n'); + // extraLines.append("RunAsDaemon 1").append('\n'); // extraLines.append("AvoidDiskWrites 1").append('\n');
@@ -689,7 +706,7 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC extraLines.append("SocksListenAddress 0.0.0.0").append('\n');
- extraLines.append("HTTPTunnelPort ").append(checkPortOrAuto(HTTP_PROXY_PORT_DEFAULT)).append('\n'); + extraLines.append("HTTPTunnelPort ").append(httpPortPref).append('\n');
if(prefs.getBoolean(OrbotConstants.PREF_CONNECTION_PADDING, false)) { diff --git a/orbotservice/src/main/java/org/torproject/android/service/TorEventHandler.java b/orbotservice/src/main/java/org/torproject/android/service/TorEventHandler.java index 466c4323..def94fcf 100644 --- a/orbotservice/src/main/java/org/torproject/android/service/TorEventHandler.java +++ b/orbotservice/src/main/java/org/torproject/android/service/TorEventHandler.java @@ -215,7 +215,7 @@ public class TorEventHandler implements EventHandler, TorServiceConstants {
if (node.ipAddress == null && (!node.isFetchingInfo) && Prefs.useDebugLogging()) { node.isFetchingInfo = true; - mService.exec(new ExternalIPFetcher(mService, node, TorService.mPortHTTP)); + mService.exec(new ExternalIPFetcher(mService, node, OrbotService.mPortHTTP)); }
isFirstNode = false; diff --git a/orbotservice/src/main/java/org/torproject/android/service/TorServiceConstants.java b/orbotservice/src/main/java/org/torproject/android/service/TorServiceConstants.java index 4962ac29..5776abe9 100644 --- a/orbotservice/src/main/java/org/torproject/android/service/TorServiceConstants.java +++ b/orbotservice/src/main/java/org/torproject/android/service/TorServiceConstants.java @@ -11,6 +11,7 @@ public interface TorServiceConstants { String DIRECTORY_TOR_DATA = "data";
String TOR_CONTROL_PORT_FILE = "control.txt"; + String TOR_PID_FILE = "torpid";
//torrc (tor config file) String TORRC_ASSET_KEY = "torrc"; diff --git a/orbotservice/src/main/java/org/torproject/android/service/util/ExternalIPFetcher.java b/orbotservice/src/main/java/org/torproject/android/service/util/ExternalIPFetcher.java index ae99e7de..080ed961 100644 --- a/orbotservice/src/main/java/org/torproject/android/service/util/ExternalIPFetcher.java +++ b/orbotservice/src/main/java/org/torproject/android/service/util/ExternalIPFetcher.java @@ -2,8 +2,8 @@ package org.torproject.android.service.util;
import org.json.JSONArray; import org.json.JSONObject; +import org.torproject.android.service.OrbotService; import org.torproject.android.service.TorEventHandler; -import org.torproject.android.service.TorService;
import java.io.BufferedReader; import java.io.InputStream; @@ -15,12 +15,12 @@ import java.net.URLConnection;
public class ExternalIPFetcher implements Runnable {
- private TorService mService; + private OrbotService mService; private TorEventHandler.Node mNode; private final static String ONIONOO_BASE_URL = "https://onionoo.torproject.org/details?fields=country_name,as_name,or_addres..."; private int mLocalHttpProxyPort = 8118;
- public ExternalIPFetcher (TorService service, TorEventHandler.Node node, int localProxyPort ) + public ExternalIPFetcher (OrbotService service, TorEventHandler.Node node, int localProxyPort ) { mService = service; mNode = node; diff --git a/orbotservice/src/main/java/org/torproject/android/service/vpn/VpnUtils.java b/orbotservice/src/main/java/org/torproject/android/service/vpn/VpnUtils.java index 5a9901ff..acc15316 100644 --- a/orbotservice/src/main/java/org/torproject/android/service/vpn/VpnUtils.java +++ b/orbotservice/src/main/java/org/torproject/android/service/vpn/VpnUtils.java @@ -1,5 +1,6 @@ package org.torproject.android.service.vpn;
+import android.app.ActivityManager; import android.content.Context; import android.content.SharedPreferences;
@@ -7,7 +8,9 @@ import java.io.BufferedReader; import java.io.File; import java.io.IOException; import java.io.InputStreamReader; +import java.util.List;
+import static android.content.Context.ACTIVITY_SERVICE; import static java.lang.Runtime.getRuntime; import static org.torproject.android.service.vpn.VpnConstants.SHELL_CMD_PS; import static org.torproject.android.service.vpn.VpnPrefs.PREF_TOR_SHARED_PREFS; @@ -20,25 +23,32 @@ public class VpnUtils { }
public static int findProcessId(String command) throws IOException { - Process procPs = getRuntime().exec(SHELL_CMD_PS); - BufferedReader reader = new BufferedReader(new InputStreamReader(procPs.getInputStream()));
- String line; - while ((line = reader.readLine()) != null) { - if (!line.contains("PID") && line.contains(command)) { - String[] lineParts = line.split("\s+"); - try { - return Integer.parseInt(lineParts[1]); //for most devices it is the second - } catch (NumberFormatException e) { - return Integer.parseInt(lineParts[0]); //but for samsungs it is the first - } finally { + String[] cmds = {"ps -ef","ps -A","toolbox ps","busybox ps"}; + + for (int i = 0; i < cmds.length;i++) { + Process procPs = getRuntime().exec(cmds[i]); + + BufferedReader reader = new BufferedReader(new InputStreamReader(procPs.getInputStream())); + + String line; + while ((line = reader.readLine()) != null) { + if (!line.contains("PID") && line.contains(command)) { + String[] lineParts = line.split("\s+"); try { - procPs.destroy(); - } catch (Exception e) { + return Integer.parseInt(lineParts[1]); //for most devices it is the second + } catch (NumberFormatException e) { + return Integer.parseInt(lineParts[0]); //but for samsungs it is the first + } finally { + try { + procPs.destroy(); + } catch (Exception e) { + } } } } } + return -1; }
@@ -46,18 +56,29 @@ public class VpnUtils { killProcess(fileProcBin, "-9"); // this is -KILL }
- public static void killProcess(File fileProcBin, String signal) throws Exception { + public static int killProcess(File fileProcBin, String signal) throws Exception { + int procId = -1; int killAttempts = 0;
- while ((procId = findProcessId(fileProcBin.getCanonicalPath())) != -1) { + while ((procId = findProcessId(fileProcBin.getName())) != -1) { killAttempts++; String pidString = String.valueOf(procId); - try { - getRuntime().exec("busybox killall " + signal + " " + fileProcBin.getName - ()); - } catch (IOException ioe) { + + String[] cmds = {"","busybox ","toolbox "}; + + for (int i = 0; i < cmds.length;i++) { + try { + getRuntime().exec(cmds[i] + "killall " + signal + " " + fileProcBin.getName + ()); + } catch (IOException ioe) { + } + try { + getRuntime().exec(cmds[i] + "killall " + signal + " " + fileProcBin.getCanonicalPath()); + } catch (IOException ioe) { + } } + killProcess(pidString, signal);
try { @@ -69,25 +90,20 @@ public class VpnUtils { if (killAttempts > 4) throw new Exception("Cannot kill: " + fileProcBin.getAbsolutePath()); } + + return procId; }
public static void killProcess(String pidString, String signal) throws Exception {
+ String[] cmds = {"","busybox ","toolbox "};
+ for (int i = 0; i < cmds.length;i++) { try { getRuntime().exec("toolbox kill " + signal + " " + pidString); } catch (IOException ioe) { } - try { - getRuntime().exec("busybox kill " + signal + " " + pidString); - } catch (IOException ioe) { - } - try { - getRuntime().exec("kill " + signal + " " + pidString); - } catch (IOException ioe) { - } - - + }
}