native中的android_Looper
Java 层MessageQueue调用 native层实现,即 C++ 中的 android::Looper,它才是整个 Android 消息轮询机制的底层核心。
一、Java 到 Native 的连接点
Java 层的 MessageQueue.nativeXXX() 方法,在编译期通过 JNI 连接到了:
// frameworks/base/core/jni/android_os_MessageQueue.cpp
static const JNINativeMethod gMessageQueueMethods[] = {
{ "nativeInit", "()J", (void*)android_os_MessageQueue_nativeInit },
{ "nativeDestroy", "(J)V", (void*)android_os_MessageQueue_nativeDestroy },
{ "nativePollOnce", "(JI)V", (void*)android_os_MessageQueue_nativePollOnce },
{ "nativeWake", "(J)V", (void*)android_os_MessageQueue_nativeWake },
{ "nativeIsIdling", "(J)Z", (void*)android_os_MessageQueue_nativeIsIdling },
};
所以 MessageQueue.nativePollOnce(ptr, timeoutMillis) 实际就是调用:
android_os_MessageQueue_nativePollOnce()
它内部用的是 Looper::pollOnce()。
二、C++ 层:android::Looper
Looper 是 Android 自研的事件轮询器,它不像 Linux Looper 或 glibc 的 select/poll,而是封装了 epoll,对性能做了深度优化。
三、nativePollOnce 实现过程(简化流程)
int Looper::pollOnce(int timeoutMillis) {
// 1. 等待事件(消息、管道、eventfd)
int result = pollInner(timeoutMillis);
// 2. 调用对应的回调(如 socket、fd、MessageHandler 等)
if (result == POLL_WAKE) {
// 有 wake() 唤醒(比如主线程被唤醒处理 Handler 消息)
awoken = false;
}
// 3. 返回给 Java 层,Java 继续处理 Message
return result;
}
四、Looper 中关键组件
组件 | 作用 |
---|---|
epollFd | 核心 epoll 实例,用于高效监听事件 |
eventFd / pipeFd | 与 Java 层交互的唤醒机制 |
requestWake() | 被 Java 层 nativeWake() 调用,写入 pipe 触发 epoll |
MessageEnvelope | C++ 层的 Message 封装,支持 callback/what 等 |
五、epoll 等待/唤醒原理图
Java: Handler.sendMessage() → nativeWake()
↓
native: Looper.requestWake() 写 eventfd
↓
Looper.epollWait() 被唤醒,pollOnce 返回
↓
Java: MessageQueue.next() → 返回 msg → Looper.dispatchMessage()
- Looper 通常处于 epoll_wait 阻塞状态;
- 一旦有新事件(包括 Java 线程发的消息),就会唤醒并返回;
- 消息分为多种类型:fd 读写、定时器、handler 消息、idle handler 等。
六、nativeWake 实现(C++)
void Looper::wake() {
uint64_t inc = 1;
write(mWakeEventFd, &inc, sizeof(uint64_t)); // 写入 eventfd
}
这段代码保证 epoll 能立即被唤醒,从而处理新消息(否则一直阻塞)。
七、整体执行流程图(Java & Native)
[Java Thread] [Native (C++) Looper]
↓ ↓
Handler.post() nativeWake()
↓ ↓
enqueueMessage() → Looper::wake() → eventFd write → epoll 唤醒
↓ ↓
MessageQueue.next() ← nativePollOnce()
↓
获取到 msg → Looper.dispatchMessage()
八、总结重点
Java 层调用 | 对应 native 操作 | 作用 |
---|---|---|
nativeInit() | 创建 android::Looper 实例 | 初始化 |
nativePollOnce() | epoll_wait 等待事件 | 阻塞直到事件到来 |
nativeWake() | eventfd 写入,唤醒 epoll | 提前唤醒轮询线程 |
nativeDestroy() | 删除 Looper 对象 | 释放资源 |
nativeIsIdling() | 检查当前是否没有活跃事件 | 可选功能 |