Binder机制在AIDL中的实现分析

本篇主要通过结合已经阅读的Binder机制相关资料(《Android开发艺术探索》和 http://weishu.me/2016/01/12/binder-index-for-newer/),通过AIDL来进行Binder机制的初步理解

感谢两位作者:任玉刚和WeiShu

  • 一 一个AIDL Demo的组成部分
  • 二 通信机制的分析
    • 1 bindService 与 onBind
    • 2 代理是如何传递过去的呢
    • 3 数据传递的实现
  • 三 小结

一、 一个AIDL Demo的组成部分

当我们想对一个自定义数据类型(如:Book)来实现跨进程通信时,AIDL的实现核心包括四个部分,分别是:(1).Book.java (2).Book.aidl (3).IBookManager.aidl (4).IBookManager.java

以上4个文件是aidl不可缺少的部分,怎么实现就不说了,到处都有例子说明。这里就简单贴一下各个文件的代码:

/**
 * Created by songjunmin on 2016/11/14.
 * 支持跨进程传输的数据类型
 */

public class Book implements Parcelable {
    public int bookId;
    public String bookName;

    //普通构造函数
    public Book(int bookId, String bookName) {
        this.bookId = bookId;
        this.bookName = bookName;
    }

    //反序列化使用的构造函数
    public Book(Parcel parcel) {
        this.bookId = parcel.readInt();
        this.bookName = parcel.readString();
    }
    //序列化

    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public void writeToParcel(Parcel parcel, int i) {
        parcel.writeInt(bookId);
        parcel.writeString(bookName);
    }

    //反序列化
    public static final Parcelable.Creator<Book> CREATOR = new Parcelable.Creator<Book>() {
        @Override
        public Book[] newArray(int i) {
            return new Book[i];
        }

        @Override
        public Book createFromParcel(Parcel parcel) {
            return new Book(parcel);
        }
    };

    @Override
    public String toString() {
        return "book id = " + bookId + "; book Name = " + bookName + "\n";
    }
}
// Bookd.aidl
package com.example.songjunmin.aidldemo;

// Declare any non-default types here with import statements

parcelable Book;
// IBookManager.aidl
package com.example.songjunmin.aidldemo;

// Declare any non-default types here with import statements
import com.example.songjunmin.aidldemo.Book;
interface IBookManager {
    List<Book> getBookList();
    void addBook(in Book book);
}
/*
 * This file is auto-generated.  DO NOT MODIFY.
 * Original file: /Users/songjunmin/GitHub/AIDLdemo/app/src/main/aidl/com/example/songjunmin/aidldemo/IBookManager.aidl
 */
package com.example.songjunmin.aidldemo;
public interface IBookManager extends android.os.IInterface
{
/** Local-side IPC implementation stub class. */
public static abstract class Stub extends android.os.Binder implements com.example.songjunmin.aidldemo.IBookManager
{
private static final java.lang.String DESCRIPTOR = "com.example.songjunmin.aidldemo.IBookManager";
/** Construct the stub at attach it to the interface. */
public Stub()
{
this.attachInterface(this, DESCRIPTOR);
}
/**
 * Cast an IBinder object into an com.example.songjunmin.aidldemo.IBookManager interface,
 * generating a proxy if needed.
 */
public static com.example.songjunmin.aidldemo.IBookManager asInterface(android.os.IBinder obj)
{
if ((obj==null)) {
return null;
}
android.os.IInterface iin = obj.queryLocalInterface(DESCRIPTOR);
if (((iin!=null)&&(iin instanceof com.example.songjunmin.aidldemo.IBookManager))) {
return ((com.example.songjunmin.aidldemo.IBookManager)iin);
}
return new com.example.songjunmin.aidldemo.IBookManager.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_getBookList:
{
data.enforceInterface(DESCRIPTOR);
java.util.List<com.example.songjunmin.aidldemo.Book> _result = this.getBookList();
reply.writeNoException();
reply.writeTypedList(_result);
return true;
}
case TRANSACTION_addBook:
{
data.enforceInterface(DESCRIPTOR);
com.example.songjunmin.aidldemo.Book _arg0;
if ((0!=data.readInt())) {
_arg0 = com.example.songjunmin.aidldemo.Book.CREATOR.createFromParcel(data);
}
else {
_arg0 = null;
}
this.addBook(_arg0);
reply.writeNoException();
return true;
}
}
return super.onTransact(code, data, reply, flags);
}
private static class Proxy implements com.example.songjunmin.aidldemo.IBookManager
{
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.util.List<com.example.songjunmin.aidldemo.Book> getBookList() throws android.os.RemoteException
{
android.os.Parcel _data = android.os.Parcel.obtain();
android.os.Parcel _reply = android.os.Parcel.obtain();
java.util.List<com.example.songjunmin.aidldemo.Book> _result;
try {
_data.writeInterfaceToken(DESCRIPTOR);
mRemote.transact(Stub.TRANSACTION_getBookList, _data, _reply, 0);
_reply.readException();
_result = _reply.createTypedArrayList(com.example.songjunmin.aidldemo.Book.CREATOR);
}
finally {
_reply.recycle();
_data.recycle();
}
return _result;
}
@Override public void addBook(com.example.songjunmin.aidldemo.Book book) throws android.os.RemoteException
{
android.os.Parcel _data = android.os.Parcel.obtain();
android.os.Parcel _reply = android.os.Parcel.obtain();
try {
_data.writeInterfaceToken(DESCRIPTOR);
if ((book!=null)) {
_data.writeInt(1);
book.writeToParcel(_data, 0);
}
else {
_data.writeInt(0);
}
mRemote.transact(Stub.TRANSACTION_addBook, _data, _reply, 0);
_reply.readException();
}
finally {
_reply.recycle();
_data.recycle();
}
}
}
static final int TRANSACTION_getBookList = (android.os.IBinder.FIRST_CALL_TRANSACTION + 0);
static final int TRANSACTION_addBook = (android.os.IBinder.FIRST_CALL_TRANSACTION + 1);
}
public java.util.List<com.example.songjunmin.aidldemo.Book> getBookList() throws android.os.RemoteException;
public void addBook(com.example.songjunmin.aidldemo.Book book) throws android.os.RemoteException;
}

在上面的四个文件中,有两个java文件和两个aidl文件,Book.java是我们支持序列化跨进程传递的数据类,IBookManager.java是aidl工具为我们生成的最终跨进程接口,服务端和客户端通过这个接口来实现跨进程通信。

有了aidl文件之后,使用姿势如下:

/**
 * Created by songjunmin on 2016/11/14.
 * 建立服务端的Service,当来自别的进程需要进行IPC请求时,需要绑定到该Service获取Binder代理
 */

public class AIDLService extends Service {
    private static final String TAG = "AIDLService";

    //使用CopyOnWriteArrayList来支持线程同步,因为会有多个客户端访问服务端的场景
    private CopyOnWriteArrayList<Book> mBookList = new CopyOnWriteArrayList<>();

    private Binder mBinder = new IBookManager.Stub(){
        //Stub是继承了Binder并且实现IBookManager接口的
        //所以当进行实现方法的时候,会发现即有IBookManager里的接口方法,也有Binder里的覆写方法
        //我们需要实现接口方法
        @Override
        public List<Book> getBookList() throws RemoteException {
            return mBookList;
        }

        @Override
        public void addBook(Book book) throws RemoteException {
            mBookList.add(book);
        }
    };
    @Nullable
    @Override
    public IBinder onBind(Intent intent) {
        return mBinder;
    }

    @Override
    public void onCreate() {
        super.onCreate();
        mBookList.add(new Book(1,"Android"));
        mBookList.add(new Book(2,"iOS"));
    }
}
public class MainActivity extends AppCompatActivity {
    private static final String TAG = "MainActivity";

    private ServiceConnection conn = new ServiceConnection() {
        @Override
        public void onServiceConnected(ComponentName name, IBinder binder) {
            IBookManager bookManager = IBookManager.Stub.asInterface(binder);
            try {
                //客户端添加一本书
                bookManager.addBook(new Book(3,"Python"));
                List<Book> list = bookManager.getBookList();
                for(int i = 0; i < list.size(); i++){
                    Book book = list.get(i);
                    Log.d(TAG, book.toString());
                }
            } catch (RemoteException e) {
                e.printStackTrace();
            }
            Log.d(TAG,"绑定成功");
        }

        @Override
        public void onServiceDisconnected(ComponentName name) {
            Log.d(TAG, "解除绑定");
        }
    };
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        Intent intent = new Intent(MainActivity.this, AIDLService.class);
        bindService(intent,conn, Context.BIND_AUTO_CREATE);
    }

    @Override
    protected void onDestroy() {
        unbindService(conn);
        super.onDestroy();
    }
}
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
          package="com.example.songjunmin.aidldemo">

    <application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:supportsRtl="true"
        android:theme="@style/AppTheme">
        <activity android:name=".MainActivity">
            <intent-filter>
                <action android:name="android.intent.action.MAIN"/>

                <category android:name="android.intent.category.LAUNCHER"/>
            </intent-filter>
        </activity>

        <service android:name=".AIDLService"
            android:process=":remote"/>
    </application>

</manifest>

在Manifest文件中,我们定义同一个app下有一个来自其他进程的服务,名为AIDLService,客户端通过bindService来绑定远程服务。

下面来进行跨进程通信的一步步分析。

二、 通信机制的分析

2.1 bindService 与 onBind

在客户端,通过bindService来绑定服务,在bindService方法中需要建立一个ServiceConnection对象。 在服务端的回调方法onBind拿到一个IBinder对象,最后递交给客户端实现的ServiceConnection对象,在该对象的onServiceConnected(ComponentName name, IBinder binder)方法中完成对象的代理获取。

对这个过程进行拆分:

在AIDLService的onBind方法是这样的:

@Nullable
@Override
public IBinder onBind(Intent intent) {
    return mBinder;
}

在onBind方法中返回了IBinder类型的mBinder对象,那么mBinder对象是怎么来的呢?在服务端创建了mBinder对象

private Binder mBinder = new IBookManager.Stub(){
    //Stub是继承了Binder并且实现IBookManager接口的
    //所以当进行实现方法的时候,会发现即有IBookManager里的接口方法,也有Binder里的覆写方法
    //我们需要实现接口方法
    @Override
    public List<Book> getBookList() throws RemoteException {
        return mBookList;
    }

    @Override
    public void addBook(Book book) throws RemoteException {
        mBookList.add(book);
    }
};

可以看到,在服务端,通过AIDL接口的内部类Stub,创建了Binder对象mBinder。

在aidl文件中可以知道内部类Stub是继承自Binder类的,而Binder又实现了IBinder接口,所以可以在onBind方法中返回。

具体看一下资料中对Binder和IBinder关系的说明:

    从该说明中可以知道,凡是实现了IBinder接口的,就会受到底层驱动的支持(我可以理解为受到上帝的眷顾吗),从而可以跨进程传递这个数据。而Binder虽然实现了IBinder接口,但是其定义更加适合为本地的对象。

在该例子中,创建的mBinder是属于服务端自己的本地Binder对象,该对象可以通过跨进程传输协议(IBinder)来进行传递。

但是,但是,但是…(开始到第一个重要注意点了)

本地Binder通过跨进程协议(IBinder),传递到其他进程的并不是真身而是一个代理。

2.2 代理是如何传递过去的呢?

首先看客户端是如何实现ServiceConnection这个对象的:

public void onServiceConnected(ComponentName name, IBinder binder) {
    IBookManager bookManager = IBookManager.Stub.asInterface(binder);
}

这个代码的理解就是:1.mBinder由于实现了IBinder接口,所以具体所谓的跨进程传递自己的能力;2.实际上,传递的是mBinder代理,而并不是mBinder真身

在IBookManager.Stub.asInterface方法中,完成了真身和代理的转变。看看asInterface的实现:

/**
 * Cast an IBinder object into an com.example.songjunmin.aidldemo.IBookManager interface,
 * generating a proxy if needed.
 */
public static com.example.songjunmin.aidldemo.IBookManager asInterface(android.os.IBinder obj) {
    if ((obj == null)) {
        return null;
    }
    android.os.IInterface iin = obj.queryLocalInterface(DESCRIPTOR);
    if (((iin != null) && (iin instanceof com.example.songjunmin.aidldemo.IBookManager))) {
        return ((com.example.songjunmin.aidldemo.IBookManager) iin);
    }
    return new com.example.songjunmin.aidldemo.IBookManager.Stub.Proxy(obj);

}

从这段代码中可以看出,asInterface方法接收了一个IBinder的接口对象,这个对象怎么来的呢?实际上是底层的Binder驱动提供的,在onBind方法中返回的mBinder实际上首先扔给了驱动,binder驱动进行了对mBinder包装改变(因为binder驱动也在一个进程中,onBind返回的过程由于首先给binder驱动,所以也属于进程间对象的传递,所以binder驱动肯定会对mBinder进行包装和改变),binder驱动完成了改变之后,又交给了客户端的进程,所以客户端进程中的onServiceConnected才可以拿到一个IBinder的对象,并执行后续的asInterface方法。以上就解释了asInterface方法的参数IBinder obj的由来,它并不是直接的mBinder(服务端的onBind方法所返回的)。

了解完参数之后,先不进入asInterface方法内部,再来看一下asInterface方法的返回值:是com.example.songjunmin.aidldemo.IBookManager

这个返回值类型就是我们的 AIDL接口,我们的所谓AIDL跨进程通信,实际上基于的是AIDL接口,在本例中,就是AIDL的IBookManager接口,所以我们需要返回AIDL接口 。

明确了返回值和方法参数之后,可以进入到asInterface方法内部了:

首先需要知道的是,这个方法是在客户端进程中调用的,所以首先执行本地AIDL接口查询,使用obj.queryLocalInterface(DESCRIPTOR)

由于在客户端进程,所以拿到binder驱动返回的IBinder对象obj之后执行本地查询,查询什么呢?查询DESCRIPTOR,即 :

private static final java.lang.String DESCRIPTOR = "com.example.songjunmin.aidldemo.IBookManager";

这里注意一点:一般如果客户端进程是来自别的应用A,而服务端进程也在一个应用B中,此时的跨进程同时是属于不同应用间的,所以在客户端使用上述方法的话,肯定也需要有与服务端同样的aidl文件.

正如《Android开发艺术探索》的P73页所说。不然客户端都没有DESCRIPTOR这个变量,怎么查询呢对吧.

查询完成之后判断本进程是否有该AIDL接口,若有,则执行:

if (((iin != null) && (iin instanceof com.example.songjunmin.aidldemo.IBookManager)))

若无,则通过内部类Stub的内部类Proxy来创建一个代理对象:

private static class Proxy implements com.example.songjunmin.aidldemo.IBookManager {
    private android.os.IBinder mRemote;

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

    //...省略

}

代理对象内部有一个mRemote的IBinder对象,所以这个对象也是可以跨进程的(其实本质上都是客户端的Binder对象mBinder)。

在这个代理方法中,将binder驱动传递给客户端进程的IBinder赋值给了Proxy代理类的私有变量mRemote,而Proxy是Stub的内部类,这里千万不要被两个类在同一个文件中给弄迷糊了,这两个类在实际执行的时候是分属不同的进程空间中的。

Proxy这个内部类实现了AIDL接口,所以其对象也是可以供客户端进程使用的AIDL接口对象。

这样的话,就通过服务端的mBinder(源自AIDL接口的内部类Stub)、客户端的asInterface得到AIDL接口对象(基于代理)实现了跨进程AIDL接口的使用,进行数据交互。

2.3 数据传递的实现。

客户端拿到的是服务端的代理对象,无法直接操作服务端的对象(为了安全起见),那么拿到代理对象也可以给客户端提供一种真实操作服务端对象的假象(比如,代理对象也向客户端提供了一个与真实服务端对象中相同的同名方法),但是这仅仅只是假象,名称相同,方法内部的执行逻辑在代理对象和真实服务端对象中是不一样的。

代理对象从客户端那拿到客户端请求的数据之后,进行包装,然后递交给底层的Binder驱动,驱动解析之后扔给真正的服务端对象,服务端再通过同名方法进行真实的逻辑处理。

@Override
public java.util.List<com.example.songjunmin.aidldemo.Book> getBookList() throws android.os.RemoteException {
    android.os.Parcel _data = android.os.Parcel.obtain();
    android.os.Parcel _reply = android.os.Parcel.obtain();
    java.util.List<com.example.songjunmin.aidldemo.Book> _result;
    try {
        _data.writeInterfaceToken(DESCRIPTOR);
        mRemote.transact(Stub.TRANSACTION_getBookList, _data, _reply, 0);
        _reply.readException();
        _result = _reply.createTypedArrayList(com.example.songjunmin.aidldemo.Book.CREATOR);
    } finally {
        _reply.recycle();
        _data.recycle();
    }
    return _result;
}
在这个代码块中,可以看到,代理对象压根没做什么真实在getBookList逻辑,其核心只是创建了一个包装客户端数据的_data,建立了一个可以返回给客户端的_reply,以及该方法的返回值数据_result。之后就通过mRemote.transact方法,指定了客户端调用的方法名称ID,以及两个数据包装对象,就一并扔给了Binder驱动了.........。此时,客户端线程会处于挂起状态,傻傻的等待服务端返回。

Binder驱动在收到代理递交过来的数据之后,经过敏锐的分析,发现原来这个是代理传递过来的,辣么代理的本意应该就是要告诉真正的服务端对象,告诉啥呢?要服务端对象执行getBookList方法,此时,bind驱动会找到真实的服务端对象(因为所有的跨进程服务端对象都会注册到Binder驱动中),并执行IBinder的ontransact方法,从而回调了真实服务端的ontransact方法:
@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_getBookList: {
            data.enforceInterface(DESCRIPTOR);
            java.util.List<com.example.songjunmin.aidldemo.Book> _result = this.getBookList();
            reply.writeNoException();
            reply.writeTypedList(_result);
            return true;
        }
//省略
}

在该方法中,定位到getBookList方法的逻辑,发现调用了我们实际定义的接口方法getBookList,而该接口的具体实现就在服务端上层来实现的,需要开发人员自己定义:

private Binder mBinder = new IBookManager.Stub(){
    //Stub是继承了Binder并且实现IBookManager接口的
    //所以当进行实现方法的时候,会发现即有IBookManager里的接口方法,也有Binder里的覆写方法
    //我们需要实现接口方法
    @Override
    public List<Book> getBookList() throws RemoteException {
        return mBookList;
    }

    @Override
    public void addBook(Book book) throws RemoteException {
        mBookList.add(book);
    }
};

三、 小结

这样子,就完成了服务端各个部分的意义了,客户端的各个部分的意义也明确了。

AIDL为我们生成的aidl接口名称和我们自定义的接口名称重名,很容易混淆我们的理解,这一点要明确。IBookManager.java是真正的AIDL接口,是用于跨进程实现的,内部的Stub实现了我们的IBookManager.aidl里声明的接口,这个是用于服务端上层自己实现的,AIDL中只是拿了个方法的壳而已。

所以,Binder机制的核心是“粘合剂”,当然AIDL只是粘合剂Binder所应用的一个场景,什么场景呢?跨进程通信,这里的通信实际上是调用两个进程都可以使用的接口方法,但是互相使用方法总要传递数据吧,又有代理的加入,所以才有了粘合剂Binder的必要。

时间: 2024-10-29 19:07:34

Binder机制在AIDL中的实现分析的相关文章

基础篇-Binder机制和AIDL使用介绍

简介: 我们知道,Android系统是基于Linux内核的,而Linux内核继承和兼容了丰富的Unix系统进程间通信(IPC)机制.例如管道(Pipe),报文队列(Message).共享内存(Share Memory)和信号量(Semaphore)等等.但是Android系统没有采用上述提到的各种进程间通信机制,而是采用Binder机制.在Android系统的Binder机制中,由一系列系统组件组成,分别是Client.Server.Service Manager和Binder驱动程序,其中Cl

谈谈Android Binder机制及AIDL使用

Binder原理 1.概述 Android系统中,涉及到多进程间的通信底层都是依赖于Binder IPC机制.例如当进 程A中的Activity要向进程B中的Service通信,这便需要依赖于Binder IPC.不仅于 此,整个Android系统架构中,大量采用了Binder机制作为IPC(进程间通信, Interprocess Communication)方案. 当然也存在部分其他的IPC方式,如管道.SystemV.Socket等.那么Android为什 么不使用这些原有的技术,而是要使开

Binder机制1---Binder原理介绍

1.Binder通信机制介绍 这篇文章会先对照Binder机制与Linux的通信机制的区别,了解为什么Android会另起炉灶,採用Binder.接着,会依据Binder的机制,去理解什么是Service Manager,在C/S模型中扮演什么角色.最后,会从一次完整的通信活动中,去理解Binder通信的过程. 1.1 Android与Linux通信机制的比較 尽管Android继承使用Linux的内核,但Linux与Android的通信机制不同. 在Linux中使用的IPC通信机制例如以下:

[Android] 彻底了解Binder机制原理和底层实现

1.Binder通信机制介绍 这篇文章会先对比Binder机制与Linux的通信机制的差别,了解为什么Android会另起炉灶,采用Binder.接着,会根据 Binder的机制,去理解什么是Service  Manager,在C/S模型中扮演什么角色.最后,会从一次完整的通信活动中,去理解Binder通信的过程. 1.1 Android与Linux通信机制的比较 虽然Android继承使用Linux的内核,但Linux与Android的通信机制不同. 在Linux中使用的IPC通信机制如下:

Binder AIDL中自定义类型传递的源码分析

binder机制实现的IPC和共享内存的方式不同,它采取的是值拷贝的方式,即进程间传递的实体遵循Parcelable协议, Bp端负责向Parcel里写东西,Bn端负责从Parcel里读取还原,顺序是双方约定的.原型如下,Bp/Bn端收到的其实 都只是彼此的clone. Aidl(Android Interface Definition Language)简化了binder的使用,做了大量封装 但Aidl默认支持的类型包括Java 原始类型(如int.long.boolean等) 和 基础封装类

从源码角度分析Android中的Binder机制的前因后果

前面我也讲述过一篇文章<带你从零学习linux下的socket编程>,主要是从进程通信的角度开篇然后延伸到linux中的socket的开发.本篇文章依然是从进程通信的角度去分析下Android中的进程通信机制. 为什么在Android中使用binder通信机制? 众所周知linux中的进程通信有很多种方式,比如说管道.消息队列.socket机制等.socket我们再熟悉不过了,然而其作为一款通用的接口,通信开销大,数据传输效率低,主要用在跨网络间的进程间通信以及在本地的低速通信.消息队列和管道

Android中的Binder机制的简要理解

转载自:http://www.linuxidc.com/Linux/2012-07/66195.htm http://blog.csdn.net/sunxingzhesunjinbiao/article/details/42195013 我们知道,在Android系统中,每一个应用程序都运行在独立的进程中,这也保证了当其中一个程序出现异常而不会影响另一个应用程序的正常运转.在许多情况下,我们activity都会与各种系统的service打交道,很显然,我们写的程序中activity与系统serv

Android系统篇之----Binder机制和远程服务调用机制分析

一.前景概要 最近要实现Android中免注册Activity就可以运行的问题,那么结果是搞定了,就是可以不用在AndroidManifest.xml中声明这个Activity即可运行,主要是通过骗取系统,偷龙转凤技术的,这个知识点后面会详细讲解的,因为在研究了这个问题过程中遇到了很多知识点,当然最重要也是最根本的就是Android中的Binder机制和远程服务调用机制,而关于Binder机制的话,在Android中算是一个非常大的系统架构模块了,光这篇文章是肯定不能讲解到全部的,而且本人也不是

Android系统进程间通信Binder机制在应用程序框架层的Java接口源代码分析

文章转载至CSDN社区罗升阳的安卓之旅,原文地址:http://blog.csdn.net/luoshengyang/article/details/6642463 在前面几篇文章中,我们详细介绍了Android系统进程间通信机制Binder的原理,并且深入分析了系统提供的Binder运行库和驱动程序的 源代码.细心的读者会发现,这几篇文章分析的Binder接口都是基于C/C++语言来实现的,但是我们在编写应用程序都是基于Java语言的,那么,我 们如何使用Java语言来使用系统的Binder机