androidwakelock_Android 电源管理 -- wakelock机制

PowerManager.WakeLock有加锁和解锁两种状态,加锁的方式有两种:

第一种是永久的锁住,这样的锁除非显式的放开,否则是不会解锁的,所以这种锁用起来要非常的小心。

第二种锁是超时锁,这种锁会在锁住后一段时间解锁。

在创建了PowerManager.WakeLock后,有两种机制,第一种是不计数锁机制,另一种是计数锁机制。可以通过setReferenceCounted(boolean value)来指定,一般默认为计数机制。这两种机制的区别在于,前者无论acquire()了多少次,只要通过一次release()即可解锁。而后者正真解锁是在(--count == 0)的时候,同样当(count == 0)的时候才会去申请加锁。所以PowerManager.WakeLock的计数机制并不是正真意义上的对每次请求进行申请/释放每一把锁,它只是对同一把锁被申请/释放的次数进行了统计,然后再去操作。

源码 位置:frameworks/base/core/java/android/os/PowerManager.java

++++++++++++++++++++++++

讲述 应用层 申请的锁怎么传到kernel下面的,来理解整个wakelock的框架。比如android跑起来之后 在 /sys/power/wake_lock 下面的PowerManagerService的生成过程。

1).应用程序申请锁

Android 提供了现成 android.os.PowerManager 类 , 类中提供newWakeLock(int flags, String tag)方法 来取得应用层的锁, 此函数的定义frameworks/base/core/java/android/os/PowerManager.java

应用程序 在申请wake_lock时 都会有调用以下 部分。

实例:

PowerManagerpm = (PowerManager)getSystemService(Context.POWER_SERVICE);

PowerManager.WakeLock wl = pm.newWakeLock(PowerManager.SCREEN_DIM_WAKE_LOCK, “MyTag”);

wl.acquire();//申请锁,这里会调用PowerManagerService里面acquireWakeLock()

***********************

wl.release(); //释放锁,显示的释放锁,如果申请的锁不在此释放,系统就不会进入休眠。

======================================

2). frameworks层

/frameworks/base/services/java/com/android/server/PowerManagerService.java这个类是来管理 所有的应用程序 申请的wakelock。比如音视、频播放器、camera等申请的wakelock 都是通过这个类来 管理的。

static final String PARTIAL_NAME ="PowerManagerService"

nativeAcquireWakeLock(PARTIAL_WAKE_LOCK_ID, PARTIAL_NAME);

上面 这个函数调用Power类 里面的acquireWakeLock(),此时的PARTIAL_NAME作为参数传递到底层去。

public static native void nativeAcquireWakeLock(int lock, String id);

注:在PowerManagerService类中没有实现nativeAcquireWakeLock,其实现体在frameworks/base/core/jni/android_os_Power.cpp中,所以nativeAcquireWakeLock()方法时会调用JNI下的实现方法。

3).JNI层的实现

路径:frameworks/base/core/jni/android_os_Power.cpp //

static void acquireWakeLock(JNIEnv *env, jobject clazz,jint lock, jstring idObj)

{

**************

const char *id = env->GetStringUTFChars(idObj, NULL);

acquire_wake_lock(lock, id);

env->ReleaseStringUTFChars(idObj, id);

}

注:在acquireWakeLock()中调用了路径下hardware/libhardware_legacy/power/power.c下面的acquire_wake_lock(lock, id)

4).与kernel层的交互

在power.c下的acquire_wake_lock(lock, id)函数如下:

int acquire_wake_lock(int lock, const char* id)

{

**************

return write(fd, id, strlen(id));

}

注:fd就是文件描述符,在此表示”/sys/power/wake_lock”id就是从PowerManagerService类中传下来的参数即:PARTIAL_NAME = "PowerManagerService"到此 就是通过 文件系统 来与kernel层 交互的地方。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值