Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ensure TorService properly shuts down whenever the tor thread stops #65

Merged

Conversation

eighthave
Copy link
Member

@eighthave eighthave commented Dec 17, 2021

This unnests the try/finally block that was added in pull #59, and moves it to the main try block, where it now handles the whole shutdown procedure.

@grote @akwizgran

The intention of this is probably easier to see when the diff starts from before 09de98d in #59:

--- a/tor-android-binary/src/main/java/org/torproject/jni/TorService.java
+++ b/tor-android-binary/src/main/java/org/torproject/jni/TorService.java
@@ -7,6 +7,7 @@ import android.os.Binder;
 import android.os.FileObserver;
 import android.os.IBinder;
 import android.os.Process;
+import android.util.Log;
 
 import net.freehaven.tor.control.RawEventListener;
 import net.freehaven.tor.control.TorControlCommands;
@@ -24,6 +25,7 @@ import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.concurrent.CountDownLatch;
 import java.util.concurrent.TimeUnit;
+import java.util.concurrent.locks.ReentrantLock;
 
 import androidx.annotation.Nullable;
 import androidx.localbroadcastmanager.content.LocalBroadcastManager;
@@ -167,6 +166,12 @@ public class TorService extends Service {
 
     private TorControlConnection torControlConnection;
 
+    /**
+     * This lock must be acquired before calling createTorConfiguration() and
+     * held until mainConfigurationFree() has been called.
+     */
+    private static final ReentrantLock runLock = new ReentrantLock();
+
     private native String apiGetProviderVersion();
 
     private native boolean createTorConfiguration();

@@ -314,6 +320,11 @@ public class TorService extends Service {
                         httpTunnelPort = Integer.toString(8118);
                     }
 
+                    if (runLock.isLocked()) {
+                        Log.i(TAG, "Waiting for lock");
+                    }
+                    runLock.lock();
+                    Log.i(TAG, "Acquired lock");
                     createTorConfiguration();
                     ArrayList<String> lines = new ArrayList<>(Arrays.asList("tor", "--verify-config", // must always be here
                             "--RunAsDaemon", "0",
@@ -363,11 +374,16 @@ public class TorService extends Service {
                 } catch (IllegalStateException | IllegalArgumentException | InterruptedException e) {
                     e.printStackTrace();
                     broadcastError(context, e);
+                } finally {
                     broadcastStatus(context, STATUS_STOPPING);
+                    mainConfigurationFree();
+                    Log.i(TAG, "Releasing lock");
+                    runLock.unlock();
                     TorService.this.stopSelf();
                 }
             }
         }.start();
+
     }
 
     @Override
@@ -377,7 +393,6 @@ public class TorService extends Service {
             torControlConnection.removeRawEventListener(startedEventListener);
         }
         shutdownTor(TorControlCommands.SIGNAL_SHUTDOWN);
-        mainConfigurationFree();
         broadcastStatus(TorService.this, STATUS_OFF);
     }
 

@eighthave
Copy link
Member Author

Also, working on this made me think: what happens when TorService is given kill -9 from Android and the finally block isn't run? Will runLock still be locked?

@akwizgran
Copy link
Contributor

Also, working on this made me think: what happens when TorService is given kill -9 from Android and the finally block isn't run? Will runLock still be locked?

The static lock is shared by TorService instances within the same process. kill -9 will kill the process, taking the static lock with it.

This unnests the try/finally block that was added in pull guardianproject#59, and moves it
to the main try block, where it now handles the whole shutdown procedure.

* guardianproject#61 (comment)
* guardianproject#57
* guardianproject#59
@eighthave eighthave force-pushed the shutdown-when-thread-stops branch from 583ae1b to 9d9bab1 Compare December 21, 2021 12:04
@eighthave eighthave changed the title WIP: ensure TorService properly shuts down whenever the tor thread stops ensure TorService properly shuts down whenever the tor thread stops Dec 21, 2021
@eighthave eighthave merged commit 9d9bab1 into guardianproject:master Dec 21, 2021
@eighthave eighthave deleted the shutdown-when-thread-stops branch December 21, 2021 18:05
@syphyr
Copy link
Contributor

syphyr commented Dec 21, 2021

After applying this commit, Orbot no longer shuts down

@syphyr
Copy link
Contributor

syphyr commented Dec 21, 2021

12-21 20:31:28.753 8596 8596 W InputEventReceiver: Attempted to finish an input event but the input event receiver has already been disposed.
12-21 20:35:04.019 8596 8938 D Orbot : stopTor

@eighthave
Copy link
Member Author

eighthave commented Dec 21, 2021 via email

@syphyr
Copy link
Contributor

syphyr commented Dec 21, 2021

I believe it is something different, because I did not have this issue with 0.4.6.8. This just started happening with 0.4.6.9.

@n8fr8
Copy link
Member

n8fr8 commented Dec 21, 2021

Orbot isn't using 0.4.6.9, at least not my official RC build. We are still using .8

@syphyr
Copy link
Contributor

syphyr commented Dec 21, 2021

I am using my own build of tor-android with latest Orbot tag. I just confirmed that this commit is causing the issue by reverting it.

@syphyr
Copy link
Contributor

syphyr commented Dec 21, 2021

The way I reproduce the issue is start Orbot (select onion), then stop Orbot (select onion). Then Orbot gets stuck and I have to kill the process to start Orbot again.

@syphyr
Copy link
Contributor

syphyr commented Dec 21, 2021

I also wanted to mention that this PR (guardianproject/orbot#561) does not fix this issue with Orbot

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants