diff options
| -rw-r--r-- | core/java/android/os/Binder.java | 45 | ||||
| -rw-r--r-- | core/jni/android_util_Binder.cpp | 10 |
2 files changed, 37 insertions, 18 deletions
diff --git a/core/java/android/os/Binder.java b/core/java/android/os/Binder.java index 44e6f1b79102..a83c7b318d94 100644 --- a/core/java/android/os/Binder.java +++ b/core/java/android/os/Binder.java @@ -21,7 +21,6 @@ import android.util.Log; import android.util.Slog; import com.android.internal.util.FastPrintWriter; -import com.android.internal.util.FunctionalUtils; import com.android.internal.util.FunctionalUtils.ThrowingRunnable; import com.android.internal.util.FunctionalUtils.ThrowingSupplier; @@ -200,7 +199,7 @@ public class Binder implements IBinder { * then its own pid is returned. */ public static final native int getCallingPid(); - + /** * Return the Linux uid assigned to the process that sent you the * current transaction that is being processed. This uid can be used with @@ -333,7 +332,7 @@ public class Binder implements IBinder { * it needs to. */ public static final native void flushPendingCommands(); - + /** * Add the calling thread to the IPC thread pool. This function does * not return until the current process is exiting. @@ -370,7 +369,7 @@ public class Binder implements IBinder { } } } - + /** * Convenience method for associating a specific interface with the Binder. * After calling, queryLocalInterface() will be implemented for you @@ -381,7 +380,7 @@ public class Binder implements IBinder { mOwner = owner; mDescriptor = descriptor; } - + /** * Default implementation returns an empty interface name. */ @@ -406,7 +405,7 @@ public class Binder implements IBinder { public boolean isBinderAlive() { return true; } - + /** * Use information supplied to attachInterface() to return the * associated IInterface if it matches the requested @@ -607,7 +606,7 @@ public class Binder implements IBinder { } return r; } - + /** * Local implementation is a no-op. */ @@ -620,7 +619,7 @@ public class Binder implements IBinder { public boolean unlinkToDeath(DeathRecipient recipient, int flags) { return true; } - + protected void finalize() throws Throwable { try { destroyBinder(); @@ -714,7 +713,15 @@ public class Binder implements IBinder { } } +/** + * Java proxy for a native IBinder object. + * Allocated and constructed by the native javaObjectforIBinder function. Never allocated + * directly from Java code. + */ final class BinderProxy implements IBinder { + // See android_util_Binder.cpp for the native half of this. + // TODO: Consider using NativeAllocationRegistry instead of finalization. + // Assume the process-wide default value when created volatile boolean mWarnOnBlocking = Binder.sWarnOnBlocking; @@ -773,7 +780,7 @@ final class BinderProxy implements IBinder { reply.recycle(); } } - + public void dumpAsync(FileDescriptor fd, String[] args) throws RemoteException { Parcel data = Parcel.obtain(); Parcel reply = Parcel.obtain(); @@ -810,7 +817,7 @@ final class BinderProxy implements IBinder { BinderProxy() { mSelf = new WeakReference(this); } - + @Override protected void finalize() throws Throwable { try { @@ -819,9 +826,9 @@ final class BinderProxy implements IBinder { super.finalize(); } } - + private native final void destroy(); - + private static final void sendDeathNotice(DeathRecipient recipient) { if (false) Log.v("JavaBinder", "sendDeathNotice to " + recipient); try { @@ -832,8 +839,20 @@ final class BinderProxy implements IBinder { exc); } } - + + // This WeakReference to "this" is used only by native code to "attach" to the + // native IBinder object. + // Using WeakGlobalRefs instead currently appears unsafe, in that they can yield a + // non-null value after the BinderProxy is enqueued for finalization. + // Used only once immediately after construction. + // TODO: Consider making the extra native-to-java call to compute this on the fly. final private WeakReference mSelf; + + // Native pointer to the wrapped native IBinder object. Counted as strong reference. private long mObject; + + // Native pointer to native DeathRecipientList. Counted as strong reference. + // Basically owned by the JavaProxy object. Reference counted only because DeathRecipients + // hold a weak reference that can be temporarily promoted. private long mOrgue; } diff --git a/core/jni/android_util_Binder.cpp b/core/jni/android_util_Binder.cpp index 5b0f7768c165..768f53f30f62 100644 --- a/core/jni/android_util_Binder.cpp +++ b/core/jni/android_util_Binder.cpp @@ -488,8 +488,8 @@ protected: private: JavaVM* const mVM; - jobject mObject; - jweak mObjectWeak; // will be a weak ref to the same VM-side DeathRecipient after binderDied() + jobject mObject; // Initial strong ref to Java-side DeathRecipient. Cleared on binderDied(). + jweak mObjectWeak; // weak ref to the same Java-side DeathRecipient after binderDied(). wp<DeathRecipientList> mList; }; @@ -561,7 +561,7 @@ static void proxy_cleanup(const void* id, void* obj, void* cleanupCookie) env->DeleteGlobalRef((jobject)obj); } -static Mutex mProxyLock; +static Mutex gProxyLock; jobject javaObjectForIBinder(JNIEnv* env, const sp<IBinder>& val) { @@ -576,7 +576,7 @@ jobject javaObjectForIBinder(JNIEnv* env, const sp<IBinder>& val) // For the rest of the function we will hold this lock, to serialize // looking/creation/destruction of Java proxies for native Binder proxies. - AutoMutex _l(mProxyLock); + AutoMutex _l(gProxyLock); // Someone else's... do we know about it? jobject object = (jobject)val->findObject(&gBinderProxyOffsets); @@ -1252,7 +1252,7 @@ static jboolean android_os_BinderProxy_unlinkToDeath(JNIEnv* env, jobject obj, static void android_os_BinderProxy_destroy(JNIEnv* env, jobject obj) { // Don't race with construction/initialization - AutoMutex _l(mProxyLock); + AutoMutex _l(gProxyLock); IBinder* b = (IBinder*) env->GetLongField(obj, gBinderProxyOffsets.mObject); |