Android中IPC的几种方式详细分析与优缺点分
AndrobindServ(UIntent, Uconn, BIND_AUTO_CREATE);id是基于linux内核的。所以linux支持的IPC,android都用到了。比如命名管道,共享内存。 除此外,android还使用了一套自己独特的IPC方式 binder. 主要用于2个进程间的远程调用。但是这里就牵扯远程调用如何传递参数,如何回传结果。 这需要调用者对数据进行打包和解包,是一个繁琐的过程。为此,andro}id引入了aidl(android intece description launguage). 开发人员定义好aidl,android会根据aidl的描述生产stub代码,帮助调用者对数据打包,解包。开发人员所要做的事是继承stub代码,实现stub代码中的函数。这些函数是你在aidl中定义的。
androidaidl原理 android基本原理
androidaidl原理 android基本原理
androidaidl原理 android基本原理
android studio aidl文件怎么建立
72}8.调用远程用startServ,bindServ创建的服务只能在本应用程序内访问,如果要使得本程序的服务能够被其他应用程序访问,这时候就要使用远程过程调用(Remote Procedure Call,RPC)方式来实现,安卓定义了一种接口定义语言Android Intece Definition Language,简称AIDL。今天记录一下如何在Android Studio下创建AIDL Serivce。
aidl android 5.0上怎么使用
Android中使用AIDL需要遵循一套规范,最关键的就是定义AIDL文件,下面以AndroidStudio为例一步步说明AIDL的使用。
由于要测试Android的跨进程通信,所以这里我们需要建立两个项目,一个项目调用另外一个项目的服务。
(1)新建远程服务项目,取名为MyRemoteServ,该项目主要用于开放接口,提供服务给调用者使用。
(2)为MyRemoteServ项目编写AIDL文件。AIDL文件声明了可以被跨进程调用的函数接口,AIDL文件的语法跟声明Ja接口很类似,但又稍有区别,下面是本例子中MyRemoteServ项目的AIDL文件代码:
[html] view plain copy print?
// IServ.aidl
// Declare any non-default types here with import statements
intece IServ {
Demonstrates some basic types that you can use as parameters
and return values in AID35L.
/
void basicTypes(int anInt, long aLong, boolean aBoolean, float aFloat,
double aDouble, String aString);
int add(in25 public class Remote extends ActionBarActivity {t a, int b);
如何用Android Serv通过aidl传递一个数据流
另外,在aidl文件中必须指定好package,否则会编译出错步:部署我们的服务端,也就是Serv端:
代码如下:
这是我Serv端的部署情况(其中MainActivity可以不用去实现,因为我们只提供服务,没有窗口显示):
第二步:部署客户端:
1.在客户端新建一个包,命名需要和服务端放置aidl文件的包名相同(我这里是com.example.remoteserv),然后把服务端的Person.ja,Pet.ja,Person.aidl,Pet.aidl,IPet.aidl到这个包下面
2.在activity中绑定远程服务进行数据交换,layout布局和activity代码如下:
1
15
16
20
21
27
28
29
36
37
41
42
43
44
1 package com.example.remoteclient;
23 import android.app.Serv;
4 import android.content.ComponentName;
583 import android.content.Intent;
6 import android.content.ServConnection;
7 import android.os.Bundle;
8 import android.os.IBinder;
9 import android.os.RemoteException;
10 import android.support.v7.app.ActionBarActivity;
11 import android.util.Log;
12 import android.view.View;
13 import android.view.View.OnClickListener;
14 import android.widget.ArrayAdapter;
15 import android.widget.Button;
16 import android.widget.EditText;
17 import android.widget.ListView;
18
19 import com.example.remoteserv.IPet;
20 import com.example.remoteserv.Person;
21 import com.example.remoteserv.Pet;
22
23 import ja.util.List;
24
26
27 public static final String REMOTE_SERVICE_ACTION = com.example.remoteserv.RemoteServ.ACTION;
28 EditText editText;
30 ListView listView;
31
32 IPet petServ;// 声明IPet接口
33 List
34 ServConnection conn = new ServConnection() {
36 @Override
37 public void onServDisconnected(ComponentName name) {
38 Log.i(csx, onServDisconnected);
40 }
42 @Override
43 public void onServConnected(ComponentName name, IBinder serv) {
44 Log.i(csx, onServConnected);
45 petServ = IPet.Stub.asIntece(serv);// 通过远程服务的Binder实现接口
46
47 }
48 };
49
51 protected void onCreate(Bundle sedInstanceState) {
52 super.onCreate(sedInstanceState);
53 setContentView(R.layout.remote_client_layout);
54 editText = (EditText) findViewById(R.id.editText_person);
55 button = (Button) findViewById(R.id.button_ok);
56 listView = (ListView) findViewById(R.id.listView_pet);
57
58 Intent serv = new Intent();
59 serv.setAction(REMOTE_SERVICE_ACTION);
60
61 bindServ(serv, conn, Serv.BIND_AUTO_CREATE);// 绑定远程服务
62
64
65 @Override
66 public void onClick(View v) {
67 String personName = editText.getText().toString();
69
70 return;
71 }
73 try {
74 pets = petServ.getPets(new Person(1, personName, personName));// 调用远程serv的getPets方法
75 updataListView();
76
77 } catch (RemoteException e) {
78
79 e.printStackTrace();
80 } catch (NullPointerException e) {
81 e.printStackTrace();
82 }
84 }
85 });
86
87 }
89 public void updataListView() {
92 if (pets == null || pets.isEmpty()) {
93 return;
94
95 }
96 ArrayAdapter
97 android.R.layout._list__1, pets);
98 listView.setAdapter(adapter);
99
100 }
101
102 @Override
103 protected void onDestroy() {
104
105 unbindServ(conn);// 解除绑定
107 }
108
109 }
到此为止所有的工作都完成了,下面我们看一下效果:我在编辑框中输入“csx”,点击确定,就会显示出服务端RemoteServ中pets的相应数据。
如何理解android hal中的stub
68 if (personName == null || personName.equals()) {stub是为了方便client,serv交互而生成出来的代码。
AIDL(android 接口描述语言)是一个IDL语言,它可以生成一段代码,可以使在一个android设备上运行的两个进程使用内部通信进程进行交互。如果你需要在一个进程中(例如:在一个Activity中)访问另一个进程中(例如:一个Serv)某个对象的方法,你就可以使用AIDL来生成这样的代码来伪装传递各种参数。
要使用AIDL,Serv需要以aidl文件的方式提供服务接口,AIDL工具将生成一个相应的ja接口,并且在生成的服务接口中包含一个功能调用的stub服务桩类。Serv的实现类需要去继承这个stub服务桩类。Serv的onBind方返回实现类的对象,之后你就可以使用它了。
交互过程client<-->proxy106 super.onDestroy();<-->stub<-->serv
stub和proxy是为了方便client/serv交互而生成出来的代码,这样client/serv的代码就会比较干净,不会嵌入很多很难懂的与业务无关的代码
如何在AndroidStudio中使用AIDL
/1.首先创建一个AndroidStudio工程(这个是远程应用,提供方法让另外的应用调用的),在mian目录下边创建aidl文件夹(和ja文件夹同级),右键app->New->Folder->AIDL Folder
private FDAidlIntece mFDAidlIntece;这里写描述
2.在aidl下创建一个包,包里创建一个.aidl文件,右键aidl->New->AIDL->AIDL file(红框就是创建完成后的样子)
这里写描述
3.在aidl文件写要被调用的方法,此方法不能有权限修饰符
这里写描述
4.首先build下,然后创建一个Serv(注意一定要在onBind方法中返回mIBinder,)
public class FDServ extends Serv{
@Override
return mIBinder;
}private IBinder mIBinder = new FDAidlIntece.Stub() {
@Override
public void callFDSetRoute() throws RemoteException {
Log.e(“wjh”,”收到了远程的请求”);
}@Override
public int add(int a, int b) throws RemoteException {
Log.e("wjh","收到了远程的请求");
return a+b;
}5.清单文件中注册服务
这里写描述
6.创建一个本地应用调用远程应用提供的方法,同样的在main文件夹下创建aidl文件夹,创建包,包名和远程远程应用aidl里的包名相同,然后把远程应用的aidl文件过来
这里写描述
7.开始写本地应用里的代码,改方法放到onCreate中
private ServConnection conn;
private void bindServ() {
Intent intent = new Intent(“com.qujia.ni.aidl”);
conn = new MyConn();
bindServ(intent,conn, Context.BIND_AUTO_CREATE);
}8.然后调用远程的方法
try {
int num = mFDAidlIntece.add(3,4);
} catch (RemoteException e) {
Android Studio开发环境建立aidl文件,怎么生成相应的ja文件
ImyservMar.aidl一,在实现Parcelable接口的类所在的包上右键New -> AIDL
二,AS会自动生成aidl文件夹以及对应的包名。接着声明所需要类。提示intece name must 63 button.setOnClickListener(new OnClickListener() {be unique时,可以随意命名,新建完成后再重命名。
三,点击Build -> Make Project后可生成Ja文件
android studio 使用aidl 问题,求助,在线等
}};2.aidl创建包,包创建.aidl文件,右键aidl->New->AIDL->AIDL file(红框创建完)
90 listView.setAdapter(null);3.aidl文件写要调用,能权限修饰符
4.首先build,创建Serv(注意定要onBind返mIBinder,)
public class FDServ extends Serv{
@Override
return mIBinder;
}private IBinder mIBinder = new FDAidlIntece.Stub() {
@Override
public void callFDSetRoute() throws RemoteException {
Log.e(wjh,收远程请求);
}@Override
public int add(int a, int b) throws RemoteException {
Log.e("wjh","收远程请求");
return a+b;
}5.清单文件注册服务
6.创建本应用调用远程应用提供,同main文件夹创建aidl文件夹,创建包,包名远程远程应用aidl包名相同,远程应用aidl文件
7.始写本应用代码,改放onCreate
private ServConnection conn;
private void bindServ() {
Intent intent = new Intent(com.qujia.ni.aidl);
intent.setPackage(com.example.admin.fdaidl);
conn = new MyConn();
bindServ(intent,conn, Context.BIND_AUTO_CREATE);
try {
int num = mFDAidlIntece.add(3,4);
} catch (RemoteException e) {
Log.e(wjh,调用远程错);
}-
android怎么与pc上的进程进行rpc通信
理解Android系统的进程间通信原理(二)----RPC机制
理解Android系统中的轻量级解决方案RPC的原理,需要先回顾一下JAVA中的RMI(Remote Mod Invocation)这个易于使用的纯JAVA方案(用来实现分布式应用)。有关RMI的相关知识,可以通过下图来归纳:
RMI原理 (2)
Android中的RPC也是参考了JAVA中的RMI方案,这里我们再详细了解一下RPC的实现过程。
Android中的RPC机制是为了实现一个进程使用另一个进程中的远程对象,它使用了Android自己的AIDL(接口定义语言),使用户很方便地定义出一个接口作为规范,通过一个远程Serv为代intent.setPackage(“com.example.admin.fdaidl”);理 ,客户端在绑定该远程Serv过程中获取远程对象,进而使用该对象。可参考下图所示:
Android的RLog.e(“wjh”,”调用远程方法出错”);PC原理及应用 (2)
补充:RPC的另一个目的是对客户端只声明接口及方法,隐藏掉具体实现类,供客户端直接获取此接口实例。
实例代码:
实例一:通过Serv来远程调用一个接口子类的函数方法
功能描述:在MainActivity中通过绑定MyServ服务类,来远程调用MyPlayer(实现了IPlayer接口)的方法过程。需要定义一个IPlayer.aidl文件,ADT工具会自动生成一个IPlayer接口类,然后再由MyPlayer继承IPlayer接口类中的静态内部抽象类,实现接口方法,进而供其它应用程序远程调用。(在本例中为了方便,MainActivity与MyServ类同处一个应用程序中,实现运用时,可以不在同一个应用程序中,只要有权限访问MyServ服务,就能得到IPlayer接口,进而执行该接口实例方法)
程序清单:IPlayer.aidl