Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(2161)

Unified Diff: base/android/java/src/org/chromium/base/library_loader/LibraryLoader.java

Issue 935333002: Update from https://crrev.com/316786 (Closed) Base URL: git@github.com:domokit/mojo.git@master
Patch Set: Created 5 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « base/android/build_info.h ('k') | base/android/java/src/org/chromium/base/metrics/RecordHistogram.java » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: base/android/java/src/org/chromium/base/library_loader/LibraryLoader.java
diff --git a/base/android/java/src/org/chromium/base/library_loader/LibraryLoader.java b/base/android/java/src/org/chromium/base/library_loader/LibraryLoader.java
index 2168c21827fddcd17c1d7d2f5de4d0dd17155a62..d68fb4a814a19f1e187fd0afe77a2227b5df40e4 100644
--- a/base/android/java/src/org/chromium/base/library_loader/LibraryLoader.java
+++ b/base/android/java/src/org/chromium/base/library_loader/LibraryLoader.java
@@ -8,6 +8,7 @@ import android.content.Context;
import android.os.SystemClock;
import android.util.Log;
+import org.chromium.base.CalledByNative;
import org.chromium.base.CommandLine;
import org.chromium.base.JNINamespace;
import org.chromium.base.TraceEvent;
@@ -40,41 +41,68 @@ public class LibraryLoader {
// Guards all access to the libraries
private static final Object sLock = new Object();
+ // The singleton instance of LibraryLoader.
+ private static LibraryLoader sInstance;
+
// One-way switch becomes true when the libraries are loaded.
- private static boolean sLoaded = false;
+ private boolean mLoaded;
// One-way switch becomes true when the Java command line is switched to
// native.
- private static boolean sCommandLineSwitched = false;
+ private boolean mCommandLineSwitched;
// One-way switch becomes true when the libraries are initialized (
// by calling nativeLibraryLoaded, which forwards to LibraryLoaded(...) in
// library_loader_hooks.cc).
- private static boolean sInitialized = false;
+ private boolean mInitialized;
// One-way switches recording attempts to use Relro sharing in the browser.
// The flags are used to report UMA stats later.
- private static boolean sIsUsingBrowserSharedRelros = false;
- private static boolean sLoadAtFixedAddressFailed = false;
+ private boolean mIsUsingBrowserSharedRelros;
+ private boolean mLoadAtFixedAddressFailed;
// One-way switch becomes true if the device supports memory mapping the
// APK file with executable permissions.
- private static boolean sMapApkWithExecPermission = false;
+ private boolean mMapApkWithExecPermission;
// One-way switch to indicate whether we probe for memory mapping the APK
// file with executable permissions. We suppress the probe under some
// conditions.
// For more, see:
// https://code.google.com/p/chromium/issues/detail?id=448084
- private static boolean sProbeMapApkWithExecPermission = true;
+ private boolean mProbeMapApkWithExecPermission = true;
// One-way switch becomes true if the Chromium library was loaded from the
// APK file directly.
- private static boolean sLibraryWasLoadedFromApk = false;
+ private boolean mLibraryWasLoadedFromApk;
// One-way switch becomes false if the Chromium library should be loaded
// directly from the APK file but it was compressed or not aligned.
- private static boolean sLibraryIsMappableInApk = true;
+ private boolean mLibraryIsMappableInApk = true;
+
+ // The type of process the shared library is loaded in.
+ private int mLibraryProcessType;
+
+ /**
+ * @param libraryProcessType the process the shared library is loaded in. refer to
+ * LibraryProcessType for possible values.
+ * @return LibraryLoader if existing, otherwise create a new one.
+ */
+ public static LibraryLoader get(int libraryProcessType) throws ProcessInitException {
+ synchronized (sLock) {
+ if (sInstance != null) {
+ if (sInstance.mLibraryProcessType == libraryProcessType) return sInstance;
+ throw new ProcessInitException(
+ LoaderErrors.LOADER_ERROR_NATIVE_LIBRARY_LOAD_FAILED);
+ }
+ sInstance = new LibraryLoader(libraryProcessType);
+ return sInstance;
+ }
+ }
+
+ private LibraryLoader(int libraryProcessType) {
+ mLibraryProcessType = libraryProcessType;
+ }
/**
* The same as ensureInitialized(null, false), should only be called
@@ -82,7 +110,7 @@ public class LibraryLoader {
*
* @throws ProcessInitException
*/
- public static void ensureInitialized() throws ProcessInitException {
+ public void ensureInitialized() throws ProcessInitException {
ensureInitialized(null, false);
}
@@ -96,11 +124,11 @@ public class LibraryLoader {
* @param shouldDeleteFallbackLibraries The flag tells whether the method
* should delete the fallback libraries or not.
*/
- public static void ensureInitialized(
+ public void ensureInitialized(
Context context, boolean shouldDeleteFallbackLibraries)
throws ProcessInitException {
synchronized (sLock) {
- if (sInitialized) {
+ if (mInitialized) {
// Already initialized, nothing to do.
return;
}
@@ -114,7 +142,7 @@ public class LibraryLoader {
*/
public static boolean isInitialized() {
synchronized (sLock) {
- return sInitialized;
+ return sInstance != null && sInstance.mInitialized;
}
}
@@ -124,7 +152,7 @@ public class LibraryLoader {
*
* @throws ProcessInitException
*/
- public static void loadNow() throws ProcessInitException {
+ public void loadNow() throws ProcessInitException {
loadNow(null, false);
}
@@ -141,7 +169,7 @@ public class LibraryLoader {
*
* @throws ProcessInitException if the native library failed to load.
*/
- public static void loadNow(Context context, boolean shouldDeleteFallbackLibraries)
+ public void loadNow(Context context, boolean shouldDeleteFallbackLibraries)
throws ProcessInitException {
synchronized (sLock) {
loadAlreadyLocked(context, shouldDeleteFallbackLibraries);
@@ -153,19 +181,19 @@ public class LibraryLoader {
* native will call its "main" thread. The library must have previously been
* loaded with loadNow.
*/
- public static void initialize() throws ProcessInitException {
+ public void initialize() throws ProcessInitException {
synchronized (sLock) {
initializeAlreadyLocked();
}
}
// Invoke System.loadLibrary(...), triggering JNI_OnLoad in native code
- private static void loadAlreadyLocked(
+ private void loadAlreadyLocked(
Context context, boolean shouldDeleteFallbackLibraries)
throws ProcessInitException {
try {
- if (!sLoaded) {
- assert !sInitialized;
+ if (!mLoaded) {
+ assert !mInitialized;
long startTime = SystemClock.uptimeMillis();
boolean useChromiumLinker = Linker.isUsed();
@@ -183,17 +211,17 @@ public class LibraryLoader {
if (manufacturer != null
&& manufacturer.toLowerCase(Locale.ENGLISH).contains("samsung")) {
Log.w(TAG, "Suppressed load from APK support check on this device");
- sProbeMapApkWithExecPermission = false;
+ mProbeMapApkWithExecPermission = false;
}
// Check if the device supports memory mapping the APK file
// with executable permissions.
if (context != null) {
apkFilePath = context.getApplicationInfo().sourceDir;
- if (sProbeMapApkWithExecPermission) {
- sMapApkWithExecPermission = Linker.checkMapExecSupport(apkFilePath);
+ if (mProbeMapApkWithExecPermission) {
+ mMapApkWithExecPermission = Linker.checkMapExecSupport(apkFilePath);
}
- if (!sMapApkWithExecPermission && Linker.isInZipFile()) {
+ if (!mMapApkWithExecPermission && Linker.isInZipFile()) {
Log.w(TAG, "the no map executable support fallback will be used because"
+ " memory mapping the APK file with executable permissions is"
+ " not supported");
@@ -222,9 +250,9 @@ public class LibraryLoader {
if (apkFilePath != null && Linker.isInZipFile()) {
// The library is in the APK file.
if (!Linker.checkLibraryIsMappableInApk(apkFilePath, libFilePath)) {
- sLibraryIsMappableInApk = false;
+ mLibraryIsMappableInApk = false;
}
- if (sLibraryIsMappableInApk || useMapExecSupportFallback) {
+ if (mLibraryIsMappableInApk || useMapExecSupportFallback) {
// Load directly from the APK (or use the no map executable
// support fallback, see crazy_linker_elf_loader.cpp).
zipFilePath = apkFilePath;
@@ -251,7 +279,7 @@ public class LibraryLoader {
// Load the library.
boolean isLoaded = false;
if (Linker.isUsingBrowserSharedRelros()) {
- sIsUsingBrowserSharedRelros = true;
+ mIsUsingBrowserSharedRelros = true;
try {
loadLibrary(zipFilePath, libFilePath);
isLoaded = true;
@@ -259,7 +287,7 @@ public class LibraryLoader {
Log.w(TAG, "Failed to load native library with shared RELRO, "
+ "retrying without");
Linker.disableSharedRelros();
- sLoadAtFixedAddressFailed = true;
+ mLoadAtFixedAddressFailed = true;
}
}
if (!isLoaded) {
@@ -287,7 +315,7 @@ public class LibraryLoader {
startTime % 10000,
stopTime % 10000));
- sLoaded = true;
+ mLoaded = true;
}
} catch (UnsatisfiedLinkError e) {
throw new ProcessInitException(LoaderErrors.LOADER_ERROR_NATIVE_LIBRARY_LOAD_FAILED, e);
@@ -305,17 +333,17 @@ public class LibraryLoader {
// Load a native shared library with the Chromium linker. If the zip file
// path is not null, the library is loaded directly from the zip file.
- private static void loadLibrary(@Nullable String zipFilePath, String libFilePath) {
+ private void loadLibrary(@Nullable String zipFilePath, String libFilePath) {
Linker.loadLibrary(zipFilePath, libFilePath);
if (zipFilePath != null) {
- sLibraryWasLoadedFromApk = true;
+ mLibraryWasLoadedFromApk = true;
}
}
// The WebView requires the Command Line to be switched over before
// initialization is done. This is okay in the WebView's case since the
// JNI is already loaded by this point.
- public static void switchCommandLineForWebView() {
+ public void switchCommandLineForWebView() {
synchronized (sLock) {
ensureCommandLineSwitchedAlreadyLocked();
}
@@ -324,24 +352,24 @@ public class LibraryLoader {
// Switch the CommandLine over from Java to native if it hasn't already been done.
// This must happen after the code is loaded and after JNI is ready (since after the
// switch the Java CommandLine will delegate all calls the native CommandLine).
- private static void ensureCommandLineSwitchedAlreadyLocked() {
- assert sLoaded;
- if (sCommandLineSwitched) {
+ private void ensureCommandLineSwitchedAlreadyLocked() {
+ assert mLoaded;
+ if (mCommandLineSwitched) {
return;
}
nativeInitCommandLine(CommandLine.getJavaSwitchesOrNull());
CommandLine.enableNativeProxy();
- sCommandLineSwitched = true;
+ mCommandLineSwitched = true;
}
// Invoke base::android::LibraryLoaded in library_loader_hooks.cc
- private static void initializeAlreadyLocked() throws ProcessInitException {
- if (sInitialized) {
+ private void initializeAlreadyLocked() throws ProcessInitException {
+ if (mInitialized) {
return;
}
// Setup the native command line if necessary.
- if (!sCommandLineSwitched) {
+ if (!mCommandLineSwitched) {
nativeInitCommandLine(CommandLine.getJavaSwitchesOrNull());
}
@@ -352,13 +380,13 @@ public class LibraryLoader {
// From this point on, native code is ready to use and checkIsReady()
// shouldn't complain from now on (and in fact, it's used by the
// following calls).
- sInitialized = true;
+ mInitialized = true;
// The Chrome JNI is registered by now so we can switch the Java
// command line over to delegating to native if it's necessary.
- if (!sCommandLineSwitched) {
+ if (!mCommandLineSwitched) {
CommandLine.enableNativeProxy();
- sCommandLineSwitched = true;
+ mCommandLineSwitched = true;
}
// From now on, keep tracing in sync with native.
@@ -366,32 +394,32 @@ public class LibraryLoader {
}
// Called after all native initializations are complete.
- public static void onNativeInitializationComplete(Context context) {
+ public void onNativeInitializationComplete(Context context) {
recordBrowserProcessHistogram(context);
}
// Record Chromium linker histogram state for the main browser process. Called from
// onNativeInitializationComplete().
- private static void recordBrowserProcessHistogram(Context context) {
+ private void recordBrowserProcessHistogram(Context context) {
if (Linker.isUsed()) {
- nativeRecordChromiumAndroidLinkerBrowserHistogram(sIsUsingBrowserSharedRelros,
- sLoadAtFixedAddressFailed,
+ nativeRecordChromiumAndroidLinkerBrowserHistogram(mIsUsingBrowserSharedRelros,
+ mLoadAtFixedAddressFailed,
getLibraryLoadFromApkStatus(context));
}
}
// Returns the device's status for loading a library directly from the APK file.
// This method can only be called when the Chromium linker is used.
- private static int getLibraryLoadFromApkStatus(Context context) {
+ private int getLibraryLoadFromApkStatus(Context context) {
assert Linker.isUsed();
- if (sLibraryWasLoadedFromApk) {
- return sMapApkWithExecPermission
+ if (mLibraryWasLoadedFromApk) {
+ return mMapApkWithExecPermission
? LibraryLoadFromApkStatusCodes.SUCCESSFUL
: LibraryLoadFromApkStatusCodes.USED_NO_MAP_EXEC_SUPPORT_FALLBACK;
}
- if (!sLibraryIsMappableInApk) {
+ if (!mLibraryIsMappableInApk) {
return LibraryLoadFromApkStatusCodes.USED_UNPACK_LIBRARY_FALLBACK;
}
@@ -400,11 +428,11 @@ public class LibraryLoader {
return LibraryLoadFromApkStatusCodes.UNKNOWN;
}
- if (!sProbeMapApkWithExecPermission) {
+ if (!mProbeMapApkWithExecPermission) {
return LibraryLoadFromApkStatusCodes.UNKNOWN;
}
- return sMapApkWithExecPermission
+ return mMapApkWithExecPermission
? LibraryLoadFromApkStatusCodes.SUPPORTED
: LibraryLoadFromApkStatusCodes.NOT_SUPPORTED;
}
@@ -413,15 +441,27 @@ public class LibraryLoader {
// recorded as a histogram immediately because histograms and IPC are not ready at the
// time it are captured. This function stores a pending value, so that a later call to
// RecordChromiumAndroidLinkerRendererHistogram() will record it correctly.
- public static void registerRendererProcessHistogram(boolean requestedSharedRelro,
- boolean loadAtFixedAddressFailed) {
+ public void registerRendererProcessHistogram(boolean requestedSharedRelro,
+ boolean loadAtFixedAddressFailed) {
if (Linker.isUsed()) {
nativeRegisterChromiumAndroidLinkerRendererHistogram(requestedSharedRelro,
loadAtFixedAddressFailed);
}
}
- private static native void nativeInitCommandLine(String[] initCommandLine);
+ /**
+ * @return the process the shared library is loaded in, see the LibraryProcessType
+ * for possible values.
+ */
+ @CalledByNative
+ public static int getLibraryProcessType() {
+ synchronized (sLock) {
+ if (sInstance == null) return LibraryProcessType.PROCESS_UNINITIALIZED;
+ return sInstance.mLibraryProcessType;
+ }
+ }
+
+ private native void nativeInitCommandLine(String[] initCommandLine);
// Only methods needed before or during normal JNI registration are during System.OnLoad.
// nativeLibraryLoaded is then called to register everything else. This process is called
@@ -429,13 +469,13 @@ public class LibraryLoader {
// definition in base/android/library_loader/library_loader_hooks.cc.
//
// Return true on success and false on failure.
- private static native boolean nativeLibraryLoaded();
+ private native boolean nativeLibraryLoaded();
// Method called to record statistics about the Chromium linker operation for the main
// browser process. Indicates whether the linker attempted relro sharing for the browser,
// and if it did, whether the library failed to load at a fixed address. Also records
// support for loading a library directly from the APK file.
- private static native void nativeRecordChromiumAndroidLinkerBrowserHistogram(
+ private native void nativeRecordChromiumAndroidLinkerBrowserHistogram(
boolean isUsingBrowserSharedRelros,
boolean loadAtFixedAddressFailed,
int libraryLoadFromApkStatus);
@@ -443,11 +483,11 @@ public class LibraryLoader {
// Method called to register (for later recording) statistics about the Chromium linker
// operation for a renderer process. Indicates whether the linker attempted relro sharing,
// and if it did, whether the library failed to load at a fixed address.
- private static native void nativeRegisterChromiumAndroidLinkerRendererHistogram(
+ private native void nativeRegisterChromiumAndroidLinkerRendererHistogram(
boolean requestedSharedRelro,
boolean loadAtFixedAddressFailed);
// Get the version of the native library. This is needed so that we can check we
// have the right version before initializing the (rest of the) JNI.
- private static native String nativeGetVersionNumber();
+ private native String nativeGetVersionNumber();
}
« no previous file with comments | « base/android/build_info.h ('k') | base/android/java/src/org/chromium/base/metrics/RecordHistogram.java » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698