文章目录
一、Handler机制架构图
二、Handler同步屏障机制
流程图在关键处对同步机制进行了说明, 接下来只取部分关键代码进行说明
2.1 MessageQueue.next()
Message next() {
int pendingIdleHandlerCount = -1; // -1 only during first iteration
int nextPollTimeoutMillis = 0;
for (;;) {
if (nextPollTimeoutMillis != 0) {
Binder.flushPendingCommands();
}
nativePollOnce(ptr, nextPollTimeoutMillis);
synchronized (this) {
// Try to retrieve the next message. Return if found.
final long now = SystemClock.uptimeMillis();
Message prevMsg = null;
Message msg = mMessages;
// 同步屏障的消息target == null, 如果存在同步屏障, 进入到下面逻辑中
if (msg != null && msg.target == null) {
// 遍历链表取出异步消息
do {
prevMsg = msg;
msg = msg.next;
} while (msg != null && !msg.isAsynchronous());
// 注意!!! 这里并没有移除屏障的逻辑!!!
// MessageQueue.removeSyncBarrier可以移除指定的同步屏障
}
//...
三、I/O多路复用
- 1、IO多路复用的优势在于, 当处理的消耗对比IO几乎可以忽略不计时, 可以处理大量的并发IO, 而不用消耗太多的CPU/内存
- 2、IO多路复用指的是同一个进(线)成可以处理多个IO数据流
- 3、多线程+池模型指的是每个线程处理一个IO流
3.1 相关函数
3.1.1 epoll_create
// size: 告诉内核这个监听的数目一共有多大
int epoll_create(int size);
创建一个epoll句柄, 当创建好epoll句柄后, 它就是会占用一个fd值, 在使用完epoll之后, 必须调用
close()关闭, 否则就可能导致fd被耗尽
3.1.2 epoll_ctl
/**
* fd: 需要监听的fd
* *event: 告诉内核需要监听什么事件
*/
int epoll_ctl(int epfd, int op, int fd, struct epoll_event *event)
3.1.3 epoll_wait
/**
* 等待事件的产生
* timeout: 超时时间(毫秒) 0立即返回, -1将阻塞, 大于0阻塞timeout后唤醒
*/
int epoll_wait(int epfd, struct epoll_event *events, int maxevents, int timeout)