WebViewFactory.java revision 6c778cebc73e7eb76510f6e2183d804b8c07082b
1d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon/* 2d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * Copyright (C) 2012 The Android Open Source Project 3d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * 4d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * Licensed under the Apache License, Version 2.0 (the "License"); 5d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * you may not use this file except in compliance with the License. 6d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * You may obtain a copy of the License at 7d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * 8d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * http://www.apache.org/licenses/LICENSE-2.0 9d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * 10d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * Unless required by applicable law or agreed to in writing, software 11d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * distributed under the License is distributed on an "AS IS" BASIS, 12d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * See the License for the specific language governing permissions and 14d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * limitations under the License. 15d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon */ 16d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon 17d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixonpackage android.webkit; 18d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon 196c778cebc73e7eb76510f6e2183d804b8c07082bTorne (Richard Coles)import android.app.AppGlobals; 206c778cebc73e7eb76510f6e2183d804b8c07082bTorne (Richard Coles)import android.content.Context; 216c778cebc73e7eb76510f6e2183d804b8c07082bTorne (Richard Coles)import android.content.pm.PackageManager; 2208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles)import android.os.Build; 2308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles)import android.os.Process; 2408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles)import android.os.RemoteException; 2508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles)import android.os.ServiceManager; 26e09e976dad1d974ca28381451b0bbbeafbb872d5Ben Murdochimport android.os.StrictMode; 2703ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles)import android.util.AndroidRuntimeException; 28d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixonimport android.util.Log; 2908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles)import dalvik.system.VMRuntime; 3008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 3108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles)import java.io.File; 3208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 3308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles)import com.android.internal.os.Zygote; 34d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon 35d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon/** 36d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon * Top level factory, used creating all the main WebView implementation classes. 37b0e35846b818bdf0db9cafe881a8a535116d596eJared Duke * 38b0e35846b818bdf0db9cafe881a8a535116d596eJared Duke * @hide 39d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon */ 40b0e35846b818bdf0db9cafe881a8a535116d596eJared Dukepublic final class WebViewFactory { 41a7eaa8ee222611c28f050158db4b68c4d893a8a9Jonathan Dixon 42e09e976dad1d974ca28381451b0bbbeafbb872d5Ben Murdoch private static final String CHROMIUM_WEBVIEW_FACTORY = 43a9bbd9439c3043bd76a7474e6dca3c8131b1b258Torne (Richard Coles) "com.android.webview.chromium.WebViewChromiumFactoryProvider"; 44d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon 450e04bcfbdc1845c931b45b3498aef438b944e961Ben Murdoch private static final String NULL_WEBVIEW_FACTORY = 460e04bcfbdc1845c931b45b3498aef438b944e961Ben Murdoch "com.android.webview.nullwebview.NullWebViewFactoryProvider"; 470e04bcfbdc1845c931b45b3498aef438b944e961Ben Murdoch 4808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) // TODO(torne): we need to use a system property instead of hardcoding the library paths to 4908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) // enable it to be changed when a webview update apk is installed. 5008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) private static final String CHROMIUM_WEBVIEW_NATIVE_LIB_32 = 5108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) "/system/lib/libwebviewchromium.so"; 5208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) private static final String CHROMIUM_WEBVIEW_NATIVE_LIB_64 = 5308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) "/system/lib64/libwebviewchromium.so"; 5408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) private static final String CHROMIUM_WEBVIEW_NATIVE_RELRO_32 = 5508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) "/data/misc/shared_relro/libwebviewchromium32.relro"; 5608cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) private static final String CHROMIUM_WEBVIEW_NATIVE_RELRO_64 = 5708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) "/data/misc/shared_relro/libwebviewchromium64.relro"; 5808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 59d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon private static final String LOGTAG = "WebViewFactory"; 60d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon 61d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon private static final boolean DEBUG = false; 62d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon 63d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon // Cache the factory both for efficiency, and ensure any one process gets all webviews from the 64d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon // same provider. 65d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon private static WebViewFactoryProvider sProviderInstance; 669f9d34552f53c534141584a5ad4a8a49ad7939dcJohn Reck private static final Object sProviderLock = new Object(); 6708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) private static boolean sAddressSpaceReserved = false; 68d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon 69dc00a84af15ff3594a6dfa512be21095bf9fee82Ben Murdoch public static String getWebViewPackageName() { 70dc00a84af15ff3594a6dfa512be21095bf9fee82Ben Murdoch // TODO: Make this dynamic based on resource configuration. 71dc00a84af15ff3594a6dfa512be21095bf9fee82Ben Murdoch return "com.android.webview"; 72dc00a84af15ff3594a6dfa512be21095bf9fee82Ben Murdoch } 73dc00a84af15ff3594a6dfa512be21095bf9fee82Ben Murdoch 749f9d34552f53c534141584a5ad4a8a49ad7939dcJohn Reck static WebViewFactoryProvider getProvider() { 759f9d34552f53c534141584a5ad4a8a49ad7939dcJohn Reck synchronized (sProviderLock) { 769f9d34552f53c534141584a5ad4a8a49ad7939dcJohn Reck // For now the main purpose of this function (and the factory abstraction) is to keep 77d892afc88d3c67a7fe1c9550bfa7a452051d031dTorne (Richard Coles) // us honest and minimize usage of WebView internals when binding the proxy. 789f9d34552f53c534141584a5ad4a8a49ad7939dcJohn Reck if (sProviderInstance != null) return sProviderInstance; 79d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon 8008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) loadNativeLibrary(); 8108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 8203ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) Class<WebViewFactoryProvider> providerClass; 8303ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) try { 8403ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) providerClass = getFactoryClass(); 8503ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) } catch (ClassNotFoundException e) { 8603ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) Log.e(LOGTAG, "error loading provider", e); 8703ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) throw new AndroidRuntimeException(e); 88e09e976dad1d974ca28381451b0bbbeafbb872d5Ben Murdoch } 89e09e976dad1d974ca28381451b0bbbeafbb872d5Ben Murdoch 9003ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 9103ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) try { 9203ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) sProviderInstance = providerClass.newInstance(); 9303ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) if (DEBUG) Log.v(LOGTAG, "Loaded provider: " + sProviderInstance); 9403ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) return sProviderInstance; 9503ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) } catch (Exception e) { 9603ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) Log.e(LOGTAG, "error instantiating provider", e); 9703ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) throw new AndroidRuntimeException(e); 9803ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) } finally { 9903ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) StrictMode.setThreadPolicy(oldPolicy); 100e09e976dad1d974ca28381451b0bbbeafbb872d5Ben Murdoch } 101d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon } 102d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon } 103d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon 10403ce9b3e69f1eec85e7e7cbfd65bb9093e74cea8Torne (Richard Coles) private static Class<WebViewFactoryProvider> getFactoryClass() throws ClassNotFoundException { 1050e04bcfbdc1845c931b45b3498aef438b944e961Ben Murdoch try { 1066c778cebc73e7eb76510f6e2183d804b8c07082bTorne (Richard Coles) Context webViewContext = AppGlobals.getInitialApplication().createPackageContext( 1076c778cebc73e7eb76510f6e2183d804b8c07082bTorne (Richard Coles) getWebViewPackageName(), 1086c778cebc73e7eb76510f6e2183d804b8c07082bTorne (Richard Coles) Context.CONTEXT_INCLUDE_CODE | Context.CONTEXT_IGNORE_SECURITY); 1096c778cebc73e7eb76510f6e2183d804b8c07082bTorne (Richard Coles) ClassLoader clazzLoader = webViewContext.getClassLoader(); 1106c778cebc73e7eb76510f6e2183d804b8c07082bTorne (Richard Coles) return (Class<WebViewFactoryProvider>) Class.forName(CHROMIUM_WEBVIEW_FACTORY, true, 1116c778cebc73e7eb76510f6e2183d804b8c07082bTorne (Richard Coles) clazzLoader); 1126c778cebc73e7eb76510f6e2183d804b8c07082bTorne (Richard Coles) } catch (PackageManager.NameNotFoundException e) { 1136c778cebc73e7eb76510f6e2183d804b8c07082bTorne (Richard Coles) Log.e(LOGTAG, "Chromium WebView package does not exist"); 1140e04bcfbdc1845c931b45b3498aef438b944e961Ben Murdoch return (Class<WebViewFactoryProvider>) Class.forName(NULL_WEBVIEW_FACTORY); 1150e04bcfbdc1845c931b45b3498aef438b944e961Ben Murdoch } 116d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon } 11708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 11808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) /** 11908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) * Perform any WebView loading preparations that must happen in the zygote. 12008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) * Currently, this means allocating address space to load the real JNI library later. 12108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) */ 12208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) public static void prepareWebViewInZygote() { 12308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) try { 12408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) System.loadLibrary("webviewchromium_loader"); 12508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) sAddressSpaceReserved = nativeReserveAddressSpace(CHROMIUM_WEBVIEW_NATIVE_LIB_32, 12608cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) CHROMIUM_WEBVIEW_NATIVE_LIB_64); 12708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) if (sAddressSpaceReserved) { 12808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) if (DEBUG) Log.v(LOGTAG, "address space reserved"); 12908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } else { 13008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Log.e(LOGTAG, "reserving address space failed"); 13108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 13208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } catch (Throwable e) { 13308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) // Log and discard errors at this stage as we must not crash the zygote. 13408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Log.e(LOGTAG, "error preparing native loader", e); 13508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 13608cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 13708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 13808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) /** 13908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) * Perform any WebView loading preparations that must happen at boot from the system server, 14008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) * after the package manager has started. 14108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) * This must be called in the system server. 14208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) * Currently, this means spawning the child processes which will create the relro files. 14308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) */ 14408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) public static void prepareWebViewInSystemServer() { 14508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) if (DEBUG) Log.v(LOGTAG, "creating relro files"); 14608cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) if (new File(CHROMIUM_WEBVIEW_NATIVE_LIB_64).exists()) { 14708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) createRelroFile(Build.SUPPORTED_64_BIT_ABIS[0]); 14808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 14908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) if (new File(CHROMIUM_WEBVIEW_NATIVE_LIB_32).exists()) { 15008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) createRelroFile(Build.SUPPORTED_32_BIT_ABIS[0]); 15108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 15208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 15308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 15408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) private static void createRelroFile(String abi) { 15508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) try { 15608cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Process.start("android.webkit.WebViewFactory$RelroFileCreator", 15708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) "WebViewLoader-" + abi, 15808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Process.SHARED_RELRO_UID, 15908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Process.SHARED_RELRO_UID, 16008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) null, 16108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 0, // TODO(torne): do we need to set debug flags? 16208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Zygote.MOUNT_EXTERNAL_NONE, 16308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Build.VERSION.SDK_INT, 16408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) null, 16508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) abi, 16608cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) null); 16708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } catch (Throwable e) { 16808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) // Log and discard errors as we must not crash the system server. 16908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Log.e(LOGTAG, "error starting relro file creator for abi " + abi, e); 17008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 17108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 17208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 17308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) private static class RelroFileCreator { 17408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) // Called in an unprivileged child process to create the relro file. 17508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) public static void main(String[] args) { 17608cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) if (!sAddressSpaceReserved) { 17708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Log.e(LOGTAG, "can't create relro file; address space not reserved"); 17808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) return; 17908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 18008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) boolean result = nativeCreateRelroFile(CHROMIUM_WEBVIEW_NATIVE_LIB_32, 18108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) CHROMIUM_WEBVIEW_NATIVE_LIB_64, 18208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) CHROMIUM_WEBVIEW_NATIVE_RELRO_32, 18308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) CHROMIUM_WEBVIEW_NATIVE_RELRO_64); 18408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) if (!result) { 18508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Log.e(LOGTAG, "failed to create relro file"); 18608cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } else if (DEBUG) { 18708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Log.v(LOGTAG, "created relro file"); 18808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 18908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) try { 19008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) getUpdateService().notifyRelroCreationCompleted(VMRuntime.getRuntime().is64Bit(), 19108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) result); 19208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } catch (RemoteException e) { 19308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Log.e(LOGTAG, "error notifying update service", e); 19408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 19508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 19608cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) // Must explicitly exit or else this process will just sit around after we return. 19708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) System.exit(0); 19808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 19908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 20008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 20108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) private static void loadNativeLibrary() { 20208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) if (!sAddressSpaceReserved) { 20308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Log.e(LOGTAG, "can't load with relro file; address space not reserved"); 20408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) return; 20508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 20608cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 20708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) try { 20808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) getUpdateService().waitForRelroCreationCompleted(VMRuntime.getRuntime().is64Bit()); 20908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } catch (RemoteException e) { 21008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Log.e(LOGTAG, "error waiting for relro creation, proceeding without", e); 21108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) return; 21208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 21308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 21408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) boolean result = nativeLoadWithRelroFile(CHROMIUM_WEBVIEW_NATIVE_LIB_32, 21508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) CHROMIUM_WEBVIEW_NATIVE_LIB_64, 21608cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) CHROMIUM_WEBVIEW_NATIVE_RELRO_32, 21708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) CHROMIUM_WEBVIEW_NATIVE_RELRO_64); 21808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) if (!result) { 21908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Log.w(LOGTAG, "failed to load with relro file, proceeding without"); 22008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } else if (DEBUG) { 22108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) Log.v(LOGTAG, "loaded with relro file"); 22208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 22308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 22408cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 22508cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) private static IWebViewUpdateService getUpdateService() { 22608cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) return IWebViewUpdateService.Stub.asInterface(ServiceManager.getService("webviewupdate")); 22708cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) } 22808cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) 22908cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) private static native boolean nativeReserveAddressSpace(String lib32, String lib64); 23008cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) private static native boolean nativeCreateRelroFile(String lib32, String lib64, 23108cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) String relro32, String relro64); 23208cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) private static native boolean nativeLoadWithRelroFile(String lib32, String lib64, 23308cfaf672604422dd355d6703aec78f3aa5ee74eTorne (Richard Coles) String relro32, String relro64); 234d3101b1d300f5942fdb7dfa323dc8830c4edc007Jonathan Dixon} 235