binder机制原理分析一共分5个部分,其实省了一点,但是分析到后面都差不多了,以后再补充吧。
1、ServiceManager 进程启动
2、普通Service注册到ServiceManager
3、从ServiceManager中获取服务
4、java层service的注册过程
5、Java层service的获取过程
步骤一、初始化注册jni对象
Binder通信最终还是依赖与native层,java层的binder是native层binder的一个封装,实现还是在native层,这个映射关系在系统初始化的时候(在AndroidRuntime.cpp中)就将javaBinder和nativeBinder进行建立。并分别有结构体与之对应,如gBinderOffset与Binder、gBinderInternalOffset与BinderInternal、gBinderProxyOffset与BinderProxy的映射关系,映射的地址都存在对应结构起的mObject中。
首先初始化jni:为了通过java调用native
int register_android_os_Binder(JNIEnv* env){
建立native与javaBinder之间的映射关系,gBinderOffset与Binder的映射,地址都存在mObject中
if (int_register_android_os_Binder(env) < 0)
return -1;
建立native与javaBinderInternal之间的映射关系,gBinderInternalOffset与BinderInternal的映射
if (int_register_android_os_BinderInternal(env) < 0)
return -1;
建立native与javaBinderProxy之间的映射关系,gBinderProxyOffset与BinderProxy的映射
if (int_register_android_os_BinderProxy(env) < 0)
return -1;
return 0;
}
举例:AMS的启动过程
ActivityManagerService.java
public void setSystemProcess() {
ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true);
}
ServiceManager.java
public static void addService(String name, IBinder service) {
getIServiceManager().addService(name, service, false);
}
步骤二、首先获取ServiceManager对象
private static IServiceManager getIServiceManager() {
..............判空略过.............
sServiceManager = ServiceManagerNative.asInterface(BinderInternal.getContextObject());
return sServiceManager;
}
BinderInternal.getContextObject()中调用的是native IBinder getContextObject(),因此:
static jobject android_os_BinderInternal_getContextObject(JNIEnv* env, jobject clazz){
//好熟悉的味道~~~
sp<IBinder> b = ProcessState::self()->getContextObject(NULL);
BpBinder(0)
return javaObjectForIBinder(env, b);
}
如果是native的addService,那么到这里就结束了,java层还需要转换一下:
- new BinderProx(),它是Binder的内部类
- BinderProx.mObject = BpBinder(0),也就是吧BpBinder(0)给了BinderProxy的mObject对象
jobject javaObjectForIBinder(JNIEnv* env, const sp<IBinder>& val){
.........
//创建一个新的BinderProxy对象,并将它注册到Natice BpBinder对象的ObjectManager中
object = env->NewObject(gBinderProxyOffsets.mClass, gBinderProxyOffsets.mConstructor);
if (object != NULL) {
// 通过BinderProxy.mObject,把这个BpBinder对象和BinderProxy对象关联了起来
env->SetLongField(object, gBinderProxyOffsets.mObject, (jlong)val.get());
val->incStrong((void*)javaObjectForIBinder);
jobject refObject = env->NewGlobalRef(
env->GetObjectField(object, gBinderProxyOffsets.mSelf));
val->attachObject(&gBinderProxyOffsets, refObject,
jnienv_to_javavm(env), proxy_cleanup);
// 新建一个死亡通知,并将死亡通知list存放在binder代理的mOrgue里面
sp<DeathRecipientList> drl = new DeathRecipientList;
drl->incStrong((void*)javaObjectForIBinder);
env->SetLongField(object,gBinderProxyOffsets.mOrgue,reinterpret_cast<jlong>(drl.get()));
android_atomic_inc(&gNumProxyRefs);
incRefsCreated(env);
}
return object;
}
所以前面的getIServiceManager就变成了ServiceManagerNative.asInterface(new BinderProxy());
private static IServiceManager getIServiceManager() {
..............判空略过.............
sServiceManager = ServiceManagerNative.asInterface(new BinderProxy());
return sServiceManager;
}
ServiceManagerNative & ServiceManagerNative.class
这里接着asInterface方法,为了进一步获取java层代理类
static public IServiceManager asInterface(IBinder obj){
//BinderProxy.class中的queryLocalInterface()方法很干脆,直接返回null。
IServiceManager in = (IServiceManager)obj.queryLocalInterface(descriptor);
if (in != null) {
return in;
}
//所以最终得到一个jave层binder的代理类ServiceManagerProxy()
return new ServiceManagerProxy(obj);
}
public IInterface queryLocalInterface(String descriptor) {
return null;
}
小节一下:
因此addService方法最后返回的IServiceManager就是new ServiceManagerProxy(new BinderProxy()),这个跟C++中得到的new BpServiceManager(new BpBinder(0))其实是一毛一样的,都是熟悉的味道。而且BinderProxy中的mObject对象其实就是存着native层的new BpBinder(0)。
步骤三、addService
封装parcel对象
获取到ServiceManager后就可以addService了,实际调用的是ServiceManagerProxy的addService方法
public void addService(String name, IBinder service, boolean allowIsolated)throws RemoteException{
同样,先封装一个parcel对象,java层的parcel也是对native层parcel的一个封装,
java层存的是native层parcel的地址对象。
Parcel data = Parcel.obtain();
Parcel reply = Parcel.obtain();
data.writeInterfaceToken(IServiceManager.descriptor);
data.writeString(name);
这里跟native的方法一样,也是通过native的Parcel::的writeStrongBinder方法写入server
data.writeStrongBinder(service);
data.writeInt(allowIsolated ? 1 : 0);
在native中也是通过remote()——>transact方法将信息透传到IPCThreadState中去发送,这里的remote就是java层的BinderProxy对象。一个套路
mRemote.transact(ADD_SERVICE_TRANSACTION, data, reply, 0);
reply.recycle();
data.recycle();
}
调用transact方法
BinderProxy中的transact调用了transactNative方法,也就是下面这个,将数据抛到了native层处理
static jboolean android_os_BinderProxy_transact(JNIEnv* env, jobject obj,jint code, jobject dataObj, jobject replyObj, jint flags){
........这里一大坨是将java式的参数转为native式..........
然后就是从BinderProxy的mObject中将BpBinder(0)对象取出来。
IBinder* target = (IBinder*)env->GetLongField(obj, gBinderProxyOffsets.mObject);
然后就是这句熟悉的话
status_t err = target->transact(code, *data, reply, flags);
}
最后在来说说这句:因为这个service是new出来的,而且service都继承了Binder对象。因此也调用了Binder的构造方法Binder(){init()},这个init()方法调用的就是native的init方法。
static void android_os_Binder_init(JNIEnv* env, jobject obj){
这里创建了JavaBBinderHolder,然后将它跟BinderOffset的mObject绑定。Jbh—>get一下就是JavaBBinder
JavaBBinderHolder* jbh = new JavaBBinderHolder();
jbh->incStrong((void*)android_os_Binder_init);
env->SetLongField(obj, gBinderOffsets.mObject, (jlong)jbh);
}
Parcel中的writeStrongBinder方法
public final void writeStrongBinder(IBinder val) {
nativeWriteStrongBinder(mNativePtr, val);
}
这里nativePtr就是Parcel.cpp的地址,ibinderForJavaObject(env, object)就是调用了object.get
static void android_os_Parcel_writeStrongBinder(JNIEnv* env, jclass clazz, jlong nativePtr, jobject object){
Parcel* parcel = reinterpret_cast<Parcel*>(nativePtr);
const status_t err = parcel->writeStrongBinder(ibinderForJavaObject(env, object));
}
sp<IBinder> ibinderForJavaObject(JNIEnv* env, jobject obj){
如果是Binder类型,就获取JavaBBinder对象
if (env->IsInstanceOf(obj, gBinderOffsets.mClass)) {
JavaBBinderHolder* jbh = (JavaBBinderHolder*)
env->GetLongField(obj, gBinderOffsets.mObject);
return jbh != NULL ? jbh->get(env, obj) : NULL;
}
如果是BinderProxy对象就获取BpBinder对象
if (env->IsInstanceOf(obj, gBinderProxyOffsets.mClass)) {
return (IBinder*)
env->GetLongField(obj, gBinderProxyOffsets.mObject);
}
return NULL;
}
这里也就是相当于:
const status_t err = parcel->writeStrongBinder(new JavaBBinder());
最后设置AMS的type类型,远程的BINDER_TYPE_HANDLER、本地的BINDER_TYPE_BINDER
status_t flatten_binder(const sp<ProcessState>&const sp<IBinder>& binder, Parcel* out){
IBinder *local = binder->localBinder();
if (!local) {
BpBinder *proxy = binder->remoteBinder();
const int32_t handle = proxy ? proxy->handle() : 0;
obj.type = BINDER_TYPE_HANDLE;
} else {
obj.type = BINDER_TYPE_BINDER;
}
return finish_flatten_binder(binder, obj, out);
}
接下来的过程就跟native注册server是binder的传输是一样的了。通过IpcThreadState调用transact方法,执行与binder驱动的一些列交互。
总结:
java层的binder注册最终还是通过调用native方法完成的,getIServiceManager()先获取到ServiceManagerProxy(BinderProxy),其中BinderProxy相当于BpBinder,ServiceManagerProxy相当于IServiceManager,然后通过BinderProxy.trance()方法通过调用transactNative()将parcel发送到native层去。