总结:NetlinkManager是直接接收Kernel消息的模块,其从kernel接收Uevent事件,然后转换成一个NetlinkEvent对象,最后调用VolumeManager的处理函数继续后续操作。NetLinkEvent以及Uevent存在的目的就是告知上层底层发生的一切。
1、system/vold/NetlinkManager.cpp
由之前的了解,可知,在系统启动后,NetlinkManager会做以下事情:
1、nm->setBroadcaster((SocketListener *) cl); 2、if (nm->start()) { SLOGE("Unable to start NetlinkManager (%s)", strerror(errno)); exit(1); } 3、coldboot("/sys/block");
void setBroadcaster(SocketListener *sl) { mBroadcaster = sl; }2、2:start方法:
首先初始化接收底层消息的socket,并为其开辟内存空间。
struct sockaddr_nl nladdr; int sz = 64 * 1024; int on = 1; memset(&nladdr, 0, sizeof(nladdr)); nladdr.nl_family = AF_NETLINK; nladdr.nl_pid = getpid(); nladdr.nl_groups = 0xffffffff; if ((mSock = socket(PF_NETLINK, SOCK_DGRAM,NETLINK_KOBJECT_UEVENT)) < 0) { SLOGE("Unable to create uevent socket: %s", strerror(errno)); return -1; }执行bind操作:
if (bind(mSock, (struct sockaddr *) &nladdr, sizeof(nladdr)) < 0) { SLOGE("Unable to bind uevent socket: %s", strerror(errno)); goto out; }
mHandler = new NetlinkHandler(mSock); if (mHandler->start()) { SLOGE("Unable to start NetlinkHandler: %s", strerror(errno)); goto out; }
2.3:coldboot("/sys/block");方法
static void do_coldboot(DIR *d, int lvl) { struct dirent *de; int dfd, fd; dfd = dirfd(d); fd = openat(dfd, "uevent", O_WRONLY); if(fd >= 0) { write(fd, "add\n", 4); close(fd); } while((de = readdir(d))) { DIR *d2; if (de->d_name[0] == '.') continue; if (de->d_type != DT_DIR && lvl > 0) continue; fd = openat(dfd, de->d_name, O_RDONLY | O_DIRECTORY); if(fd < 0) continue; d2 = fdopendir(fd); if(d2 == 0) close(fd); else { do_coldboot(d2, lvl + 1); closedir(d2); } } }
3、NetlinkHandler执行start方法
NetlinkHandler的start方法,最终会执行SocketListener中:
int NetlinkHandler::start() { return this->startListener(); }SocketListener
int SocketListener::startListener() { return startListener(4); } int SocketListener::startListener(int backlog) { if (!mSocketName && mSock == -1) { SLOGE("Failed to start unbound listener"); errno = EINVAL; return -1; } else if (mSocketName) { if ((mSock = android_get_control_socket(mSocketName)) < 0) { SLOGE("Obtaining file descriptor socket '%s' failed: %s", mSocketName, strerror(errno)); return -1; } SLOGV("got mSock = %d for %s", mSock, mSocketName); } if (mListen && listen(mSock, backlog) < 0) { SLOGE("Unable to listen on socket (%s)", strerror(errno)); return -1; } else if (!mListen) mClients->push_back(new SocketClient(mSock, false, mUseCmdNum)); if (pipe(mCtrlPipe)) { SLOGE("pipe failed (%s)", strerror(errno)); return -1; } if (pthread_create(&mThread, NULL, SocketListener::threadStart, this)) { SLOGE("pthread_create (%s)", strerror(errno)); return -1; } return 0; }这里主要处理了3件事情:
1、以mSock作为参数,构建SocketClient,并加入到mClient中。
mClients->push_back(new SocketClient(mSock, false, mUseCmdNum));
if (pipe(mCtrlPipe)) { SLOGE("pipe failed (%s)", strerror(errno)); return -1; }
3、创建线程SocketListener,并执行。
if (pthread_create(&mThread, NULL, SocketListener::threadStart, this)) { SLOGE("pthread_create (%s)", strerror(errno)); return -1; }5、那么我们接下来的流程就到了NetlinkHandler创建的线程的执行中。
void *SocketListener::threadStart(void *obj) { SocketListener *me = reinterpret_cast<SocketListener *>(obj); me->runListener(); pthread_exit(NULL); return NULL; }
这个方法会做如下事情 :
socket获取kernel上报的NetLinkEvent并回调onEvent方法。
NetlinkEvent *evt = new NetlinkEvent(); if (evt->decode(mBuffer, count, mFormat)) { onEvent(evt); } else if (mFormat != NETLINK_FORMAT_BINARY) { // Don't complain if parseBinaryNetlinkMessage returns false. That can // just mean that the buffer contained no messages we're interested in. SLOGE("Error decoding NetlinkEvent"); }最终:NetLinkHandler方法执行onEvent方法:
VolumeManager *vm = VolumeManager::Instance(); const char *subsys = evt->getSubsystem(); if (!subsys) { SLOGW("No subsystem found in netlink event"); return; } if (!strcmp(subsys, "block")) { vm->handleBlockEvent(evt); }