11、四大组件之二-Service高级(二)Native Service

一、Service的分类

1.1>Android Service

使用Java编写在JVM中运行的服务

1.2>Native Service

使用C/C++完成的服务,一般在系统开始时完成初始化,如MediaService, Audio Service等。

二、Native Service工作流程分析

int main(int argc, char** argv) {

sp<ProcessState> proc(ProcessState::self());

sp<IServiceManager> sm = defaultServiceManager();

LOGI("ServiceManager: %p", sm.get());

AudioFlinger::instantiate();

MediaPlayerService::instantiate();

CameraService::instantiate();

AudioPolicyService::instantiate();

ProcessState::self()->startThreadPool();

IPCThreadState::self()->joinThreadPool();

}

2.1、创建ProcessState和DefaultServiceManager

sp<ProcessState> proc(ProcessState::self());

sp<IServiceManager> sm = defaultServiceManager();

ProcessState放置在全局变量gProcess中,每个进程只有一个ProcessState对象,负责打开Binder设备驱动,建立线程池等。而IPCThreadState每个线程有一个,IPCThreadState实例登记在Linux线程程的上下文附属数据中,主要负责Binder数据读取,写入和请求处理框架。IPCThreadSate在构造的时候,获取进程的ProcessSate并记录在自己的成员变量mProcess中,通过mProcess可以获取到Binder的句柄。

 2.2、将服务放进ServiceManager

AudioFlinger::instantiate();

===>>

defaultServiceManager()->addService(String16("media.audio_flinger"), new AudioFlinger());

 2.3、开始服务循环

ProcessState::self()->startThreadPool();

IPCThreadState::self()->joinThreadPool();

a读取/写入:talkWithDriver()@IPCThreadState对ioctl(mProcess->mDriverFD, BINDER_WRITE_READ, &bwr)进行包装。

b请求处理:executeCommand(...)@ IPCThreadState

c循环结构:joinThreadPool()

joinThreadPool(){

While(1){

talkWithDriver(...)

...

executeCommand(...)

 }

}

2.4、透过 IBinder::transact() 函数来与核心服务互传数据。

 

三、编写自己的Native Service

(1) 编写DemoNativeService 

 1 int DemoService::instantiate() {
 2               LOGE("DemoService instantiate");
 3               int r = defaultServiceManager()->DemoService(
 4                             String16("alfred.demo"), new DemoService());
 5               LOGE("DemoService r = %d\n", r);
 6               return r;
 7        }
 8 
 9 
10 status_t DemoService::onTransact(
11               uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags){
12    switch(code) {
13       case 0: {
14                       pid_t pid = data.readInt32();
15                       int num = data.readInt32();
16                       num = num + 1000;
17                       reply->writeInt32(num);
18                       return NO_ERROR;
19               } break;
20       default:
21               return BBinder::onTransact(code, data, reply, flags);
22    }
23 }      

(2) 编写DemoLoader启动DemoNativeService 

1 int main(int argc, char** argv)
2 {
3 sp<ProcessState> proc(ProcessState::self());
4 sp<IServiceManager> sm = defaultServiceManager();
5 LOGI("ServiceManager: %p", sm.get());
6 DemoService::instantiate();
7 ProcessState::self()->startThreadPool();
8 IPCThreadState::self()->joinThreadPool();
9 }

(3) 编写mk文件

(4) 编写Native代码调用DemoNativeService 

 1 int Demo::setN(int n){
 2    getDemoService();
 3    Parcel data, reply;
 4    data.writeInt32(getpid());
 5    data.writeInt32(n);
 6 
 7    LOGE("BpDemoService::create remote()->transact()\n");
 8    binder->transact(0, data, &reply);
 9    int i = reply.readInt32();
10    return i;
11 }
12 const void Demo::getDemoService(){
13    sp<IServiceManager> sm = defaultServiceManager();
14    binder = sm->getService(String16("guilh.add"));
15    LOGE("Add::getDemoService %p\n",sm.get());
16    if (binder == 0) {
17            LOGW("DemoService not published, waiting...");
18            return;
19    }
20 }

(5) 使用JNI实现Java和NativeService的衔接

(6) 在Activity中调用DemoNativeService

 

posted on 2014-09-15 11:37  大米稀饭  阅读(1814)  评论(0编辑  收藏  举报