| OLD | NEW |
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 package org.chromium.base.library_loader; | 5 package org.chromium.base.library_loader; |
| 6 | 6 |
| 7 import android.os.Bundle; | 7 import android.os.Bundle; |
| 8 import android.os.Parcel; | 8 import android.os.Parcel; |
| 9 | 9 |
| 10 import org.chromium.base.Log; | 10 import org.chromium.base.Log; |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 64 | 64 |
| 65 // The map of libraries that are currently loaded in this process. | 65 // The map of libraries that are currently loaded in this process. |
| 66 private HashMap<String, LibInfo> mLoadedLibraries = null; | 66 private HashMap<String, LibInfo> mLoadedLibraries = null; |
| 67 | 67 |
| 68 // Private singleton constructor, and singleton factory method. | 68 // Private singleton constructor, and singleton factory method. |
| 69 private LegacyLinker() {} | 69 private LegacyLinker() {} |
| 70 static Linker create() { | 70 static Linker create() { |
| 71 return new LegacyLinker(); | 71 return new LegacyLinker(); |
| 72 } | 72 } |
| 73 | 73 |
| 74 // Used internally to initialize the linker's data. Assume lock is held. | 74 // Used internally to initialize the linker's data. Assumes lock is held. |
| 75 // Loads JNI, and sets mMemoryDeviceConfig and mBrowserUsesSharedRelro. |
| 75 private void ensureInitializedLocked() { | 76 private void ensureInitializedLocked() { |
| 76 assert Thread.holdsLock(mLock); | 77 assert Thread.holdsLock(mLock); |
| 77 | 78 |
| 78 if (mInitialized) { | 79 if (mInitialized || !NativeLibraries.sUseLinker) { |
| 79 return; | 80 return; |
| 80 } | 81 } |
| 81 | 82 |
| 82 if (NativeLibraries.sUseLinker) { | 83 // On first call, load libchromium_android_linker.so. Cannot be done in
the |
| 83 // Load libchromium_android_linker.so. | 84 // constructor because instantiation occurs on the UI thread. |
| 84 loadLinkerJNILibrary(); | 85 loadLinkerJniLibrary(); |
| 85 | 86 |
| 86 if (mMemoryDeviceConfig == MEMORY_DEVICE_CONFIG_INIT) { | 87 if (mMemoryDeviceConfig == MEMORY_DEVICE_CONFIG_INIT) { |
| 87 if (SysUtils.isLowEndDevice()) { | 88 if (SysUtils.isLowEndDevice()) { |
| 88 mMemoryDeviceConfig = MEMORY_DEVICE_CONFIG_LOW; | 89 mMemoryDeviceConfig = MEMORY_DEVICE_CONFIG_LOW; |
| 90 } else { |
| 91 mMemoryDeviceConfig = MEMORY_DEVICE_CONFIG_NORMAL; |
| 92 } |
| 93 } |
| 94 |
| 95 // Cannot run in the constructor because SysUtils.isLowEndDevice() relie
s |
| 96 // on CommandLine, which may not be available at instantiation. |
| 97 switch (BROWSER_SHARED_RELRO_CONFIG) { |
| 98 case BROWSER_SHARED_RELRO_CONFIG_NEVER: |
| 99 mBrowserUsesSharedRelro = false; |
| 100 break; |
| 101 case BROWSER_SHARED_RELRO_CONFIG_LOW_RAM_ONLY: |
| 102 if (mMemoryDeviceConfig == MEMORY_DEVICE_CONFIG_LOW) { |
| 103 mBrowserUsesSharedRelro = true; |
| 104 Log.w(TAG, "Low-memory device: shared RELROs used in all pro
cesses"); |
| 89 } else { | 105 } else { |
| 90 mMemoryDeviceConfig = MEMORY_DEVICE_CONFIG_NORMAL; | 106 mBrowserUsesSharedRelro = false; |
| 91 } | 107 } |
| 92 } | 108 break; |
| 93 | 109 case BROWSER_SHARED_RELRO_CONFIG_ALWAYS: |
| 94 switch (BROWSER_SHARED_RELRO_CONFIG) { | 110 Log.w(TAG, "Beware: shared RELROs used in all processes!"); |
| 95 case BROWSER_SHARED_RELRO_CONFIG_NEVER: | 111 mBrowserUsesSharedRelro = true; |
| 96 mBrowserUsesSharedRelro = false; | 112 break; |
| 97 break; | 113 default: |
| 98 case BROWSER_SHARED_RELRO_CONFIG_LOW_RAM_ONLY: | 114 assert false : "Unreached"; |
| 99 if (mMemoryDeviceConfig == MEMORY_DEVICE_CONFIG_LOW) { | 115 break; |
| 100 mBrowserUsesSharedRelro = true; | |
| 101 Log.w(TAG, "Low-memory device: shared RELROs used in all
processes"); | |
| 102 } else { | |
| 103 mBrowserUsesSharedRelro = false; | |
| 104 } | |
| 105 break; | |
| 106 case BROWSER_SHARED_RELRO_CONFIG_ALWAYS: | |
| 107 Log.w(TAG, "Beware: shared RELROs used in all processes!"); | |
| 108 mBrowserUsesSharedRelro = true; | |
| 109 break; | |
| 110 default: | |
| 111 assert false : "Unreached"; | |
| 112 break; | |
| 113 } | |
| 114 } else { | |
| 115 if (DEBUG) { | |
| 116 Log.i(TAG, "Linker disabled"); | |
| 117 } | |
| 118 } | 116 } |
| 119 | 117 |
| 120 mInitialized = true; | 118 mInitialized = true; |
| 121 } | 119 } |
| 122 | 120 |
| 123 /** | 121 /** |
| 124 * Call this method to determine if this chromium project must | |
| 125 * use this linker. If not, System.loadLibrary() should be used to load | |
| 126 * libraries instead. | |
| 127 */ | |
| 128 @Override | |
| 129 public boolean isUsed() { | |
| 130 // Only GYP targets that are APKs and have the 'use_chromium_linker' var
iable | |
| 131 // defined as 1 will use this linker. For all others (the default), the | |
| 132 // auto-generated NativeLibraries.sUseLinker variable will be false. | |
| 133 if (!NativeLibraries.sUseLinker) { | |
| 134 return false; | |
| 135 } | |
| 136 | |
| 137 synchronized (mLock) { | |
| 138 ensureInitializedLocked(); | |
| 139 return true; | |
| 140 } | |
| 141 } | |
| 142 | |
| 143 /** | |
| 144 * Call this method to determine if the linker will try to use shared RELROs | 122 * Call this method to determine if the linker will try to use shared RELROs |
| 145 * for the browser process. | 123 * for the browser process. |
| 146 */ | 124 */ |
| 147 @Override | 125 @Override |
| 148 public boolean isUsingBrowserSharedRelros() { | 126 public boolean isUsingBrowserSharedRelros() { |
| 149 synchronized (mLock) { | 127 synchronized (mLock) { |
| 150 ensureInitializedLocked(); | 128 ensureInitializedLocked(); |
| 151 return mBrowserUsesSharedRelro; | 129 return mBrowserUsesSharedRelro; |
| 152 } | 130 } |
| 153 } | 131 } |
| (...skipping 26 matching lines...) Expand all Loading... |
| 180 @Override | 158 @Override |
| 181 public void finishLibraryLoad() { | 159 public void finishLibraryLoad() { |
| 182 if (DEBUG) { | 160 if (DEBUG) { |
| 183 Log.i(TAG, "finishLibraryLoad() called"); | 161 Log.i(TAG, "finishLibraryLoad() called"); |
| 184 } | 162 } |
| 185 synchronized (mLock) { | 163 synchronized (mLock) { |
| 186 ensureInitializedLocked(); | 164 ensureInitializedLocked(); |
| 187 if (DEBUG) { | 165 if (DEBUG) { |
| 188 Log.i(TAG, | 166 Log.i(TAG, |
| 189 String.format(Locale.US, | 167 String.format(Locale.US, |
| 190 "mInBrowserProcess=%s mBrowserUsesSharedRelro=%s
mWaitForSharedRelros=%s", | 168 "mInBrowserProcess=%b mBrowserUsesSharedRelro=%b
mWaitForSharedRelros=%b", |
| 191 mInBrowserProcess ? "true" : "false", | 169 mInBrowserProcess, mBrowserUsesSharedRelro, mWai
tForSharedRelros)); |
| 192 mBrowserUsesSharedRelro ? "true" : "false", | |
| 193 mWaitForSharedRelros ? "true" : "false")); | |
| 194 } | 170 } |
| 195 | 171 |
| 196 if (mLoadedLibraries == null) { | 172 if (mLoadedLibraries == null) { |
| 197 if (DEBUG) { | 173 if (DEBUG) { |
| 198 Log.i(TAG, "No libraries loaded"); | 174 Log.i(TAG, "No libraries loaded"); |
| 199 } | 175 } |
| 200 } else { | 176 } else { |
| 201 if (mInBrowserProcess) { | 177 if (mInBrowserProcess) { |
| 202 // Create new Bundle containing RELRO section information | 178 // Create new Bundle containing RELRO section information |
| 203 // for all loaded libraries. Make it available to getSharedR
elros(). | 179 // for all loaded libraries. Make it available to getSharedR
elros(). |
| (...skipping 104 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 308 /** | 284 /** |
| 309 * Call this method before loading any libraries to indicate that this | 285 * Call this method before loading any libraries to indicate that this |
| 310 * process shall neither create or reuse shared RELRO sections. | 286 * process shall neither create or reuse shared RELRO sections. |
| 311 */ | 287 */ |
| 312 @Override | 288 @Override |
| 313 public void disableSharedRelros() { | 289 public void disableSharedRelros() { |
| 314 if (DEBUG) { | 290 if (DEBUG) { |
| 315 Log.i(TAG, "disableSharedRelros() called"); | 291 Log.i(TAG, "disableSharedRelros() called"); |
| 316 } | 292 } |
| 317 synchronized (mLock) { | 293 synchronized (mLock) { |
| 294 ensureInitializedLocked(); |
| 318 mInBrowserProcess = false; | 295 mInBrowserProcess = false; |
| 319 mWaitForSharedRelros = false; | 296 mWaitForSharedRelros = false; |
| 320 mBrowserUsesSharedRelro = false; | 297 mBrowserUsesSharedRelro = false; |
| 321 } | 298 } |
| 322 } | 299 } |
| 323 | 300 |
| 324 /** | 301 /** |
| 325 * Call this method before loading any libraries to indicate that this | 302 * Call this method before loading any libraries to indicate that this |
| 326 * process is ready to reuse shared RELRO sections from another one. | 303 * process is ready to reuse shared RELRO sections from another one. |
| 327 * Typically used when starting service processes. | 304 * Typically used when starting service processes. |
| (...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 434 if (!nativeUseSharedRelro(libName, libInfo)) { | 411 if (!nativeUseSharedRelro(libName, libInfo)) { |
| 435 Log.w(TAG, "Could not use shared RELRO section for " + libName); | 412 Log.w(TAG, "Could not use shared RELRO section for " + libName); |
| 436 } else { | 413 } else { |
| 437 if (DEBUG) { | 414 if (DEBUG) { |
| 438 Log.i(TAG, "Using shared RELRO section for " + libName); | 415 Log.i(TAG, "Using shared RELRO section for " + libName); |
| 439 } | 416 } |
| 440 } | 417 } |
| 441 } | 418 } |
| 442 | 419 |
| 443 // In service processes, close all file descriptors from the map now. | 420 // In service processes, close all file descriptors from the map now. |
| 444 if (!mInBrowserProcess) closeLibInfoMap(relroMap); | 421 if (!mInBrowserProcess) { |
| 422 closeLibInfoMap(relroMap); |
| 423 } |
| 445 | 424 |
| 446 if (DEBUG) { | 425 if (DEBUG) { |
| 447 Log.i(TAG, "Linker.useSharedRelrosLocked() exiting"); | 426 Log.i(TAG, "Linker.useSharedRelrosLocked() exiting"); |
| 448 } | 427 } |
| 449 } | 428 } |
| 450 | 429 |
| 451 /** | 430 /** |
| 452 * Implements loading a native shared library with the Chromium linker. | 431 * Implements loading a native shared library with the Chromium linker. |
| 453 * | 432 * |
| 454 * Load a native shared library with the Chromium linker. If the zip file | 433 * Load a native shared library with the Chromium linker. If the zip file |
| (...skipping 181 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 636 | 615 |
| 637 /** | 616 /** |
| 638 * Native method used to use a shared RELRO section. | 617 * Native method used to use a shared RELRO section. |
| 639 * | 618 * |
| 640 * @param library Library name. | 619 * @param library Library name. |
| 641 * @param libInfo A LibInfo instance containing valid RELRO information | 620 * @param libInfo A LibInfo instance containing valid RELRO information |
| 642 * @return true on success. | 621 * @return true on success. |
| 643 */ | 622 */ |
| 644 private static native boolean nativeUseSharedRelro(String library, LibInfo l
ibInfo); | 623 private static native boolean nativeUseSharedRelro(String library, LibInfo l
ibInfo); |
| 645 } | 624 } |
| OLD | NEW |