Android5.0中Binder机制相关的native层和java层中的Binder代理和实体的对象的分析
2016-12-03 11:19
866 查看
文章仅仅用于个人的学习记录,基本上内容都是网上各个大神的杰作,此处摘录过来以自己的理解学习方式记录一下。
个人最为认可和推崇的大神文章:
http://blog.csdn.net/luoshengyang/article/details/6618363 罗升阳Binder系列文章
http://blog.csdn.net/innost/article/details/47208049 Innost的Binder讲解
https://my.oschina.net/youranhongcha/blog/149575 侯 亮的Binder系列文章.
1、java层的binder相关方法总结.
1.1、Binder
1)、获取正在进行跨进程调用的进程的uid、pid以及一些清楚和恢复的方法.
2)、queryLocalInterface(String descriptor)
当前不是出于跨进程调用时候会返回mOwner,否则返回null。配合attachInterface
private String mDescriptor;
3)、getInterfaceDescriptor()
4)、onTransact()
一般来说都不会调用到此方法,会调用它的具体实现类,来完成各子的逻辑(在aidl生成的其实内部去去调用proxy了)
5)、transact()
内部主要的就是调用了onTransact()方法每次是叫如是子类对象在调用的话,那么很显然调用到了子类重写的onTransact当中.
6)、execTransact()
这个函数很关键,是JNI层往java层走的切入点,在驱动处理完client端的请求的时候,服务端的处理函数就会回调到
这里。很显现就是去调用具体的Binder实现类的onTransact函数进而完成服务端的处理.
2.1、BinderProxy
1)、queryLocalInterface(String descriptor)
此时肯定是跨进程调用,这个方法返回null,从名字也可以看出来,毕竟它不是本地Local接口.
2)、transact(...)
可以看出直接调用了native的方法transactNative,去进一步处理,请求驱动通信.
3)、getInterfaceDescriptor()
public native String getInterfaceDescriptor() throws RemoteException;
2、native层的重要的类的方法总结.
2.1、Binder对象的实体BBinder
1)、transact(......).
2)、onTransact(......).
这个方法一般也调用不到,会调用到子类重写的这个.
3)、queryLocalInterface(......).
此方法在IBinder类中默认实现是返回null,而BBinder和BpBinder都继承自它,所以没有额外的重写的时候也是返回nul.
但是在Binder机制中:class BnInterface : public INTERFACE, public BBinder 而每个实现的IXXX都要用这个更模板类,
在这个模板类中在IInterface.h文件中重写了queryLocalInterface如下:
也是属于本进程的描述符的时候返回this.也就是BBinder对象.
2.2、Binder的引用对象BpBinder.
1)、构造(int32_t handle).
这个参数很关键,用来查找相应的引用,并且通过IPCThreadState::self()来获得一个对象准备和驱动交互.
2)、transact(......).
最主要的就是调用IPCThreadState对象的transact.
3)、queryLocalInterface(......).
由于BpBinder没有重写这个,它的子类BpInterface也没有重写,所以默认它是返回的null.
个人最为认可和推崇的大神文章:
http://blog.csdn.net/luoshengyang/article/details/6618363 罗升阳Binder系列文章
http://blog.csdn.net/innost/article/details/47208049 Innost的Binder讲解
https://my.oschina.net/youranhongcha/blog/149575 侯 亮的Binder系列文章.
1、java层的binder相关方法总结.
1.1、Binder
1)、获取正在进行跨进程调用的进程的uid、pid以及一些清楚和恢复的方法.
public static final native int getCallingPid();
public static final native int getCallingUid();
public static final native long clearCallingIdentity();
public static final native void restoreCallingIdentity(long token);
2)、queryLocalInterface(String descriptor)
当前不是出于跨进程调用时候会返回mOwner,否则返回null。配合attachInterface
private String mDescriptor;
public IInterface queryLocalInterface(String descriptor) {
if (mDescriptor.equals(descriptor)) {
return mOwner;
}
return null;
}
public void attachInterface(IInterface owner, String descriptor) {
mOwner = owner;
mDescriptor = descriptor;
}
3)、getInterfaceDescriptor()
public String getInterfaceDescriptor() {
return mDescriptor;
}
4)、onTransact()
一般来说都不会调用到此方法,会调用它的具体实现类,来完成各子的逻辑(在aidl生成的其实内部去去调用proxy了)
protected boolean onTransact(int code, Parcel data, Parcel reply,
int flags) throws RemoteException {
if (code == INTERFACE_TRANSACTION) {
reply.writeString(getInterfaceDescriptor());
return true;
} else if (code == DUMP_TRANSACTION) {
//...... 处理一些通信异常信息
}
return false;
}
5)、transact()
内部主要的就是调用了onTransact()方法每次是叫如是子类对象在调用的话,那么很显然调用到了子类重写的onTransact当中.
public final boolean transact(int code, Parcel data, Parcel reply,
int flags) throws RemoteException {
if (false) Log.v("Binder", "Transact: " + code + " to " + this);
if (data != null) {
data.setDataPosition(0);
}
boolean r = onTransact(code, data, reply, flags);
if (reply != null) {
reply.setDataPosition(0);
}
return r;
}
6)、execTransact()
这个函数很关键,是JNI层往java层走的切入点,在驱动处理完client端的请求的时候,服务端的处理函数就会回调到
这里。很显现就是去调用具体的Binder实现类的onTransact函数进而完成服务端的处理.
// Entry point from android_util_Binder.cpp's onTransact
private boolean execTransact(int code, long dataObj, long replyObj,
int flags) {
Parcel data = Parcel.obtain(dataObj);
Parcel reply = Parcel.obtain(replyObj);
boolean res;
try {
//此时相应的子类,有重写就调用自己的onTransact,
res = onTransact(code, data, reply, flags);
} catch (RemoteException e) {
//......
} catch (RuntimeException e) {
//......
} catch (OutOfMemoryError e) {
//......
}
//......
return res;
}
2.1、BinderProxy
1)、queryLocalInterface(String descriptor)
此时肯定是跨进程调用,这个方法返回null,从名字也可以看出来,毕竟它不是本地Local接口.
public IInterface queryLocalInterface(String descriptor) {//代理端的这个查询本地接口返回的是null.
return null;
}
2)、transact(...)
可以看出直接调用了native的方法transactNative,去进一步处理,请求驱动通信.
public native boolean transactNative(int code, Parcel data, Parcel reply,
int flags) throws RemoteException;
public boolean transact(int code, Parcel data, Parcel reply, int flags) throws RemoteException {
Binder.checkParcel(this, code, data, "Unreasonably large binder buffer");
return transactNative(code, data, reply, flags);
}
3)、getInterfaceDescriptor()
public native String getInterfaceDescriptor() throws RemoteException;
2、native层的重要的类的方法总结.
2.1、Binder对象的实体BBinder
1)、transact(......).
status_t BBinder::transact(
uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
{
data.setDataPosition(0);
status_t err = NO_ERROR;
switch (code) {
case PING_TRANSACTION:
reply->writeInt32(pingBinder());
break;
default:
err = onTransact(code, data, reply, flags);//就是调用自己的onTransact函数嘛,谁实例化的就调用谁!
break;
}
if (reply != NULL) {
reply->setDataPosition(0);
}
return err;
}
2)、onTransact(......).
这个方法一般也调用不到,会调用到子类重写的这个.
status_t BBinder::onTransact(
uint32_t code, const Parcel& data, Parcel* reply, uint32_t /*flags*/)
{
switch (code) {
case INTERFACE_TRANSACTION:
reply->writeString16(getInterfaceDescriptor());
return NO_ERROR;
case DUMP_TRANSACTION: {
int fd = data.readFileDescriptor();
int argc = data.readInt32();
Vector<String16> args;
for (int i = 0; i < argc && data.dataAvail() > 0; i++) {
args.add(data.readString16());
}
return dump(fd, args);
}
case SYSPROPS_TRANSACTION: {
report_sysprop_change();
return NO_ERROR;
}
default:
return UNKNOWN_TRANSACTION;
}
}
3)、queryLocalInterface(......).
此方法在IBinder类中默认实现是返回null,而BBinder和BpBinder都继承自它,所以没有额外的重写的时候也是返回nul.
但是在Binder机制中:class BnInterface : public INTERFACE, public BBinder 而每个实现的IXXX都要用这个更模板类,
在这个模板类中在IInterface.h文件中重写了queryLocalInterface如下:
也是属于本进程的描述符的时候返回this.也就是BBinder对象.
template<typename INTERFACE>
inline sp<IInterface> BnInterface<INTERFACE>::queryLocalInterface(
const String16& _descriptor)
{
if (_descriptor == INTERFACE::descriptor) return this;
return NULL;
}
2.2、Binder的引用对象BpBinder.
1)、构造(int32_t handle).
这个参数很关键,用来查找相应的引用,并且通过IPCThreadState::self()来获得一个对象准备和驱动交互.
BpBinder::BpBinder(int32_t handle)
: mHandle(handle)
, mAlive(1)
, mObitsSent(0)
, mObituaries(NULL)
{
ALOGV("Creating BpBinder %p handle %d\n", this, mHandle);
extendObjectLifetime(OBJECT_LIFETIME_WEAK);
IPCThreadState::self()->incWeakHandle(handle);
}
2)、transact(......).
最主要的就是调用IPCThreadState对象的transact.
status_t BpBinder::transact(
uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
{
// Once a binder has died, it will never come back to life.
if (mAlive) {
//那mHandle就是咋实例化BpBinder的时候传入的.
//BpBinder最终是调用IPCThreadState去和驱动打交道的,这个IPCThreadState每个线程一个.
status_t status = IPCThreadState::self()->transact(
mHandle, code, data, reply, flags);
if (status == DEAD_OBJECT) mAlive = 0;
return status;
}
return DEAD_OBJECT;
}
3)、queryLocalInterface(......).
由于BpBinder没有重写这个,它的子类BpInterface也没有重写,所以默认它是返回的null.
相关文章推荐
- Android5.0中Binder机制相关的native层的Parcel分析
- Java动态代理机制分析
- Android系统的Binder机制之三——服务代理对象(2)
- Android系统进程间通信Binder机制在应用程序框架层的Java接口源代码文件分析
- Android系统的Binder机制之二——服务代理对象(1)
- Android系统的Binder机制之三——服务代理对象(2)
- Java 动态代理机制分析及扩展,第 1 部分
- Java 动态代理机制分析及扩展
- Android系统的Binder机制之二——服务代理对象(1)
- [Binder.5] Android系统进程间通信Binder机制在应用程序框架层的Java接口源代码分析
- Android系统进程间通信Binder机制在应用程序框架层的Java接口源代码分析
- 转:Java 动态代理机制分析及扩展
- Java 动态代理机制分析及扩展
- Android系统进程间通信Binder机制在应用程序框架层的Java接口源代码分析(2)
- Android系统的Binder机制之三——服务代理对象(2)
- Android系统的Binder机制之二——服务代理对象(1)
- Android系统进程间通信Binder机制在应用程序框架层的Java接口源代码分析
- Android系统进程间通信Binder机制在应用程序框架层的Java接口源代码分析
- Android系统Binder机制之二(服务代理对象 上篇)
- Android系统的Binder机制之二——服务代理对象(1)