Android Framework P4 - ServiceManager 进程

发布时间:2026/5/25 21:10:26

Android Framework P4 - ServiceManager 进程 ServiceManager 进程// /system/core/rootdir/init.rc service servicemanager /system/bin/servicemanager class core user system group system critical onrestart restart healthd onrestart restart zygote onrestart restart media onrestart restart surfaceflinger onrestart restart drm// /frameworks/native/cmds/servicemanager/service_manager.cintmain(intargc,char**argv){structbinder_state*bs;bsbinder_open(128*1024);if(!bs){ALOGE(failed to open binder driver\n);return-1;}if(binder_become_context_manager(bs)){ALOGE(cannot become context manager (%s)\n,strerror(errno));return-1;}selinux_enabledis_selinux_enabled();sehandleselinux_android_service_context_handle();selinux_status_open(true);if(selinux_enabled0){if(sehandleNULL){ALOGE(SELinux: Failed to acquire sehandle. Aborting.\n);abort();}if(getcon(service_manager_context)!0){ALOGE(SELinux: Failed to acquire service_manager context. Aborting.\n);abort();}}unionselinux_callback cb;cb.func_auditaudit_callback;selinux_set_callback(SELINUX_CB_AUDIT,cb);cb.func_logselinux_log_callback;selinux_set_callback(SELINUX_CB_LOG,cb);binder_loop(bs,svcmgr_handler);return0;}// /frameworks/native/cmds/servicemanager/binder.cstructbinder_state*binder_open(size_tmapsize){structbinder_state*bs;structbinder_versionvers;bsmalloc(sizeof(*bs));if(!bs){errnoENOMEM;returnNULL;}bs-fdopen(/dev/binder,O_RDWR);if(bs-fd0){fprintf(stderr,binder: cannot open device (%s)\n,strerror(errno));gotofail_open;}if((ioctl(bs-fd,BINDER_VERSION,vers)-1)||(vers.protocol_version!BINDER_CURRENT_PROTOCOL_VERSION)){fprintf(stderr,binder: kernel driver version (%d) differs from user space version (%d)\n,vers.protocol_version,BINDER_CURRENT_PROTOCOL_VERSION);gotofail_open;}bs-mapsizemapsize;bs-mappedmmap(NULL,mapsize,PROT_READ,MAP_PRIVATE,bs-fd,0);if(bs-mappedMAP_FAILED){fprintf(stderr,binder: cannot map device (%s)\n,strerror(errno));gotofail_map;}returnbs;fail_map:close(bs-fd);fail_open:free(bs);returnNULL;}// /frameworks/native/cmds/servicemanager/binder.cintbinder_become_context_manager(structbinder_state*bs){returnioctl(bs-fd,BINDER_SET_CONTEXT_MGR,0);}// /frameworks/native/cmds/servicemanager/binder.cvoidbinder_loop(structbinder_state*bs,binder_handler func){intres;structbinder_write_readbwr;uint32_treadbuf[32];bwr.write_size0;bwr.write_consumed0;bwr.write_buffer0;readbuf[0]BC_ENTER_LOOPER;binder_write(bs,readbuf,sizeof(uint32_t));for(;;){bwr.read_sizesizeof(readbuf);bwr.read_consumed0;bwr.read_buffer(uintptr_t)readbuf;resioctl(bs-fd,BINDER_WRITE_READ,bwr);if(res0){ALOGE(binder_loop: ioctl failed (%s)\n,strerror(errno));break;}resbinder_parse(bs,0,(uintptr_t)readbuf,bwr.read_consumed,func);if(res0){ALOGE(binder_loop: unexpected reply?!\n);break;}if(res0){ALOGE(binder_loop: io error %d %s\n,res,strerror(errno));break;}}}// /frameworks/native/cmds/servicemanager/binder.cintbinder_parse(structbinder_state*bs,structbinder_io*bio,uintptr_tptr,size_tsize,binder_handler func){intr1;uintptr_tendptr(uintptr_t)size;while(ptrend){uint32_tcmd*(uint32_t*)ptr;ptrsizeof(uint32_t);#ifTRACEfprintf(stderr,%s:\n,cmd_name(cmd));#endifswitch(cmd){caseBR_NOOP:break;caseBR_TRANSACTION_COMPLETE:break;caseBR_INCREFS:caseBR_ACQUIRE:caseBR_RELEASE:caseBR_DECREFS:#ifTRACEfprintf(stderr, %p, %p\n,(void*)ptr,(void*)(ptrsizeof(void*)));#endifptrsizeof(structbinder_ptr_cookie);break;caseBR_TRANSACTION:{structbinder_transaction_data*txn(structbinder_transaction_data*)ptr;if((end-ptr)sizeof(*txn)){ALOGE(parse: txn too small!\n);return-1;}binder_dump_txn(txn);if(func){unsignedrdata[256/4];structbinder_iomsg;structbinder_ioreply;intres;bio_init(reply,rdata,sizeof(rdata),4);bio_init_from_txn(msg,txn);resfunc(bs,txn,msg,reply);binder_send_reply(bs,reply,txn-data.ptr.buffer,res);}ptrsizeof(*txn);break;}caseBR_REPLY:{structbinder_transaction_data*txn(structbinder_transaction_data*)ptr;if((end-ptr)sizeof(*txn)){ALOGE(parse: reply too small!\n);return-1;}binder_dump_txn(txn);if(bio){bio_init_from_txn(bio,txn);bio0;}else{/* todo FREE BUFFER */}ptrsizeof(*txn);r0;break;}caseBR_DEAD_BINDER:{structbinder_death*death(structbinder_death*)(uintptr_t)*(binder_uintptr_t*)ptr;ptrsizeof(binder_uintptr_t);death-func(bs,death-ptr);break;}caseBR_FAILED_REPLY:r-1;break;caseBR_DEAD_REPLY:r-1;break;default:ALOGE(parse: OOPS %d\n,cmd);return-1;}}returnr;}// /frameworks/native/cmds/servicemanager/service_manager.cintsvcmgr_handler(structbinder_state*bs,structbinder_transaction_data*txn,structbinder_io*msg,structbinder_io*reply){structsvcinfo*si;uint16_t*s;size_tlen;uint32_thandle;uint32_tstrict_policy;intallow_isolated;//ALOGI(target%p code%d pid%d uid%d\n,// (void*) txn-target.ptr, txn-code, txn-sender_pid, txn-sender_euid);if(txn-target.ptr!BINDER_SERVICE_MANAGER)return-1;if(txn-codePING_TRANSACTION)return0;// Equivalent to Parcel::enforceInterface(), reading the RPC// header with the strict mode policy mask and the interface name.// Note that we ignore the strict_policy and dont propagate it// further (since we do no outbound RPCs anyway).strict_policybio_get_uint32(msg);sbio_get_string16(msg,len);if(sNULL){return-1;}if((len!(sizeof(svcmgr_id)/2))||memcmp(svcmgr_id,s,sizeof(svcmgr_id))){fprintf(stderr,invalid id %s\n,str8(s,len));return-1;}if(sehandleselinux_status_updated()0){structselabel_handle*tmp_sehandleselinux_android_service_context_handle();if(tmp_sehandle){selabel_close(sehandle);sehandletmp_sehandle;}}switch(txn-code){caseSVC_MGR_GET_SERVICE:caseSVC_MGR_CHECK_SERVICE:sbio_get_string16(msg,len);if(sNULL){return-1;}handledo_find_service(bs,s,len,txn-sender_euid,txn-sender_pid);if(!handle)break;bio_put_ref(reply,handle);return0;caseSVC_MGR_ADD_SERVICE:sbio_get_string16(msg,len);if(sNULL){return-1;}handlebio_get_ref(msg);allow_isolatedbio_get_uint32(msg)?1:0;if(do_add_service(bs,s,len,handle,txn-sender_euid,allow_isolated,txn-sender_pid))return-1;break;caseSVC_MGR_LIST_SERVICES:{uint32_tnbio_get_uint32(msg);if(!svc_can_list(txn-sender_pid)){ALOGE(list_service() uid%d - PERMISSION DENIED\n,txn-sender_euid);return-1;}sisvclist;while((n--0)si)sisi-next;if(si){bio_put_string16(reply,si-name);return0;}return-1;}default:ALOGE(unknown code %d\n,txn-code);return-1;}bio_put_uint32(reply,0);return0;}// /frameworks/native/cmds/servicemanager/service_manager.cintdo_add_service(structbinder_state*bs,constuint16_t*s,size_tlen,uint32_thandle,uid_tuid,intallow_isolated,pid_tspid){structsvcinfo*si;//ALOGI(add_service(%s,%x,%s) uid%d\n, str8(s, len), handle,// allow_isolated ? allow_isolated : !allow_isolated, uid);if(!handle||(len0)||(len127))return-1;if(!svc_can_register(s,len,spid)){ALOGE(add_service(%s,%x) uid%d - PERMISSION DENIED\n,str8(s,len),handle,uid);return-1;}sifind_svc(s,len);if(si){if(si-handle){ALOGE(add_service(%s,%x) uid%d - ALREADY REGISTERED, OVERRIDE\n,str8(s,len),handle,uid);svcinfo_death(bs,si);}si-handlehandle;}else{simalloc(sizeof(*si)(len1)*sizeof(uint16_t));if(!si){ALOGE(add_service(%s,%x) uid%d - OUT OF MEMORY\n,str8(s,len),handle,uid);return-1;}si-handlehandle;si-lenlen;memcpy(si-name,s,(len1)*sizeof(uint16_t));si-name[len]\0;si-death.func(void*)svcinfo_death;si-death.ptrsi;si-allow_isolatedallow_isolated;si-nextsvclist;svclistsi;}binder_acquire(bs,handle);binder_link_to_death(bs,handle,si-death);return0;}binder_open(128*1024)打开 Binder 驱动open(/dev/binder, O_RDWR)打开/dev/binder检查驱动版本ioctl(bs-fd, BINDER_VERSION, vers)获取驱动版本vers.protocol_version ! BINDER_CURRENT_PROTOCOL_VERSION对比版本mmap(NULL, mapsize, PROT_READ, MAP_PRIVATE, bs-fd, 0)内存映射return bs返回句柄binder_become_context_manager(bs)成为上下文管理器固定编号 0binder_loop(bs, svcmgr_handler)进入 Binder 循环处理所有请求binder_parse(bs, 0, (uintptr_t) readbuf, bwr.read_consumed, func)解析数据switch(cmd)处理业务

相关新闻