diff --git a/dom/ipc/ContentProcess.cpp b/dom/ipc/ContentProcess.cpp index 65a603029e4d..924ebd0a1218 100644 --- a/dom/ipc/ContentProcess.cpp +++ b/dom/ipc/ContentProcess.cpp @@ -83,12 +83,19 @@ SetUpSandboxEnvironment() #ifdef ANDROID static int gPrefsFd = -1; +static int gPrefMapFd = -1; void SetPrefsFd(int aFd) { gPrefsFd = aFd; } + +void +SetPrefMapFd(int aFd) +{ + gPrefMapFd = aFd; +} #endif bool @@ -228,6 +235,9 @@ ContentProcess::Init(int aArgc, char* aArgv[]) // Android is different; get the FD via gPrefsFd instead of a fixed fd. MOZ_RELEASE_ASSERT(gPrefsFd != -1); prefsHandle = Some(base::FileDescriptor(gPrefsFd, /* auto_close */ true)); + + FileDescriptor::UniquePlatformHandle handle(gPrefMapFd); + prefMapHandle.emplace(handle.get()); #elif XP_UNIX prefsHandle = Some(base::FileDescriptor(kPrefsFileDescriptor, /* auto_close */ true)); diff --git a/dom/ipc/ContentProcess.h b/dom/ipc/ContentProcess.h index 6582c94da496..8ec1b5174048 100644 --- a/dom/ipc/ContentProcess.h +++ b/dom/ipc/ContentProcess.h @@ -50,8 +50,10 @@ private: }; #ifdef ANDROID -// Android doesn't use -prefsHandle, it gets that FD another way. +// Android doesn't use -prefsHandle or -prefMapHandle. It gets those FDs +// another way. void SetPrefsFd(int aFd); +void SetPrefMapFd(int aFd); #endif } // namespace dom diff --git a/ipc/glue/GeckoChildProcessHost.cpp b/ipc/glue/GeckoChildProcessHost.cpp index f032800f701c..da4409a0e41e 100644 --- a/ipc/glue/GeckoChildProcessHost.cpp +++ b/ipc/glue/GeckoChildProcessHost.cpp @@ -1242,7 +1242,7 @@ GeckoChildProcessHost::LaunchAndroidService(const char* type, const base::file_handle_mapping_vector& fds_to_remap, ProcessHandle* process_handle) { - MOZ_RELEASE_ASSERT((2 <= fds_to_remap.size()) && (fds_to_remap.size() <= 4)); + MOZ_RELEASE_ASSERT((2 <= fds_to_remap.size()) && (fds_to_remap.size() <= 5)); JNIEnv* const env = mozilla::jni::GetEnvForThread(); MOZ_ASSERT(env); @@ -1258,18 +1258,19 @@ GeckoChildProcessHost::LaunchAndroidService(const char* type, // which they append to fds_to_remap. There must be a better way to do it. // See bug 1440207. int32_t prefsFd = fds_to_remap[0].first; - int32_t ipcFd = fds_to_remap[1].first; + int32_t prefMapFd = fds_to_remap[1].first; + int32_t ipcFd = fds_to_remap[2].first; int32_t crashFd = -1; int32_t crashAnnotationFd = -1; - if (fds_to_remap.size() == 3) { - crashAnnotationFd = fds_to_remap[2].first; - } if (fds_to_remap.size() == 4) { - crashFd = fds_to_remap[2].first; crashAnnotationFd = fds_to_remap[3].first; } + if (fds_to_remap.size() == 5) { + crashFd = fds_to_remap[3].first; + crashAnnotationFd = fds_to_remap[4].first; + } - int32_t handle = java::GeckoProcessManager::Start(type, jargs, prefsFd, ipcFd, crashFd, crashAnnotationFd); + int32_t handle = java::GeckoProcessManager::Start(type, jargs, prefsFd, prefMapFd, ipcFd, crashFd, crashAnnotationFd); if (process_handle) { *process_handle = handle; diff --git a/mobile/android/geckoview/src/main/aidl/org/mozilla/gecko/process/IChildProcess.aidl b/mobile/android/geckoview/src/main/aidl/org/mozilla/gecko/process/IChildProcess.aidl index c731a3d0cc0c..99e880b61ff5 100644 --- a/mobile/android/geckoview/src/main/aidl/org/mozilla/gecko/process/IChildProcess.aidl +++ b/mobile/android/geckoview/src/main/aidl/org/mozilla/gecko/process/IChildProcess.aidl @@ -12,7 +12,8 @@ import android.os.ParcelFileDescriptor; interface IChildProcess { int getPid(); boolean start(in IProcessManager procMan, in String[] args, in Bundle extras, int flags, - in ParcelFileDescriptor prefsPfd, in ParcelFileDescriptor ipcPfd, + in ParcelFileDescriptor prefsPfd, in ParcelFileDescriptor prefMapPfd, + in ParcelFileDescriptor ipcPfd, in ParcelFileDescriptor crashReporterPfd, in ParcelFileDescriptor crashAnnotationPfd); diff --git a/mobile/android/geckoview/src/main/java/org/mozilla/gecko/GeckoThread.java b/mobile/android/geckoview/src/main/java/org/mozilla/gecko/GeckoThread.java index 076d7b92ee99..9abfd27986ce 100644 --- a/mobile/android/geckoview/src/main/java/org/mozilla/gecko/GeckoThread.java +++ b/mobile/android/geckoview/src/main/java/org/mozilla/gecko/GeckoThread.java @@ -132,6 +132,7 @@ public class GeckoThread extends Thread { /* package */ static final String EXTRA_ARGS = "args"; private static final String EXTRA_PREFS_FD = "prefsFd"; + private static final String EXTRA_PREF_MAP_FD = "prefMapFd"; private static final String EXTRA_IPC_FD = "ipcFd"; private static final String EXTRA_CRASH_FD = "crashFd"; private static final String EXTRA_CRASH_ANNOTATION_FD = "crashAnnotationFd"; @@ -153,7 +154,8 @@ public class GeckoThread extends Thread { private synchronized boolean init(final GeckoProfile profile, final String[] args, final Bundle extras, final int flags, - final int prefsFd, final int ipcFd, + final int prefsFd, final int prefMapFd, + final int ipcFd, final int crashFd, final int crashAnnotationFd) { ThreadUtils.assertOnUiThread(); @@ -169,6 +171,7 @@ public class GeckoThread extends Thread { mExtras = (extras != null) ? new Bundle(extras) : new Bundle(3); mExtras.putInt(EXTRA_PREFS_FD, prefsFd); + mExtras.putInt(EXTRA_PREF_MAP_FD, prefMapFd); mExtras.putInt(EXTRA_IPC_FD, ipcFd); mExtras.putInt(EXTRA_CRASH_FD, crashFd); mExtras.putInt(EXTRA_CRASH_ANNOTATION_FD, crashAnnotationFd); @@ -181,18 +184,20 @@ public class GeckoThread extends Thread { public static boolean initMainProcess(final GeckoProfile profile, final String[] args, final Bundle extras, final int flags) { return INSTANCE.init(profile, args, extras, flags, /* fd */ -1, - /* fd */ -1, /* fd */ -1, /* fd */ -1); + /* fd */ -1, /* fd */ -1, /* fd */ -1, + /* fd */ -1); } public static boolean initChildProcess(final String[] args, final Bundle extras, final int flags, final int prefsFd, + final int prefMapFd, final int ipcFd, final int crashFd, final int crashAnnotationFd) { return INSTANCE.init(/* profile */ null, args, extras, flags, - prefsFd, ipcFd, crashFd, crashAnnotationFd); + prefsFd, prefMapFd, ipcFd, crashFd, crashAnnotationFd); } private static boolean canUseProfile(final Context context, final GeckoProfile profile, @@ -497,6 +502,7 @@ public class GeckoThread extends Thread { // And go. GeckoLoader.nativeRun(args, mExtras.getInt(EXTRA_PREFS_FD, -1), + mExtras.getInt(EXTRA_PREF_MAP_FD, -1), mExtras.getInt(EXTRA_IPC_FD, -1), mExtras.getInt(EXTRA_CRASH_FD, -1), mExtras.getInt(EXTRA_CRASH_ANNOTATION_FD, -1)); diff --git a/mobile/android/geckoview/src/main/java/org/mozilla/gecko/mozglue/GeckoLoader.java b/mobile/android/geckoview/src/main/java/org/mozilla/gecko/mozglue/GeckoLoader.java index 6ea25710f0b3..f04cb3644b2f 100644 --- a/mobile/android/geckoview/src/main/java/org/mozilla/gecko/mozglue/GeckoLoader.java +++ b/mobile/android/geckoview/src/main/java/org/mozilla/gecko/mozglue/GeckoLoader.java @@ -456,7 +456,7 @@ public final class GeckoLoader { public static native boolean verifyCRCs(String apkName); // These methods are implemented in mozglue/android/APKOpen.cpp - public static native void nativeRun(String[] args, int prefsFd, int ipcFd, int crashFd, int crashAnnotationFd); + public static native void nativeRun(String[] args, int prefsFd, int prefMapFd, int ipcFd, int crashFd, int crashAnnotationFd); private static native void loadGeckoLibsNative(String apkName); private static native void loadSQLiteLibsNative(String apkName); private static native void loadNSSLibsNative(String apkName); diff --git a/mobile/android/geckoview/src/main/java/org/mozilla/gecko/process/GeckoProcessManager.java b/mobile/android/geckoview/src/main/java/org/mozilla/gecko/process/GeckoProcessManager.java index d733ea5560e1..ec0d747279ad 100644 --- a/mobile/android/geckoview/src/main/java/org/mozilla/gecko/process/GeckoProcessManager.java +++ b/mobile/android/geckoview/src/main/java/org/mozilla/gecko/process/GeckoProcessManager.java @@ -182,9 +182,10 @@ public final class GeckoProcessManager extends IProcessManager.Stub { @WrapForJNI private static int start(final String type, final String[] args, - final int prefsFd, final int ipcFd, + final int prefsFd, final int prefMapFd, + final int ipcFd, final int crashFd, final int crashAnnotationFd) { - return INSTANCE.start(type, args, prefsFd, ipcFd, crashFd, crashAnnotationFd, /* retry */ false); + return INSTANCE.start(type, args, prefsFd, prefMapFd, ipcFd, crashFd, crashAnnotationFd, /* retry */ false); } private int filterFlagsForChild(int flags) { @@ -192,7 +193,8 @@ public final class GeckoProcessManager extends IProcessManager.Stub { GeckoThread.FLAG_ENABLE_NATIVE_CRASHREPORTER); } - private int start(final String type, final String[] args, final int prefsFd, + private int start(final String type, final String[] args, + final int prefsFd, final int prefMapFd, final int ipcFd, final int crashFd, final int crashAnnotationFd, final boolean retry) { final ChildConnection connection = getConnection(type); @@ -203,11 +205,13 @@ public final class GeckoProcessManager extends IProcessManager.Stub { final Bundle extras = GeckoThread.getActiveExtras(); final ParcelFileDescriptor prefsPfd; + final ParcelFileDescriptor prefMapPfd; final ParcelFileDescriptor ipcPfd; final ParcelFileDescriptor crashPfd; final ParcelFileDescriptor crashAnnotationPfd; try { prefsPfd = ParcelFileDescriptor.fromFd(prefsFd); + prefMapPfd = ParcelFileDescriptor.fromFd(prefMapFd); ipcPfd = ParcelFileDescriptor.fromFd(ipcFd); crashPfd = (crashFd >= 0) ? ParcelFileDescriptor.fromFd(crashFd) : null; crashAnnotationPfd = (crashAnnotationFd >= 0) ? ParcelFileDescriptor.fromFd(crashAnnotationFd) : null; @@ -220,8 +224,8 @@ public final class GeckoProcessManager extends IProcessManager.Stub { boolean started = false; try { - started = child.start(this, args, extras, flags, prefsPfd, ipcPfd, crashPfd, - crashAnnotationPfd); + started = child.start(this, args, extras, flags, prefsPfd, prefMapPfd, + ipcPfd, crashPfd, crashAnnotationPfd); } catch (final RemoteException e) { } @@ -232,7 +236,7 @@ public final class GeckoProcessManager extends IProcessManager.Stub { } Log.w(LOGTAG, "Attempting to kill running child " + type); connection.unbind(); - return start(type, args, prefsFd, ipcFd, crashFd, crashAnnotationFd, /* retry */ true); + return start(type, args, prefsFd, prefMapFd, ipcFd, crashFd, crashAnnotationFd, /* retry */ true); } try { diff --git a/mobile/android/geckoview/src/main/java/org/mozilla/gecko/process/GeckoServiceChildProcess.java b/mobile/android/geckoview/src/main/java/org/mozilla/gecko/process/GeckoServiceChildProcess.java index f328388a4f7e..9335fb611553 100644 --- a/mobile/android/geckoview/src/main/java/org/mozilla/gecko/process/GeckoServiceChildProcess.java +++ b/mobile/android/geckoview/src/main/java/org/mozilla/gecko/process/GeckoServiceChildProcess.java @@ -62,6 +62,7 @@ public class GeckoServiceChildProcess extends Service { final Bundle extras, final int flags, final ParcelFileDescriptor prefsPfd, + final ParcelFileDescriptor prefMapPfd, final ParcelFileDescriptor ipcPfd, final ParcelFileDescriptor crashReporterPfd, final ParcelFileDescriptor crashAnnotationPfd) { @@ -74,6 +75,7 @@ public class GeckoServiceChildProcess extends Service { } final int prefsFd = prefsPfd.detachFd(); + final int prefMapFd = prefMapPfd.detachFd(); final int ipcFd = ipcPfd.detachFd(); final int crashReporterFd = crashReporterPfd != null ? crashReporterPfd.detachFd() : -1; @@ -83,8 +85,8 @@ public class GeckoServiceChildProcess extends Service { ThreadUtils.postToUiThread(new Runnable() { @Override public void run() { - if (GeckoThread.initChildProcess(args, extras, flags, prefsFd, ipcFd, crashReporterFd, - crashAnnotationFd)) { + if (GeckoThread.initChildProcess(args, extras, flags, prefsFd, prefMapFd, ipcFd, + crashReporterFd, crashAnnotationFd)) { GeckoThread.launch(); } } diff --git a/mozglue/android/APKOpen.cpp b/mozglue/android/APKOpen.cpp index 4e32e980d36e..6d3736a52798 100644 --- a/mozglue/android/APKOpen.cpp +++ b/mozglue/android/APKOpen.cpp @@ -393,7 +393,7 @@ FreeArgv(char** argv, int argc) } extern "C" APKOPEN_EXPORT void MOZ_JNICALL -Java_org_mozilla_gecko_mozglue_GeckoLoader_nativeRun(JNIEnv *jenv, jclass jc, jobjectArray jargs, int prefsFd, int ipcFd, int crashFd, int crashAnnotationFd) +Java_org_mozilla_gecko_mozglue_GeckoLoader_nativeRun(JNIEnv *jenv, jclass jc, jobjectArray jargs, int prefsFd, int prefMapFd, int ipcFd, int crashFd, int crashAnnotationFd) { int argc = 0; char** argv = CreateArgvFromObjectArray(jenv, jargs, &argc); @@ -408,7 +408,7 @@ Java_org_mozilla_gecko_mozglue_GeckoLoader_nativeRun(JNIEnv *jenv, jclass jc, jo gBootstrap->GeckoStart(jenv, argv, argc, sAppData); ElfLoader::Singleton.ExpectShutdown(true); } else { - gBootstrap->XRE_SetAndroidChildFds(jenv, { prefsFd, ipcFd, crashFd, crashAnnotationFd }); + gBootstrap->XRE_SetAndroidChildFds(jenv, { prefsFd, prefMapFd, ipcFd, crashFd, crashAnnotationFd }); gBootstrap->XRE_SetProcessType(argv[argc - 1]); XREChildData childData; diff --git a/toolkit/xre/nsEmbedFunctions.cpp b/toolkit/xre/nsEmbedFunctions.cpp index d7c5535d79ec..fa6bfdc136b5 100644 --- a/toolkit/xre/nsEmbedFunctions.cpp +++ b/toolkit/xre/nsEmbedFunctions.cpp @@ -248,6 +248,7 @@ XRE_SetAndroidChildFds (JNIEnv* env, const XRE_AndroidChildFds& fds) { mozilla::jni::SetGeckoThreadEnv(env); mozilla::dom::SetPrefsFd(fds.mPrefsFd); + mozilla::dom::SetPrefMapFd(fds.mPrefMapFd); IPC::Channel::SetClientChannelFd(fds.mIpcFd); CrashReporter::SetNotificationPipeForChild(fds.mCrashFd); CrashReporter::SetCrashAnnotationPipeForChild(fds.mCrashAnnotationFd); diff --git a/xpcom/build/nsXULAppAPI.h b/xpcom/build/nsXULAppAPI.h index dfcb5aeb6562..1736999571ae 100644 --- a/xpcom/build/nsXULAppAPI.h +++ b/xpcom/build/nsXULAppAPI.h @@ -400,6 +400,7 @@ XRE_API(const char*, struct XRE_AndroidChildFds { int mPrefsFd; + int mPrefMapFd; int mIpcFd; int mCrashFd; int mCrashAnnotationFd;