结合Binder机制看ActivityManager(一)

一、前言

本文主要分析Android系统的进程间通信 (Binder机制) 在应用框架层的Java源代码;相关文章网上很多,我们尽量少代码多流程。

Binder是一种基于C/S的架构,主要包含四个部分:

  1. 服务端 Server;
  2. 客户端 Client;
  3. Binder驱动;
  4. ServiceManager 管理远程服务;

二、流程图

先看一些 Binder 通信的流程图:

流程图说明

  • Binder 是一种基于 C/S的架构,分为 Client、Service、Binder驱动 三部分;
  • 客户端持有一个 Binder 的代理对象 BinderProxy,用于和远程服务的通信;
  • 关于Client端为什么持有一个 BinderProxy 对象,请参考 《Android Binder框架实现源码深入分析》

看一下 IBinder 类的说明,可得出以下结论:

  • IBinder 是一个轻量级的远程对象接口,它具备很高的性能;
  • IBinder 的核心Api Binder.transact() 会自动关联到 Binder.onTransact();
  • Binder.transact() 方法允许我们发送一个数据到 Binder 对象中,也能从一个 Binder 对象中接收数据;
  • Binder.transact() 方法是一个同步的方法,直到远程对象(Service端)从 Binder.onTransact() 返回数据时,Binder.transact() 才能拿到数据;
  • 在 transact() 中,通过 Parcel 来进行数据传输,且将数据写入到一个公共的缓存区当中;
  • 系统在每个进程当中都维护了一个线程池,当有IPC通信时,该线程池就分发出一条线程来执行这个通信操作;
  • 判断远程服务失效的方法有3中:
    1,transact() 方法接收到 RemoteException 异常,说明远程服务失效;
    2,调用 IBinder.pingBinder() 方法,如果返回 false 就说明远程服务失效;
    3,调用 IBinder.linkToDeath() 方法,可以向Binder中注册一个 DeathRecipient 接口作为参数,当远程服务失效时,就会触发这个接口参数的回调;

三、类图

3.1 Binder机制在 IActivityManager 中的应用

具体分析,请查看《结合Binder机制看ActivityManager(二)》

3.2 Binder机制在 AIDL 中的应用

AIDL能实现进程间通信,其实质仍然是 Binder机制 的使用;

AIDL文件所生成 class 文件的类的关系图

分析AIDL文件生成的 class 文件的代码

1,ExecuteCommand.aidl 文件

// AIDL文件
interface ExecuteCommand {
     String execute(String param);
}

2,ExecuteCommand.class 文件

public interface ExecuteCommand extends android.os.IInterface {

    // Stub就相当于是IActivityManager类图中的ActivityManagerNative类;
    public static abstract class Stub extends android.os.Binder implements com.example.aidl.interfaze.ExecuteCommand {
        private static final java.lang.String DESCRIPTOR = "com.example.aidl.interfaze.ExecuteCommand";

        public Stub() {
            this.attachInterface(this, DESCRIPTOR);
        }

        /**
         * asInterface()传入一个BinderProxy作为参数;
         */
        public static com.example.aidl.interfaze.ExecuteCommand asInterface(android.os.IBinder obj) {
            if ((obj == null)) {
                return null;
            }
            android.os.IInterface iin = obj.queryLocalInterface(DESCRIPTOR);
            if (((iin != null) && (iin instanceof com.example.aidl.interfaze.ExecuteCommand))) {
                return ((com.example.aidl.interfaze.ExecuteCommand) iin);
            }
            // 返回一个`ExecuteCommand` 接口的远程服务代理对象;
            return new com.example.aidl.interfaze.ExecuteCommand.Stub.Proxy(obj);
        }

        @Override
        public android.os.IBinder asBinder() {
            return this;
        }

        @Override
        public boolean onTransact(int code, android.os.Parcel data, android.os.Parcel reply, int flags) throws android.os.RemoteException {
            switch (code) {
                case INTERFACE_TRANSACTION: {
                    reply.writeString(DESCRIPTOR);
                    return true;
                }
                case TRANSACTION_execute: {
                    data.enforceInterface(DESCRIPTOR);
                    java.lang.String _arg0;
                    _arg0 = data.readString();
                    java.lang.String _result = this.execute(_arg0);
                    reply.writeNoException();
                    // 这里就是向reply中写入数据,将结果返回给调用的客户端;
                    reply.writeString(_result);
                    return true;
                }
            }
            return super.onTransact(code, data, reply, flags);
        }

        // `Proxy` 对象是 `ExecuteCommand` 接口的远程服务代理对象;
        private static class Proxy implements com.example.aidl.interfaze.ExecuteCommand {
            private android.os.IBinder mRemote;

            Proxy(android.os.IBinder remote) {
                mRemote = remote;
            }

            @Override
            public android.os.IBinder asBinder() {
                return mRemote;
            }

            public java.lang.String getInterfaceDescriptor() {
                return DESCRIPTOR;
            }

            @Override
            public java.lang.String execute(java.lang.String param) throws android.os.RemoteException {
                android.os.Parcel _data = android.os.Parcel.obtain();
                android.os.Parcel _reply = android.os.Parcel.obtain();
                java.lang.String _result;
                try {
                    _data.writeInterfaceToken(DESCRIPTOR);
                    _data.writeString(param);
                    // 这个方法时同步的,需要等待远程服务端返回,返回的结果在_reply中读取;
                    mRemote.transact(Stub.TRANSACTION_execute, _data, _reply, 0);
                    _reply.readException();
                    _result = _reply.readString();
                } finally {
                    _reply.recycle();
                    _data.recycle();
                }
                return _result;
            }
        }

        static final int TRANSACTION_execute = (android.os.IBinder.FIRST_CALL_TRANSACTION + 0);
    }

    public java.lang.String execute(java.lang.String param) throws android.os.RemoteException;
}

四、类 Binder、BinderProxy

Binder、BinderProxy 类都是 IBinder 接口的实现类,我们看一下其内部的方法;

4.1 BinderProxy

final class BinderProxy implements IBinder {

    // 在接口远程服务的代理对象的方法中调用transact()
    // 如在ActivityManagerProxy对象的方法中调用transact()
    public boolean transact(int code, Parcel data, Parcel reply, int flags) throws RemoteException {
        Binder.checkParcel(this, code, data, "Unreasonably large binder buffer");
        // 最终直接调用Native层接口;
        return transactNative(code, data, reply, flags);
    }

    // 调用Native层代码
    public native boolean transactNative(int code, Parcel data, Parcel reply,
            int flags) throws RemoteException;

    BinderProxy() {
        mSelf = new WeakReference(this);
    }
}

 4.2 类 Binder

public class Binder implements IBinder {

    /**
     * Add the calling thread to the IPC thread pool.  This function does
     * not return until the current process is exiting.
     */
    public static final native void joinThreadPool();

    /**
     * Default implementation always returns true -- if you got here,
     * the object is alive.
     */
    public boolean pingBinder() {
        return true;
    }

    /**
     * Default implementation is a stub that returns false.  You will want
     * to override this to do the appropriate unmarshalling of transactions.
     *
     * <p>If you want to call this, call transact().
     */
    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) {
            ParcelFileDescriptor fd = data.readFileDescriptor();
            String[] args = data.readStringArray();
            if (fd != null) {
                try {
                    dump(fd.getFileDescriptor(), args);
                } finally {
                    try {
                        fd.close();
                    } catch (IOException e) {
                        // swallowed, not propagated back to the caller
                    }
                }
            }
            // Write the StrictMode header.
            if (reply != null) {
                reply.writeNoException();
            } else {
                StrictMode.clearGatheredViolations();
            }
            return true;
        }
        return false;
    }

    /**
     * Local implementation is a no-op.
     */
    public void linkToDeath(DeathRecipient recipient, int flags) {
    }


    // Entry point from android_util_Binder.cpp's onTransact
    // 在android_util_Binder.cpp的onTransact()方法会调用调这个方法;
    // 即在调用BinderProxy.transact()方法后,经过Native层的调用后,最终调用execTransact()方法;
    private boolean execTransact(int code, long dataObj, long replyObj,
            int flags) {
        Parcel data = Parcel.obtain(dataObj);
        Parcel reply = Parcel.obtain(replyObj);
        boolean res;    
        try {
            // 调用Binder子类的onTransact()方法;
            res = onTransact(code, data, reply, flags);

        } catch (Exception e) {
            reply.setDataPosition(0);
            reply.writeException(e);
            res = true;
        }
        reply.recycle();
        data.recycle();
        return res;
    }
}

五、类似的结构

InterfaceNativeProxyService
IActivityManagerActivityManagerNativeActivityManagerProxyActivityManagerService
IApplicationThreadApplicationThreadNativeApplicationThreadProxyApplicationThread
IServiceManagerServiceManagerNativeServiceManagerProxy/
IPackageManagerIPackageManager.StubIPackageManager.Stub.ProxyPackageManagerService
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值