BatteryManager主要是去主动查看电池状态,主要通过binder通信去healthd中查看电池的各个属性。
可以看下BatteryManager的主要代码
private long queryProperty(int id) {
long ret;
if (mBatteryPropertiesRegistrar == null) {
IBinder b = ServiceManager.getService("batteryproperties");//这个service就是在healthd中加入ServiceManager中
mBatteryPropertiesRegistrar =
IBatteryPropertiesRegistrar.Stub.asInterface(b);//转化接口
if (mBatteryPropertiesRegistrar == null)
return Long.MIN_VALUE;
}
try {
BatteryProperty prop = new BatteryProperty();//新建一个数据类型
if (mBatteryPropertiesRegistrar.getProperty(id, prop) == 0)//prop作为结果返回
ret = prop.getLong();
else
ret = Long.MIN_VALUE;
} catch (RemoteException e) {
ret = Long.MIN_VALUE;
}
return ret;
}
public int getIntProperty(int id) {
return (int)queryProperty(id);
}
public long getLongProperty(int id) {
return queryProperty(id);
}
}
接下来我们看下healthd中batteryproperties这个service:
void BatteryPropertiesRegistrar::publish() {
defaultServiceManager()->addService(String16(“batteryproperties”), this);//将service加入到serviceManager中
}
void BatteryPropertiesRegistrar::notifyListeners(struct BatteryProperties props) {
Mutex::Autolock _l(mRegistrationLock);
for (size_t i = 0; i < mListeners.size(); i++) {//通知各个注册到healthd中的listener,类似BatteryService中注册到healthd中的listener(binder通信)
mListeners[i]->batteryPropertiesChanged(props);
}
}
void BatteryPropertiesRegistrar::registerListener(const sp& listener) {//注册到healthd的函数,比如BatteryService中,实现一个aidl,然后将这个类的stub实现,发到这边注册
//这样BatteryService中的BatteryLIstener就类似这边的一个server端,把接口发过来,到时候利用notifyListener来进行跨进程调用。
{
if (listener == NULL)
return;
Mutex::Autolock _l(mRegistrationLock);
// check whether this is a duplicate
for (size_t i = 0; i < mListeners.size(); i++) {
if (mListeners[i]->asBinder() == listener->asBinder()) {
return;
}
}
mListeners.add(listener);
listener->asBinder()->linkToDeath(this);
}
healthd_battery_update();
}
status_t BatteryPropertiesRegistrar::getProperty(int id, struct BatteryProperty *val) {
return healthd_get_property(id, val);
}
当BatteryManager中调用getProperty会到healthd中的getProperty,下面我们再详细看看这个函数:
status_t BatteryMonitor::getProperty(int id, struct BatteryProperty *val) {
status_t ret = BAD_VALUE;
val->valueInt64 = LONG_MIN;
switch(id) {
case BATTERY_PROP_CHARGE_COUNTER:
if (!mHealthdConfig->batteryChargeCounterPath.isEmpty()) {
val->valueInt64 =
getIntField(mHealthdConfig->batteryChargeCounterPath);//将结果返回到BatteryProperty对象中
ret = NO_ERROR;//返回0是没有错
} else {
ret = NAME_NOT_FOUND;
}
break;
case BATTERY_PROP_CURRENT_NOW:
if (!mHealthdConfig->batteryCurrentNowPath.isEmpty()) {
val->valueInt64 =
getIntField(mHealthdConfig->batteryCurrentNowPath);
ret = NO_ERROR;
} else {
ret = NAME_NOT_FOUND;
}
break;
case BATTERY_PROP_CURRENT_AVG:
if (!mHealthdConfig->batteryCurrentAvgPath.isEmpty()) {
val->valueInt64 =
getIntField(mHealthdConfig->batteryCurrentAvgPath);
ret = NO_ERROR;
} else {
ret = NAME_NOT_FOUND;
}
break;
case BATTERY_PROP_CAPACITY:
if (!mHealthdConfig->batteryCapacityPath.isEmpty()) {
val->valueInt64 =
getIntField(mHealthdConfig->batteryCapacityPath);
ret = NO_ERROR;
} else {
ret = NAME_NOT_FOUND;
}
break;
case BATTERY_PROP_ENERGY_COUNTER:
if (mHealthdConfig->energyCounter) {
ret = mHealthdConfig->energyCounter(&val->valueInt64);
} else {
ret = NAME_NOT_FOUND;
}
break;
default:
break;
}
return ret;
}