summaryrefslogtreecommitdiff
path: root/jni/com_android_providers_media_FuseDaemon.cpp
diff options
context:
space:
mode:
authorMartijn Coenen <maco@google.com>2020-04-24 09:39:58 +0200
committerMartijn Coenen <maco@google.com>2020-04-24 09:46:50 +0200
commit083eb69b697fb4a8db4d58125e1225446da1aa50 (patch)
tree97e06803664c6a8da023029515c8a755f5671e83 /jni/com_android_providers_media_FuseDaemon.cpp
parent0af92df536c477e089f387dddfa956a040135864 (diff)
downloadMediaProvider-083eb69b697fb4a8db4d58125e1225446da1aa50.tar.gz
Always close FUSE file descriptor when we're exiting the thread.
We had previously relied on the process being killed when we're unable to start the FUSE daemon successfully; but while the current onStartSession() code would throw an exception, that would just get thrown over binder, without the process crashing. This could result in the following sequence: 1) We mount a new FUSE filesystem and call onStartSession() with the fuse FD, fd1 2) onStartSession() starts the FUSE daemon thread and starts waiting for it to come up 3) For whatever reaosn, the FUSE thread doesn't come up and exits; now we throw an IllegalStateException, but that just gets swallowed by binder, and the MP process stays up 4) We try to start the session again; this may be successful, but we still hold the original file descriptor fd1 open, and any requests outstanding to this filesystem would hang forever 5) llkd notices these threads are stuck for 10 minutes on I/O, and panics the kernel To prevent this from happening, just give the FUSE daemon thread ownership of the FD, and make sure it gets closed whenever something goes wrong by using unique_fd. As for why 3) can happen, it appears to be that we can attempt to mount the filesystem for user 10 before user 0. This needs a separate fix. Bug: 153816731 Test: device boots ok, filesystems mounted Change-Id: Ica89d77357c1c822dc536d5e4c946d5235670a73
Diffstat (limited to 'jni/com_android_providers_media_FuseDaemon.cpp')
-rw-r--r--jni/com_android_providers_media_FuseDaemon.cpp5
1 files changed, 4 insertions, 1 deletions
diff --git a/jni/com_android_providers_media_FuseDaemon.cpp b/jni/com_android_providers_media_FuseDaemon.cpp
index ae1c17526..3a65696f6 100644
--- a/jni/com_android_providers_media_FuseDaemon.cpp
+++ b/jni/com_android_providers_media_FuseDaemon.cpp
@@ -24,6 +24,7 @@
#include "FuseDaemon.h"
#include "MediaProviderWrapper.h"
#include "android-base/logging.h"
+#include "android-base/unique_fd.h"
namespace mediaprovider {
namespace {
@@ -42,12 +43,14 @@ void com_android_providers_media_FuseDaemon_start(JNIEnv* env, jobject self, jlo
LOG(DEBUG) << "Starting the FUSE daemon...";
fuse::FuseDaemon* const daemon = reinterpret_cast<fuse::FuseDaemon*>(java_daemon);
+ android::base::unique_fd ufd(fd);
+
ScopedUtfChars utf_chars_path(env, java_path);
if (!utf_chars_path.c_str()) {
return;
}
- daemon->Start(fd, utf_chars_path.c_str());
+ daemon->Start(std::move(ufd), utf_chars_path.c_str());
}
bool com_android_providers_media_FuseDaemon_is_started(JNIEnv* env, jobject self,