UEventObserver是android Java层利用uevent与获取Kernel层状态变化的机制。
通过grep发现framework有如下模块使用UEventObserver的功能来提供服务:电池状态:services/java/com/android/server/BatteryService.java耳机状态:services/java/com/android/server/HeadsetObserver.javaDOCK状态:services/java/com/android/server/DockObserver.javaUSB状态:services/java/com/android/server/usb/UsbService.java
它们全部继承自UEventObserver,先看看这个类的构造和原理:./core/java/android/os/UEventObserver.java | [ native_setup(),next_event() ] \|/./core/jni/android_os_UEventObserver.cpp | [ uevent_init(),uevent_next_event() ] \|//hardware/libhardware_legacy/uevent/uevent.c | [userspace]---------------------[socket]----------------------------------------------------------------------------- | \|/ [kernel] socket(PF_NETLINK, SOCK_DGRAM, NETLINK_KOBJECT_UEVENT)
下面用HeadsetObserver作为例子说明如何使用UEventObserver来监听kernel的uevent。继承UEventObserver的类必须实现自己的public abstract void onUEvent(UEvent event):
    @Override    public void onUEvent(UEventObserver.UEvent event) {        if (LOG) Slog.v(TAG, "Headset UEVENT: " + event.toString());        try {            update(event.get("SWITCH_NAME"), Integer.parseInt(event.get("SWITCH_STATE"))); // update中处理事务        } catch (NumberFormatException e) {            Slog.e(TAG, "Could not parse switch state from event " + event);        }    }

这个函数会在UEventObserver接收到event的时候由UEventObserver来回调,HeadsetObserver使用startObserving("DEVPATH=/devices/virtual/switch/h2w")来开始监听,这个API会确保sThread已经运行并且以字串参数作为匹配参数增加一个observer: public final synchronized void startObserving(String match) {
ensureThreadStarted();
sThread.addObserver(match, this);
}

UEventObserver的核心部分就是sThread的run:
public void run() {    native_setup(); //调用uevent.c中的API来打开socket    byte[] buffer = new byte[1024];    int len;    while (true) {        len = next_event(buffer); // 在uevent.c中用poll调用来获取event,会阻塞        if (len > 0) {            String bufferStr = new String(buffer, 0, len);  // easier to search a String            synchronized (mObservers) {                for (int i = 0; i < mObservers.size(); i += 2) {                    if (bufferStr.indexOf((String)mObservers.get(i)) != -1) { // 找到匹配的match参数,说明某个observer的监听的event发生了                        ((UEventObserver)mObservers.get(i+1))                                .onUEvent(new UEvent(bufferStr)); // 调用这个observer的onUEvent函数                    }                }            }        }    }}

// TODO: 分析kernel层如何上报uevent事件

更多相关文章

  1. C语言函数以及函数的使用
  2. Android jni系统变量、函数、接口定义汇总
  3. sscanf函数引起android 5.0卡死,C++中慎用C库函数
  4. android 状态栏移动到底部
  5. Android Studio3.1.2 build.gradle classpath参数报错
  6. Android实现自己的回调函数
  7. Android 如何调用MediaPlayer播放视频[状态机]【图】
  8. Android Studio中如何隐藏顶部状态栏和标题栏

随机推荐

  1. Android(安卓)网络编程
  2. Android Wear和二维码
  3. Android 关机流程分析-----(1)Framework层
  4. Android(安卓)Afianl框架(2)——FinalDB
  5. Android经典应用程序开发
  6. Android问题集锦之十:Android导入项目时An
  7. 2011.09.14(2)——— android tabhost位于
  8. Android中对媒体的使用
  9. Android(安卓)Studio 编译常见问题解决办
  10. revoke_permission 实现过程