Index: content/public/android/java/src/org/chromium/content/browser/ChildProcessConnection.java |
diff --git a/content/public/android/java/src/org/chromium/content/browser/SandboxedProcessConnection.java b/content/public/android/java/src/org/chromium/content/browser/ChildProcessConnection.java |
similarity index 65% |
rename from content/public/android/java/src/org/chromium/content/browser/SandboxedProcessConnection.java |
rename to content/public/android/java/src/org/chromium/content/browser/ChildProcessConnection.java |
index c28a3c4d66b8997a439e8e4c9e4650c044714ab1..66012c5919515eb7a65f862af3b2bd2b85137d99 100644 |
--- a/content/public/android/java/src/org/chromium/content/browser/SandboxedProcessConnection.java |
+++ b/content/public/android/java/src/org/chromium/content/browser/ChildProcessConnection.java |
@@ -22,62 +22,63 @@ import java.util.concurrent.atomic.AtomicBoolean; |
import org.chromium.base.CalledByNative; |
import org.chromium.base.CpuFeatures; |
import org.chromium.base.ThreadUtils; |
-import org.chromium.content.app.SandboxedProcessService; |
+import org.chromium.content.app.ChildProcessService; |
import org.chromium.content.common.CommandLine; |
-import org.chromium.content.common.ISandboxedProcessCallback; |
-import org.chromium.content.common.ISandboxedProcessService; |
+import org.chromium.content.common.IChildProcessCallback; |
+import org.chromium.content.common.IChildProcessService; |
import org.chromium.content.common.TraceEvent; |
-public class SandboxedProcessConnection implements ServiceConnection { |
+public class ChildProcessConnection implements ServiceConnection { |
interface DeathCallback { |
- void onSandboxedProcessDied(int pid); |
+ void onChildProcessDied(int pid); |
} |
// Names of items placed in the bind intent or connection bundle. |
public static final String EXTRA_COMMAND_LINE = |
- "com.google.android.apps.chrome.extra.sandbox_command_line"; |
+ "com.google.android.apps.chrome.extra.command_line"; |
public static final String EXTRA_NATIVE_LIBRARY_NAME = |
- "com.google.android.apps.chrome.extra.sandbox_native_library_name"; |
+ "com.google.android.apps.chrome.extra.native_library_name"; |
// Note the FDs may only be passed in the connection bundle. |
public static final String EXTRA_FILES_PREFIX = |
- "com.google.android.apps.chrome.extra.sandbox_extraFile_"; |
+ "com.google.android.apps.chrome.extra.extraFile_"; |
public static final String EXTRA_FILES_ID_SUFFIX = "_id"; |
public static final String EXTRA_FILES_FD_SUFFIX = "_fd"; |
- // Used to pass the CPU core count to sandboxed processes. |
+ // Used to pass the CPU core count to child processes. |
public static final String EXTRA_CPU_COUNT = |
"com.google.android.apps.chrome.extra.cpu_count"; |
- // Used to pass the CPU features mask to sandboxed processes. |
+ // Used to pass the CPU features mask to child processes. |
public static final String EXTRA_CPU_FEATURES = |
"com.google.android.apps.chrome.extra.cpu_features"; |
private final Context mContext; |
private final int mServiceNumber; |
- private final SandboxedProcessConnection.DeathCallback mDeathCallback; |
- private final Class<? extends SandboxedProcessService> mServiceClass; |
+ private final ChildProcessConnection.DeathCallback mDeathCallback; |
+ private final Class<? extends ChildProcessService> mServiceClass; |
// Synchronization: While most internal flow occurs on the UI thread, the public API |
// (specifically bind and unbind) may be called from any thread, hence all entry point methods |
- // into the class are synchronized on the SandboxedProcessConnection instance to protect access |
+ // into the class are synchronized on the ChildProcessConnection instance to protect access |
// to these members. But see also the TODO where AsyncBoundServiceConnection is created. |
- private ISandboxedProcessService mService = null; |
+ private final Object mUiThreadLock = new Object(); |
+ private IChildProcessService mService = null; |
private boolean mServiceConnectComplete = false; |
- private int mPID = 0; // Process ID of the corresponding sandboxed process. |
+ private int mPID = 0; // Process ID of the corresponding child process. |
private HighPriorityConnection mHighPriorityConnection = null; |
private int mHighPriorityConnectionCount = 0; |
- private static final String TAG = "SandboxedProcessConnection"; |
+ private static final String TAG = "ChildProcessConnection"; |
private static class ConnectionParams { |
final String[] mCommandLine; |
final FileDescriptorInfo[] mFilesToBeMapped; |
- final ISandboxedProcessCallback mCallback; |
+ final IChildProcessCallback mCallback; |
final Runnable mOnConnectionCallback; |
ConnectionParams( |
String[] commandLine, |
FileDescriptorInfo[] filesToBeMapped, |
- ISandboxedProcessCallback callback, |
+ IChildProcessCallback callback, |
Runnable onConnectionCallback) { |
mCommandLine = commandLine; |
mFilesToBeMapped = filesToBeMapped; |
@@ -90,9 +91,9 @@ public class SandboxedProcessConnection implements ServiceConnection { |
private ConnectionParams mConnectionParams; |
private boolean mIsBound; |
- SandboxedProcessConnection(Context context, int number, |
- SandboxedProcessConnection.DeathCallback deathCallback, |
- Class<? extends SandboxedProcessService> serviceClass) { |
+ ChildProcessConnection(Context context, int number, |
+ ChildProcessConnection.DeathCallback deathCallback, |
+ Class<? extends ChildProcessService> serviceClass) { |
mContext = context; |
mServiceNumber = number; |
mDeathCallback = deathCallback; |
@@ -103,43 +104,48 @@ public class SandboxedProcessConnection implements ServiceConnection { |
return mServiceNumber; |
} |
- synchronized ISandboxedProcessService getService() { |
- return mService; |
+ IChildProcessService getService() { |
+ synchronized(mUiThreadLock) { |
+ return mService; |
+ } |
} |
private Intent createServiceBindIntent() { |
Intent intent = new Intent(); |
- intent.setClassName(mContext, mServiceClass.getName() + mServiceNumber); |
+ String serviceClassNameBase = mServiceClass.getName().replaceAll("[0-9]*$", ""); |
+ intent.setClassName(mContext, serviceClassNameBase + mServiceNumber); |
intent.setPackage(mContext.getPackageName()); |
return intent; |
} |
/** |
- * Bind to an ISandboxedProcessService. This must be followed by a call to setupConnection() |
+ * Bind to an IChildProcessService. This must be followed by a call to setupConnection() |
* to setup the connection parameters. (These methods are separated to allow the client |
* to pass whatever parameters they have available here, and complete the remainder |
* later while reducing the connection setup latency). |
* @param nativeLibraryName The name of the shared native library to be loaded for the |
- * sandboxed process. |
- * @param commandLine (Optional) Command line for the sandboxed process. If omitted, then |
+ * child process. |
+ * @param commandLine (Optional) Command line for the child process. If omitted, then |
* the command line parameters must instead be passed to setupConnection(). |
*/ |
- synchronized void bind(String nativeLibraryName, String[] commandLine) { |
- TraceEvent.begin(); |
- assert !ThreadUtils.runningOnUiThread(); |
+ void bind(String nativeLibraryName, String[] commandLine) { |
+ synchronized(mUiThreadLock) { |
+ TraceEvent.begin(); |
+ assert !ThreadUtils.runningOnUiThread(); |
- final Intent intent = createServiceBindIntent(); |
+ final Intent intent = createServiceBindIntent(); |
- intent.putExtra(EXTRA_NATIVE_LIBRARY_NAME, nativeLibraryName); |
- if (commandLine != null) { |
- intent.putExtra(EXTRA_COMMAND_LINE, commandLine); |
- } |
+ intent.putExtra(EXTRA_NATIVE_LIBRARY_NAME, nativeLibraryName); |
+ if (commandLine != null) { |
+ intent.putExtra(EXTRA_COMMAND_LINE, commandLine); |
+ } |
- mIsBound = mContext.bindService(intent, this, Context.BIND_AUTO_CREATE); |
- if (!mIsBound) { |
- onBindFailed(); |
+ mIsBound = mContext.bindService(intent, this, Context.BIND_AUTO_CREATE); |
+ if (!mIsBound) { |
+ onBindFailed(); |
+ } |
+ TraceEvent.end(); |
} |
- TraceEvent.end(); |
} |
/** Setup a connection previous bound via a call to bind(). |
@@ -150,50 +156,56 @@ public class SandboxedProcessConnection implements ServiceConnection { |
* @param callback Used for status updates regarding this process connection. |
* @param onConnectionCallback will be run when the connection is setup and ready to use. |
*/ |
- synchronized void setupConnection( |
+ void setupConnection( |
String[] commandLine, |
FileDescriptorInfo[] filesToBeMapped, |
- ISandboxedProcessCallback callback, |
+ IChildProcessCallback callback, |
Runnable onConnectionCallback) { |
- TraceEvent.begin(); |
- assert mConnectionParams == null; |
- mConnectionParams = new ConnectionParams(commandLine, filesToBeMapped, callback, |
- onConnectionCallback); |
- if (mServiceConnectComplete) { |
- doConnectionSetup(); |
+ synchronized(mUiThreadLock) { |
+ TraceEvent.begin(); |
+ assert mConnectionParams == null; |
+ mConnectionParams = new ConnectionParams(commandLine, filesToBeMapped, callback, |
+ onConnectionCallback); |
+ if (mServiceConnectComplete) { |
+ doConnectionSetup(); |
+ } |
+ TraceEvent.end(); |
} |
- TraceEvent.end(); |
} |
/** |
- * Unbind the ISandboxedProcessService. It is safe to call this multiple times. |
+ * Unbind the IChildProcessService. It is safe to call this multiple times. |
*/ |
- synchronized void unbind() { |
- if (mIsBound) { |
- mContext.unbindService(this); |
- mIsBound = false; |
- } |
- if (mService != null) { |
- if (mHighPriorityConnection != null) { |
- unbindHighPriority(true); |
+ void unbind() { |
+ synchronized(mUiThreadLock) { |
+ if (mIsBound) { |
+ mContext.unbindService(this); |
+ mIsBound = false; |
+ } |
+ if (mService != null) { |
+ if (mHighPriorityConnection != null) { |
+ unbindHighPriority(true); |
+ } |
+ mService = null; |
+ mPID = 0; |
} |
- mService = null; |
- mPID = 0; |
+ mConnectionParams = null; |
+ mServiceConnectComplete = false; |
} |
- mConnectionParams = null; |
- mServiceConnectComplete = false; |
} |
// Called on the main thread to notify that the service is connected. |
@Override |
public void onServiceConnected(ComponentName className, IBinder service) { |
- TraceEvent.begin(); |
- mServiceConnectComplete = true; |
- mService = ISandboxedProcessService.Stub.asInterface(service); |
- if (mConnectionParams != null) { |
- doConnectionSetup(); |
+ synchronized(mUiThreadLock) { |
+ TraceEvent.begin(); |
+ mServiceConnectComplete = true; |
+ mService = IChildProcessService.Stub.asInterface(service); |
+ if (mConnectionParams != null) { |
+ doConnectionSetup(); |
+ } |
+ TraceEvent.end(); |
} |
- TraceEvent.end(); |
} |
// Called on the main thread to notify that the bindService() call failed (returned false). |
@@ -212,8 +224,7 @@ public class SandboxedProcessConnection implements ServiceConnection { |
TraceEvent.begin(); |
assert mServiceConnectComplete && mConnectionParams != null; |
// Capture the callback before it is potentially nulled in unbind(). |
- Runnable onConnectionCallback = |
- mConnectionParams != null ? mConnectionParams.mOnConnectionCallback : null; |
+ Runnable onConnectionCallback = mConnectionParams.mOnConnectionCallback; |
if (onConnectionCallback == null) { |
unbind(); |
} else if (mService != null) { |
@@ -273,7 +284,7 @@ public class SandboxedProcessConnection implements ServiceConnection { |
TraceEvent.end(); |
} |
- // Called on the main thread to notify that the sandboxed service did not disconnect gracefully. |
+ // Called on the main thread to notify that the child service did not disconnect gracefully. |
@Override |
public void onServiceDisconnected(ComponentName className) { |
int pid = mPID; // Stash pid & connection callback since unbind() will clear them. |
@@ -282,7 +293,7 @@ public class SandboxedProcessConnection implements ServiceConnection { |
Log.w(TAG, "onServiceDisconnected (crash?): pid=" + pid); |
unbind(); // We don't want to auto-restart on crash. Let the browser do that. |
if (pid != 0) { |
- mDeathCallback.onSandboxedProcessDied(pid); |
+ mDeathCallback.onChildProcessDied(pid); |
} |
if (onConnectionCallback != null) { |
onConnectionCallback.run(); |
@@ -293,30 +304,34 @@ public class SandboxedProcessConnection implements ServiceConnection { |
* Bind the service with a new high priority connection. This will make the service |
* as important as the main process. |
*/ |
- synchronized void bindHighPriority() { |
- if (mService == null) { |
- Log.w(TAG, "The connection is not bound for " + mPID); |
- return; |
- } |
- if (mHighPriorityConnection == null) { |
- mHighPriorityConnection = new HighPriorityConnection(); |
- mHighPriorityConnection.bind(); |
+ void bindHighPriority() { |
+ synchronized(mUiThreadLock) { |
+ if (mService == null) { |
+ Log.w(TAG, "The connection is not bound for " + mPID); |
+ return; |
+ } |
+ if (mHighPriorityConnection == null) { |
+ mHighPriorityConnection = new HighPriorityConnection(); |
+ mHighPriorityConnection.bind(); |
+ } |
+ mHighPriorityConnectionCount++; |
} |
- mHighPriorityConnectionCount++; |
} |
/** |
* Unbind the service as the high priority connection. |
*/ |
- synchronized void unbindHighPriority(boolean force) { |
- if (mService == null) { |
- Log.w(TAG, "The connection is not bound for " + mPID); |
- return; |
- } |
- mHighPriorityConnectionCount--; |
- if (force || (mHighPriorityConnectionCount == 0 && mHighPriorityConnection != null)) { |
- mHighPriorityConnection.unbind(); |
- mHighPriorityConnection = null; |
+ void unbindHighPriority(boolean force) { |
+ synchronized(mUiThreadLock) { |
+ if (mService == null) { |
+ Log.w(TAG, "The connection is not bound for " + mPID); |
+ return; |
+ } |
+ mHighPriorityConnectionCount--; |
+ if (force || (mHighPriorityConnectionCount == 0 && mHighPriorityConnection != null)) { |
+ mHighPriorityConnection.unbind(); |
+ mHighPriorityConnection = null; |
+ } |
} |
} |
@@ -350,7 +365,9 @@ public class SandboxedProcessConnection implements ServiceConnection { |
/** |
* @return The connection PID, or 0 if not yet connected. |
*/ |
- synchronized public int getPid() { |
- return mPID; |
+ public int getPid() { |
+ synchronized(mUiThreadLock) { |
+ return mPID; |
+ } |
} |
} |