1752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor/*
2526f8cf339f6c215d2d89924824b674cb99cfcc9Sandeep Patil * Copyright (C) 2016 The Android Open Source Project
3752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor *
4752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor * Licensed under the Apache License, Version 2.0 (the "License");
5752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor * you may not use this file except in compliance with the License.
6752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor * You may obtain a copy of the License at
7752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor *
8752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor *      http://www.apache.org/licenses/LICENSE-2.0
9752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor *
10752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor * Unless required by applicable law or agreed to in writing, software
11752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor * distributed under the License is distributed on an "AS IS" BASIS,
12752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor * See the License for the specific language governing permissions and
14752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor * limitations under the License.
15752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor */
16752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor
17752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor#define LOG_TAG "healthd"
18752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor#define KLOG_LEVEL 6
19752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor
20e98e177a34eb3200b9f95be8379223271933b885Yabin Cui#include <healthd/healthd.h>
21752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor
22752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor#include <stdio.h>
23752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor#include <stdlib.h>
24752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor#include <unistd.h>
25752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor#include <cutils/klog.h>
26752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor
27a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil#include <android/hardware/health/1.0/IHealth.h>
28a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil#include <android/hardware/health/1.0/types.h>
29a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil#include <hal_conversion.h>
30a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
31752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynorusing namespace android;
32752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor
33a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patilusing IHealth = ::android::hardware::health::V1_0::IHealth;
34a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patilusing Result = ::android::hardware::health::V1_0::Result;
35a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patilusing HealthConfig = ::android::hardware::health::V1_0::HealthConfig;
36a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patilusing HealthInfo = ::android::hardware::health::V1_0::HealthInfo;
37a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
38a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patilusing ::android::hardware::health::V1_0::hal_conversion::convertToHealthConfig;
39a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patilusing ::android::hardware::health::V1_0::hal_conversion::convertFromHealthConfig;
40a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patilusing ::android::hardware::health::V1_0::hal_conversion::convertToHealthInfo;
41a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patilusing ::android::hardware::health::V1_0::hal_conversion::convertFromHealthInfo;
42a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
43a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil// device specific hal interface;
44a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patilstatic sp<IHealth> gHealth;
45a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
46526f8cf339f6c215d2d89924824b674cb99cfcc9Sandeep Patil// main healthd loop
47526f8cf339f6c215d2d89924824b674cb99cfcc9Sandeep Patilextern int healthd_main(void);
48c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynor
49c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynor// Android mode
50c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynorextern void healthd_mode_android_init(struct healthd_config *config);
51c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynorextern int healthd_mode_android_preparetowait(void);
52526f8cf339f6c215d2d89924824b674cb99cfcc9Sandeep Patilextern void healthd_mode_android_heartbeat(void);
53c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynorextern void healthd_mode_android_battery_update(
54c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynor    struct android::BatteryProperties *props);
55c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynor
56c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynorstatic struct healthd_mode_ops android_ops = {
57c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynor    .init = healthd_mode_android_init,
58c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynor    .preparetowait = healthd_mode_android_preparetowait,
59526f8cf339f6c215d2d89924824b674cb99cfcc9Sandeep Patil    .heartbeat = healthd_mode_android_heartbeat,
60c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynor    .battery_update = healthd_mode_android_battery_update,
61c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynor};
62c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynor
63a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil// default energy counter property redirect to talk to device
64a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil// HAL
65a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patilstatic int healthd_board_get_energy_counter(int64_t *energy) {
66a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
67a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    if (gHealth == nullptr) {
68a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil        return NAME_NOT_FOUND;
69a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    }
70a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
71a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    Result result = Result::NOT_SUPPORTED;
72a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    gHealth->energyCounter([=, &result] (Result ret, int64_t energyOut) {
73a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil                result = ret;
74a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil                *energy = energyOut;
75a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil            });
76a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
77a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    return result == Result::SUCCESS ? OK : NAME_NOT_FOUND;
78a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil}
79a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
80a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patilvoid healthd_board_init(struct healthd_config *config) {
81a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
82a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    // Initialize the board HAL - Equivalent of healthd_board_init(config)
83a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    // in charger/recovery mode.
84a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
8568f4085e0707e34bfbd88a0d06062d46b7c05204Chris Phoenix    gHealth = IHealth::getService();
86a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    if (gHealth == nullptr) {
87a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil        KLOG_WARNING(LOG_TAG, "unable to get HAL interface, using defaults\n");
88a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil        return;
89a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    }
90a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
91a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    HealthConfig halConfig;
92a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    convertToHealthConfig(config, halConfig);
93a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    gHealth->init(halConfig, [=] (const auto &halConfigOut) {
94a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil            convertFromHealthConfig(halConfigOut, config);
95a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil            // always redirect energy counter queries
96a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil            config->energyCounter = healthd_board_get_energy_counter;
97a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil            });
98a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil}
99a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
100a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patilint healthd_board_battery_update(struct android::BatteryProperties *props) {
101a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    int logthis = 0;
102a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
103a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    if (gHealth == nullptr) {
104a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil        return logthis;
105a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    }
106a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
107a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    HealthInfo info;
108a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    convertToHealthInfo(props, info);
109a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    gHealth->update(info,
110a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil            [=, &logthis] (int32_t ret, const auto &infoOut) {
111a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil                logthis = ret;
112a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil                convertFromHealthInfo(infoOut, props);
113a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil            });
114a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
115a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil    return logthis;
116a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil}
117a3681954b4241c8322d48a973be038df64ee0af4Sandeep Patil
118526f8cf339f6c215d2d89924824b674cb99cfcc9Sandeep Patilint main(int /*argc*/, char ** /*argv*/) {
1197b27f27d3de9e39d0de86c6e592d49bd4cc89158Todd Poynor
120c7464c9150eb63ad277cc5b5f704f4fd5e6678c5Todd Poynor    healthd_mode_ops = &android_ops;
121752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor
122526f8cf339f6c215d2d89924824b674cb99cfcc9Sandeep Patil    return healthd_main();
123752faf2c18407fd79127fb3f3773910b4ddf669dTodd Poynor}
124