最近在看Android源码,在看到IPC相关的部分时有了比较大的疑惑。
以Toast为例,在看代码的时候发现Toast的实现显示过程要调用NotificationManagerService的enqueueToast方法
public void enqueueToast(java.lang.String pkg, android.app.ITransientNotification callback, int duration)
这里是IPC调用,NotificationManagerService作为服务端,Toast对象作为客户端,但是我发现enqueueToast方法传递了一个TN对象过去,而这个TN对象是一个继承于Binder类的对象,在INotificationManager接口中的Proxy类里,是这样传递的
public void enqueueToast(java.lang.String pkg, android.app.ITransientNotification callback, int duration) throws android.os.RemoteException { android.os.Parcel _data = android.os.Parcel.obtain(); android.os.Parcel _reply = android.os.Parcel.obtain(); try { _data.writeInterfaceToken(DESCRIPTOR); _data.writeString(pkg);
_data.writeStrongBinder((((callback!=null))?(callback.asBinder()):(null)));
_data.writeInt(duration); mRemote.transact(Stub.TRANSACTION_enqueueToast, _data, _reply, 0); _reply.readException(); } finally { _reply.recycle(); _data.recycle(); } }
writeStrongBinder在这里传递了Binder对象过去,而在服务端NotificationManagerService,直接就通过该对象调用了它的show方法。
我的疑惑是:在这一步中,服务端通过这个TN对象调用客户端的show方法,是不是也得通过IPC机制,即这时候客户端Toast对象中的TN对象成了服务端?我看书的时候书上说每实例化一个Binder对象都会开启一个线程,在Binder驱动中注册一个服务,这里也是这样的吗?
客户端的Binder是用于服务端异步回调。