转载处:http://blog.csdn.net/xieqibao/article/details/6585143

    ServiceMananger是android中比较重要的一个进程,它是在init进程启动之后启动,从名字上就可以看出来它是用来管理系统中的service。比如:InputMethodService、ActivityManagerService等。在ServiceManager中有两个比较重要的方法:add_service、check_service。系统的service需要通过add_service把自己的信息注册到ServiceManager中,当需要使用时,通过check_service检查该service是否存在。

    主函数

    从它的主函数代码开始:

    [java] view plain copy
    1. intmain(intargc,char**argv)
    2. {
    3. structbinder_state*bs;
    4. void*svcmgr=BINDER_SERVICE_MANAGER;
    5. bs=binder_open(128*1024);
    6. if(binder_become_context_manager(bs)){
    7. LOGE("cannotbecomecontextmanager(%s)\n",strerror(errno));
    8. return-1;
    9. }
    10. svcmgr_handle=svcmgr;
    11. binder_loop(bs,svcmgr_handler);
    12. return0;
    13. }

    从main函数中可以看出,它主要做了三件事情:

  1. 打开/dev/binder设备,并在内存中映射128K的空间。
  2. 通知Binder设备,把自己变成context_manager
  3. 进入循环,不停的去读Binder设备,看是否有对service的请求,如果有的话,就去调用svcmgr_handler函数回调处理请求。

    服务注册

    再来看看ServiceManager中是怎么样去注册服务的。先来看先,当有对service的请求时,调用的回调函数svcmgr_handler:

    [java] view plain copy
    1. intsvcmgr_handler(structbinder_state*bs,
    2. structbinder_txn*txn,
    3. structbinder_io*msg,
    4. structbinder_io*reply)
    5. {
    6. structsvcinfo*si;
    7. uint16_t*s;
    8. unsignedlen;
    9. void*ptr;
    10. uint32_tstrict_policy;
    11. //LOGI("target=%pcode=%dpid=%duid=%d\n",
    12. //txn->target,txn->code,txn->sender_pid,txn->sender_euid);
    13. if(txn->target!=svcmgr_handle)
    14. return-1;
    15. //EquivalenttoParcel::enforceInterface(),readingtheRPC
    16. //headerwiththestrictmodepolicymaskandtheinterfacename.
    17. //Notethatweignorethestrict_policyanddon'tpropagateit
    18. //further(sincewedonooutboundRPCsanyway).
    19. strict_policy=bio_get_uint32(msg);
    20. s=bio_get_string16(msg,&len);
    21. if((len!=(sizeof(svcmgr_id)/2))||
    22. memcmp(svcmgr_id,s,sizeof(svcmgr_id))){
    23. fprintf(stderr,"invalidid%s\n",str8(s));
    24. return-1;
    25. }
    26. switch(txn->code){
    27. caseSVC_MGR_GET_SERVICE:
    28. caseSVC_MGR_CHECK_SERVICE:
    29. s=bio_get_string16(msg,&len);
    30. ptr=do_find_service(bs,s,len);
    31. if(!ptr)
    32. break;
    33. bio_put_ref(reply,ptr);
    34. return0;
    35. caseSVC_MGR_ADD_SERVICE:
    36. s=bio_get_string16(msg,&len);
    37. ptr=bio_get_ref(msg);
    38. if(do_add_service(bs,s,len,ptr,txn->sender_euid))
    39. return-1;
    40. break
    41. caseSVC_MGR_LIST_SERVICES:{
    42. unsignedn=bio_get_uint32(msg);
    43. si=svclist;
    44. while((n-->0)&&si)
    45. si=si->next;
    46. if(si){
    47. bio_put_string16(reply,si->name);
    48. return0;
    49. }
    50. return-1;
    51. }
    52. default:
    53. LOGE("unknowncode%d\n",txn->code);
    54. return-1;
    55. }
    56. bio_put_uint32(reply,0);
    57. return0;
    58. }

    在该回调函数中会判断Service有什么需要,如果是请求注册service,那么久执行:

    [java] view plain copy
    1. caseSVC_MGR_ADD_SERVICE:
    2. s=bio_get_string16(msg,&len);
    3. ptr=bio_get_ref(msg);
    4. if(do_add_service(bs,s,len,ptr,txn->sender_euid))
    5. return-1;
    6. break;

    我们再来看看do_add_service中做了什么事情:

    [java] view plain copy
    1. intdo_add_service(structbinder_state*bs,
    2. uint16_t*s,unsignedlen,
    3. void*ptr,unsigneduid)
    4. {
    5. structsvcinfo*si;
    6. //LOGI("add_service('%s',%p)uid=%d\n",str8(s),ptr,uid);
    7. if(!ptr||(len==0)||(len>127))
    8. return-1
    9. if(!svc_can_register(uid,s)){
    10. LOGE("add_service('%s',%p)uid=%d-PERMISSIONDENIED\n",
    11. str8(s),ptr,uid);
    12. return-1;
    13. }
    14. si=find_svc(s,len);
    15. if(si){
    16. if(si->ptr){
    17. LOGE("add_service('%s',%p)uid=%d-ALREADYREGISTERED\n",
    18. str8(s),ptr,uid);
    19. return-1;
    20. }
    21. si->ptr=ptr;
    22. }else{
    23. si=malloc(sizeof(*si)+(len+1)*sizeof(uint16_t));
    24. if(!si){
    25. LOGE("add_service('%s',%p)uid=%d-OUTOFMEMORY\n",
    26. str8(s),ptr,uid);
    27. return-1;
    28. }
    29. si->ptr=ptr;
    30. si->len=len;
    31. memcpy(si->name,s,(len+1)*sizeof(uint16_t));
    32. si->name[len]='\0';
    33. si->death.func=svcinfo_death;
    34. si->death.ptr=si;
    35. si->next=svclist;
    36. svclist=si;
    37. }
    38. binder_acquire(bs,ptr);
    39. binder_link_to_death(bs,ptr,&si->death);
    40. return0;
    41. }

    在该函数中,首先会去检查是否有权限注册service,如果没有权限就直接返回,不能注册。

    [java] view plain copy
    1. if(!svc_can_register(uid,s)){
    2. LOGE("add_service('%s',%p)uid=%d-PERMISSIONDENIED\n",
    3. str8(s),ptr,uid);
    4. return-1;
    5. }

    然后会去检查该service是否已经注册过了,如果已经注册过,那么就不能再注册了:

    [java] view plain copy
    1. si=find_svc(s,len);
    2. if(si){
    3. if(si->ptr){
    4. LOGE("add_service('%s',%p)uid=%d-ALREADYREGISTERED\n",
    5. str8(s),ptr,uid);
    6. return-1;
    7. }
    8. si->ptr=ptr;
    9. }

    再判断内存是否足够:

    [java] view plain copy
    1. si=malloc(sizeof(*si)+(len+1)*sizeof(uint16_t));
    2. if(!si){
    3. LOGE("add_service('%s',%p)uid=%d-OUTOFMEMORY\n",
    4. str8(s),ptr,uid);
    5. return-1;
    6. }

    如果都没什么问题,会注册该service,加入到svcList中来。注意,在ServiceManager中维护service信息的地方就是svclist。里面存了service的name和handler。

    服务获取

    通过以上几个步骤,service就算注册成功了。那么当要获得该service的时候又是怎么去处理的。还是来看下回调函数中的判断:

    [java] view plain copy
    1. caseSVC_MGR_CHECK_SERVICE:
    2. s=bio_get_string16(msg,&len);
    3. ptr=do_find_service(bs,s,len);
    4. if(!ptr)
    5. break;
    6. bio_put_ref(reply,ptr);
    7. return0

    如果是获取service,那么执行SVC_MGR_CHECK_SERVICE,并把返回的数据写入reply,返回给客户端。

    do_find_service函数中主要执行service的查找。

    [java] view plain copy
    1. void*do_find_service(structbinder_state*bs,uint16_t*s,unsignedlen)
    2. {
    3. structsvcinfo*si;
    4. si=find_svc(s,len);
    5. //LOGI("check_service('%s')ptr=%p\n",str8(s),si?si->ptr:0);
    6. if(si&&si->ptr){
    7. returnsi->ptr;
    8. }else{
    9. return0;
    10. }
    11. }

    这样在ServiceManager中就完成了服务的注册和查找。来看下ServiceManager的功能图:



6

更多相关文章

  1. 一款霸榜 GitHub 的开源 Linux 资源监视器!
  2. log函数封装,让WIN32和android ndk共用相同的log函数,方便调试
  3. android进程(关闭自己和关闭其他进程)
  4. Android(安卓)Intent 三解决
  5. Android(安卓)SensorService源码分析(二)
  6. Android(安卓)JNI回调
  7. android 退出activity
  8. android ps 命令执行后各项值的含义
  9. Android(安卓)Eclipse 源码工程 调试

随机推荐

  1. Android下的任务和Activity栈
  2. android 判断当前application 是在前台还
  3. android > ListView -- SimpleAdapter
  4. Android Studio 3.0找不到Android Device
  5. android 5.1 usb调试默认关闭设置方法
  6. [zz] Android Service 示例
  7. Mainfest
  8. Android(安卓)分享功能的实现
  9. android 五种Log的意思
  10. Android电话拨号器