2 * Copyright 2012 Samsung Electronics Co., Ltd
4 * Licensed under the Flora License, Version 1.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.tizenopensource.org/license
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
26 #include "ss_launch.h"
29 #include "ss_device_plugin.h"
30 #include "include/ss_data.h"
32 #define BAT_MON_INTERVAL 30
33 #define BAT_MON_INTERVAL_MIN 2
35 #define BATTERY_CHARGING 65535
36 #define BATTERY_UNKNOWN -1
37 #define BATTERY_NORMAL 100
38 #define BATTERY_WARNING_LOW 15
39 #define BATTERY_CRITICAL_LOW 5
40 #define BATTERY_POWER_OFF 1
41 #define BATTERY_REAL_POWER_OFF 0
43 #define MAX_BATTERY_ERROR 10
44 #define RESET_RETRY_COUNT 3
46 #define LOWBAT_EXEC_PATH PREFIX"/bin/lowbatt-popup"
48 static int battery_level_table[] = {
49 5, /* BATTERY_LEVEL0 */
58 #define _SYS_LOW_POWER "LOW_POWER"
60 struct lowbat_process_entry {
61 unsigned cur_bat_state;
62 unsigned new_bat_state;
63 int (*action) (void *);
66 static Ecore_Timer *lowbat_timer;
67 static int cur_bat_state = BATTERY_UNKNOWN;
68 static int cur_bat_capacity = -1;
70 static int bat_err_count = 0;
72 static int battery_warning_low_act(void *ad);
73 static int battery_critical_low_act(void *ad);
74 static int battery_power_off_act(void *ad);
76 static struct lowbat_process_entry lpe[] = {
77 {BATTERY_NORMAL, BATTERY_WARNING_LOW, battery_warning_low_act},
78 {BATTERY_WARNING_LOW, BATTERY_CRITICAL_LOW, battery_critical_low_act},
79 {BATTERY_CRITICAL_LOW, BATTERY_POWER_OFF, battery_critical_low_act},
80 {BATTERY_POWER_OFF, BATTERY_REAL_POWER_OFF, battery_power_off_act},
81 {BATTERY_NORMAL, BATTERY_CRITICAL_LOW, battery_critical_low_act},
82 {BATTERY_WARNING_LOW, BATTERY_POWER_OFF, battery_critical_low_act},
83 {BATTERY_CRITICAL_LOW, BATTERY_REAL_POWER_OFF, battery_power_off_act},
84 {BATTERY_NORMAL, BATTERY_POWER_OFF, battery_critical_low_act},
85 {BATTERY_WARNING_LOW, BATTERY_REAL_POWER_OFF, battery_power_off_act},
86 {BATTERY_NORMAL, BATTERY_REAL_POWER_OFF, battery_power_off_act},
89 static int battery_warning_low_act(void *data)
91 char lowbat_noti_name[NAME_MAX];
93 heynoti_get_snoti_name(_SYS_LOW_POWER, lowbat_noti_name, NAME_MAX);
94 ss_noti_send(lowbat_noti_name);
96 ss_action_entry_call_internal(PREDEF_LOWBAT, 1, WARNING_LOW_BAT_ACT);
100 static int battery_critical_low_act(void *data)
102 ss_action_entry_call_internal(PREDEF_LOWBAT, 1, CRITICAL_LOW_BAT_ACT);
106 static int battery_power_off_act(void *data)
108 ss_action_entry_call_internal(PREDEF_LOWBAT, 1, POWER_OFF_BAT_ACT);
112 static int battery_charge_act(void *data)
117 int ss_lowbat_set_charge_on(int onoff)
119 if(vconf_set_int(VCONFKEY_SYSMAN_BATTERY_CHARGE_NOW, onoff)!=0) {
120 PRT_TRACE_ERR("fail to set charge vconf value");
126 int ss_lowbat_is_charge_in_now()
129 if (0 > plugin_intf->OEM_sys_get_battery_charge_now(&val)) {
130 PRT_TRACE_ERR("fail to read charge now from kernel");
131 ss_lowbat_set_charge_on(0);
136 ss_lowbat_set_charge_on(1);
139 ss_lowbat_set_charge_on(0);
144 static int lowbat_process(int bat_percent, void *ad)
146 int new_bat_capacity;
148 int vconf_state = -1;
151 new_bat_capacity = bat_percent;
152 if (new_bat_capacity < 0)
154 if (new_bat_capacity != cur_bat_capacity) {
155 if (vconf_set_int(VCONFKEY_SYSMAN_BATTERY_CAPACITY, new_bat_capacity) == 0)
156 cur_bat_capacity = new_bat_capacity;
157 PRT_TRACE("[BAT_MON] cur = %d new = %d", cur_bat_capacity, new_bat_capacity);
160 if (0 > vconf_get_int(VCONFKEY_SYSMAN_BATTERY_STATUS_LOW, &vconf_state)) {
161 PRT_TRACE_ERR("vconf_get_int() failed");
165 if (new_bat_capacity <= BATTERY_POWER_OFF) {
166 new_bat_state = BATTERY_POWER_OFF;
167 if (vconf_state != VCONFKEY_SYSMAN_BAT_POWER_OFF)
168 ret=vconf_set_int(VCONFKEY_SYSMAN_BATTERY_STATUS_LOW, VCONFKEY_SYSMAN_BAT_POWER_OFF);
169 } else if (new_bat_capacity <= BATTERY_CRITICAL_LOW) {
170 new_bat_state = BATTERY_CRITICAL_LOW;
171 if (vconf_state != VCONFKEY_SYSMAN_BAT_CRITICAL_LOW)
172 ret=vconf_set_int(VCONFKEY_SYSMAN_BATTERY_STATUS_LOW, VCONFKEY_SYSMAN_BAT_CRITICAL_LOW);
173 } else if (new_bat_capacity <= BATTERY_WARNING_LOW) {
174 new_bat_state = BATTERY_WARNING_LOW;
175 if (vconf_state != VCONFKEY_SYSMAN_BAT_WARNING_LOW)
176 ret=vconf_set_int(VCONFKEY_SYSMAN_BATTERY_STATUS_LOW, VCONFKEY_SYSMAN_BAT_WARNING_LOW);
178 new_bat_state = BATTERY_NORMAL;
179 if (vconf_state != VCONFKEY_SYSMAN_BAT_NORMAL)
180 ret=vconf_set_int(VCONFKEY_SYSMAN_BATTERY_STATUS_LOW, VCONFKEY_SYSMAN_BAT_NORMAL);
186 ss_lowbat_is_charge_in_now();
188 if (cur_bat_state == new_bat_state
189 && cur_bat_state != BATTERY_POWER_OFF)
192 if (cur_bat_state == BATTERY_UNKNOWN) {
194 i < sizeof(lpe) / sizeof(struct lowbat_process_entry);
196 if (new_bat_state == lpe[i].new_bat_state) {
198 cur_bat_state = new_bat_state;
204 i < sizeof(lpe) / sizeof(struct lowbat_process_entry);
206 if ((cur_bat_state == lpe[i].cur_bat_state)
207 && (new_bat_state == lpe[i].new_bat_state)) {
209 cur_bat_state = new_bat_state;
214 cur_bat_state = new_bat_state;
215 PRT_TRACE("[BATMON] Unknown battery state");
219 static int lowbat_read()
223 plugin_intf->OEM_sys_get_battery_capacity(&bat_percent);
228 int ss_lowbat_monitor(void *data)
230 struct ss_main_data *ad = (struct ss_main_data *)data;
233 bat_percent = lowbat_read();
234 if (bat_percent < 0) {
235 ecore_timer_interval_set(lowbat_timer, BAT_MON_INTERVAL_MIN);
237 if (bat_err_count > MAX_BATTERY_ERROR) {
239 ("[BATMON] Cannot read battery gage. stop read fuel gage");
244 if (bat_percent > 100)
247 if (lowbat_process(bat_percent, ad) < 0)
248 ecore_timer_interval_set(lowbat_timer, BAT_MON_INTERVAL_MIN);
250 ecore_timer_interval_set(lowbat_timer, BAT_MON_INTERVAL);
255 static int wakeup_cb(keynode_t *key_nodes, void *data)
260 vconf_keynode_get_int(key_nodes)) == VCONFKEY_PM_STATE_LCDOFF)
261 ss_lowbat_monitor(NULL);
266 /* for debugging (request by kernel) */
267 static int check_battery()
272 if (0 > plugin_intf->OEM_sys_get_battery_present(&ret)) {
273 PRT_TRACE_ERR("[BATMON] battery check : %d", ret);
275 PRT_TRACE("[BATMON] battery check : %d", ret);
280 int ss_lowbat_init(struct ss_main_data *ad)
284 /* need check battery */
286 ecore_timer_add(BAT_MON_INTERVAL_MIN, ss_lowbat_monitor, ad);
287 ss_lowbat_is_charge_in_now();
289 vconf_notify_key_changed(VCONFKEY_PM_STATE, (void *)wakeup_cb, NULL);