Android ueventd解析

android 中的ueventd是一个守护进程,主要作用是接收uevent来创建或删除/dev/xxx(设备节点),ueventd代码不多,下面我们直接针对代码分析。


int ueventd_main(int argc, char **argv)

{

   struct pollfd ufd;

   int nr;

   char tmp[32];

 

   /*

    * init sets the umask to 077 for forked processes. We need to

    * create files with exact permissions, without modification by

    * the umask.

    */

   umask(000);

 

   /* Prevent fire-and-forget children from becoming zombies.

    * If we should need to wait() for some children in the future

    * (as opposed to none right now), double-forking here instead

    * of ignoring SIGCHLD may be the better solution.

    */

   signal(SIGCHLD, SIG_IGN);

 

   open_devnull_stdio();

   klog_init();

 

   INFO("starting ueventd\n");

 

   /* Respect hardware passed in through the kernel cmd line. Here we willlook

    * for androidboot.hardware param in kernel cmdline, and save its valuein

    * hardware[]. */

   import_kernel_cmdline(0, import_kernel_nv);

 

   get_hardware_name(hardware, &revision);

 

 

   //解析ueventd.rcueventd.xx.rc,将文件中的每一行信息存放到一个perm_node结构体,然后将这些结构体组成一个双向链表,每一行包含文件名、uidgid、权限等

   ueventd_parse_config_file("/ueventd.rc");

 

   snprintf(tmp, sizeof(tmp), "/ueventd.%s.rc", hardware);

   ueventd_parse_config_file(tmp);

 

   //1.建立接收ueventsocket   2.如果没有做过coldboot,做一次coldboot

   //所谓coldboot是指让kernel重新生成deviceadd事件

   device_init();

 

   ufd.events = POLLIN;

   ufd.fd = get_device_fd();

      

   //循环poll ufdPOLLIN事件, POLLIN事件表示有数据可读,具体可参考linux poll系统调用的相关资料

   while(1) {

       ufd.revents = 0;

       nr = poll(&ufd, 1, -1);

       if (nr <= 0)

           continue;

       if (ufd.revents == POLLIN)

               handle_device_fd();   //详见下文

    }

}

 

#define UEVENT_MSG_LEN  1024

void handle_device_fd()

{

   char msg[UEVENT_MSG_LEN+2];

   int n;

   while ((n = uevent_kernel_multicast_recv(device_fd, msg,UEVENT_MSG_LEN)) > 0) {

       if(n >= UEVENT_MSG_LEN)   /*overflow -- discard */

           continue;

 

       msg[n] = '\0';

       msg[n+1] = '\0';

 

       struct uevent uevent;

       //解析uevent消息,保存到uevent变量中

       parse_event(msg, &uevent);

 

 

       handle_device_event(&uevent);            //详见下文

 

       //处理subsystemfirmwareuevent,详见下文

       handle_firmware_event(&uevent);

    }

}

 

 

 

 

static void handle_device_event(structuevent *uevent)

{

    //针对actionaddchanger,修复一下文件权限

   if (!strcmp(uevent->action,"add") ||!strcmp(uevent->action, "change"))

       fixup_sys_perms(uevent->path);

     

   //针对blockplatform等设备进行处理 

   if (!strncmp(uevent->subsystem, "block", 5)) {

       handle_block_device_event(uevent);

    }else if (!strncmp(uevent->subsystem, "platform", 8)) {

       handle_platform_device_event(uevent);

    }else {

       handle_generic_device_event(uevent);

    }

}

 

 




 


  • 0
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值