healthd: add health HAL support

Adds board-specific battery monitoring capabilities:

* processing of battery property values and additional charging logic.
* adjusted (or removed) polling intervals.
* replaced (or removed) battery status heartbeat in kernel log.

Change-Id: Ia77bca8dc92c6c2a51afa65d516cacca08da73ac
This commit is contained in:
Todd Poynor 2013-08-07 15:25:14 -07:00
parent b45f1f5bd0
commit 10b235e743
5 changed files with 137 additions and 25 deletions

View file

@ -18,6 +18,12 @@ LOCAL_UNSTRIPPED_PATH := $(TARGET_ROOT_OUT_SBIN_UNSTRIPPED)
LOCAL_STATIC_LIBRARIES := libbatteryservice libbinder libz libutils libstdc++ libcutils liblog libm libc
ifdef BOARD_LIB_HEALTHD
LOCAL_STATIC_LIBRARIES += $(BOARD_LIB_HEALTHD)
else
LOCAL_SRC_FILES += healthd_board_default.cpp
endif
include $(BUILD_EXECUTABLE)
endif

View file

@ -16,6 +16,7 @@
#define LOG_TAG "healthd"
#include "healthd.h"
#include "BatteryMonitor.h"
#include "BatteryPropertiesRegistrar.h"
@ -170,6 +171,7 @@ int BatteryMonitor::getIntField(const String8& path) {
bool BatteryMonitor::update(void) {
struct BatteryProperties props;
bool logthis;
props.chargerAcOnline = false;
props.chargerUsbOnline = false;
@ -238,27 +240,31 @@ bool BatteryMonitor::update(void) {
}
}
char dmesgline[256];
snprintf(dmesgline, sizeof(dmesgline),
"battery l=%d v=%d t=%s%d.%d h=%d st=%d",
props.batteryLevel, props.batteryVoltage,
props.batteryTemperature < 0 ? "-" : "",
abs(props.batteryTemperature / 10),
abs(props.batteryTemperature % 10), props.batteryHealth,
props.batteryStatus);
logthis = !healthd_board_battery_update(&props);
if (!mBatteryCurrentNowPath.isEmpty()) {
char b[20];
if (logthis) {
char dmesgline[256];
snprintf(dmesgline, sizeof(dmesgline),
"battery l=%d v=%d t=%s%d.%d h=%d st=%d",
props.batteryLevel, props.batteryVoltage,
props.batteryTemperature < 0 ? "-" : "",
abs(props.batteryTemperature / 10),
abs(props.batteryTemperature % 10), props.batteryHealth,
props.batteryStatus);
snprintf(b, sizeof(b), " c=%d", props.batteryCurrentNow);
strlcat(dmesgline, b, sizeof(dmesgline));
if (!mBatteryCurrentNowPath.isEmpty()) {
char b[20];
snprintf(b, sizeof(b), " c=%d", props.batteryCurrentNow);
strlcat(dmesgline, b, sizeof(dmesgline));
}
KLOG_INFO(LOG_TAG, "%s chg=%s%s%s\n", dmesgline,
props.chargerAcOnline ? "a" : "",
props.chargerUsbOnline ? "u" : "",
props.chargerWirelessOnline ? "w" : "");
}
KLOG_INFO(LOG_TAG, "%s chg=%s%s%s\n", dmesgline,
props.chargerAcOnline ? "a" : "",
props.chargerUsbOnline ? "u" : "",
props.chargerWirelessOnline ? "w" : "");
if (mBatteryPropertiesRegistrar != NULL)
mBatteryPropertiesRegistrar->notifyListeners(props);

View file

@ -17,6 +17,7 @@
#define LOG_TAG "healthd"
#define KLOG_LEVEL 6
#include "healthd.h"
#include "BatteryMonitor.h"
#include <errno.h>
@ -34,8 +35,12 @@
using namespace android;
// Periodic chores intervals in seconds
#define PERIODIC_CHORES_INTERVAL_FAST (60 * 1)
#define PERIODIC_CHORES_INTERVAL_SLOW (60 * 10)
#define DEFAULT_PERIODIC_CHORES_INTERVAL_FAST (60 * 1)
#define DEFAULT_PERIODIC_CHORES_INTERVAL_SLOW (60 * 10)
static int periodic_chores_interval_fast =
DEFAULT_PERIODIC_CHORES_INTERVAL_FAST;
static int periodic_chores_interval_slow =
DEFAULT_PERIODIC_CHORES_INTERVAL_SLOW;
#define POWER_SUPPLY_SUBSYSTEM "power_supply"
@ -48,7 +53,7 @@ static int binder_fd;
// -1 for no epoll timeout
static int awake_poll_interval = -1;
static int wakealarm_wake_interval = PERIODIC_CHORES_INTERVAL_FAST;
static int wakealarm_wake_interval = DEFAULT_PERIODIC_CHORES_INTERVAL_FAST;
static BatteryMonitor* gBatteryMonitor;
@ -61,6 +66,10 @@ static void wakealarm_set_interval(int interval) {
return;
wakealarm_wake_interval = interval;
if (interval == -1)
interval = 0;
itval.it_interval.tv_sec = interval;
itval.it_interval.tv_nsec = 0;
itval.it_value.tv_sec = interval;
@ -75,7 +84,7 @@ static void battery_update(void) {
// slow wake interval when on battery (watch for drained battery).
int new_wake_interval = gBatteryMonitor->update() ?
PERIODIC_CHORES_INTERVAL_FAST : PERIODIC_CHORES_INTERVAL_SLOW;
periodic_chores_interval_fast : periodic_chores_interval_slow;
if (new_wake_interval != wakealarm_wake_interval)
wakealarm_set_interval(new_wake_interval);
@ -85,9 +94,12 @@ static void battery_update(void) {
// poll at fast rate while awake and let alarm wake up at slow rate when
// asleep.
awake_poll_interval =
new_wake_interval == PERIODIC_CHORES_INTERVAL_FAST ?
-1 : PERIODIC_CHORES_INTERVAL_FAST * 1000;
if (periodic_chores_interval_fast == -1)
awake_poll_interval = -1;
else
awake_poll_interval =
new_wake_interval == periodic_chores_interval_fast ?
-1 : periodic_chores_interval_fast * 1000;
}
static void periodic_chores() {
@ -138,7 +150,10 @@ static void wakealarm_init(void) {
return;
}
wakealarm_set_interval(PERIODIC_CHORES_INTERVAL_FAST);
healthd_board_poll_intervals(&periodic_chores_interval_fast,
&periodic_chores_interval_slow);
wakealarm_set_interval(periodic_chores_interval_fast);
}
static void wakealarm_event(void) {

56
healthd/healthd.h Normal file
View file

@ -0,0 +1,56 @@
/*
* Copyright (C) 2013 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#ifndef _HEALTHD_H_
#define _HEALTHD_H_
#include <batteryservice/BatteryService.h>
// The following are implemented in libhealthd_board to handle board-specific
// behavior.
//
// Set periodic poll intervals in seconds.
//
// fast_interval is used while the device is not in suspend, or in suspend and
// connected to a charger (to watch for battery overheat due to charging).
// The default value is 60 (1 minute). Value -1 turns off fast_interval
// polling.
//
// slow_interval is used when the device is in suspend and not connected to a
// charger (to watch for a battery drained to zero remaining capacity). The
// default value is 600 (10 minutes). Value -1 tuns off slow interval
// polling.
//
// To use the default values, this function can simply return without
// modifying the parameters.
void healthd_board_poll_intervals(int *fast_interval, int *slow_interval);
// Process updated battery property values. This function is called when
// the kernel sends updated battery status via a uevent from the power_supply
// subsystem, or when updated values are polled by healthd, as for periodic
// poll of battery state.
//
// props are the battery properties read from the kernel. These values may
// be modified in this call, prior to sending the modified values to the
// Android runtime.
//
// Return 0 to indicate the usual kernel log battery status heartbeat message
// is to be logged, or non-zero to prevent logging this information.
int healthd_board_battery_update(struct android::BatteryProperties *props);
#endif /* _HEALTHD_H_ */

View file

@ -0,0 +1,29 @@
/*
* Copyright (C) 2013 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include <healthd.h>
void healthd_board_poll_intervals(int *fast_interval, int *slow_interval)
{
// use defaults
}
int healthd_board_battery_update(struct android::BatteryProperties *props)
{
// return 0 to log periodic polled battery status to kernel log
return 0;
}