2 * Copyright (c) 2011 - 2015 Samsung Electronics Co., Ltd All Rights Reserved
4 * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0
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.
32 * Parameters for device_power_request_lock()
34 #define STAY_CUR_STATE 0x1
35 #define GOTO_STATE_NOW 0x2
36 #define HOLD_KEY_BLOCK 0x4
37 #define STANDBY_MODE 0x8
40 * Parameters for device_power_request_unlock()
42 #define PM_SLEEP_MARGIN 0x0 /**< keep guard time for unlock */
43 #define PM_RESET_TIMER 0x1 /**< reset timer for unlock */
44 #define PM_KEEP_TIMER 0x2 /**< keep timer for unlock */
46 #define METHOD_LOCK_STATE "lockstate"
47 #define METHOD_UNLOCK_STATE "unlockstate"
48 #define METHOD_CHANGE_STATE "changestate"
49 #define METHOD_REBOOT "Reboot"
50 #define METHOD_REBOOT_WITH_OPTION "RebootWithOption"
52 #define TYPE_REBOOT "reboot"
53 #define REBOOT_REASON_NONE ""
55 #define STR_STAYCURSTATE "staycurstate"
56 #define STR_GOTOSTATENOW "gotostatenow"
58 #define STR_HOLDKEYBLOCK "holdkeyblock"
59 #define STR_STANDBYMODE "standbymode"
60 #define STR_NULL "NULL"
62 #define STR_SLEEP_MARGIN "sleepmargin"
63 #define STR_RESET_TIMER "resettimer"
64 #define STR_KEEP_TIMER "keeptimer"
66 #define STR_LCD_OFF "lcdoff"
67 #define STR_LCD_DIM "lcddim"
68 #define STR_LCD_ON "lcdon"
70 #define LOCK_CPU_TIMEOUT_MAX (24*60*60*1000) /* milliseconds */
71 #define LOCK_CPU_PADDING_TIMEOUT (20*1000) /* milliseconds */
73 #define POWER_CONF "/etc/deviced/device/power.conf"
75 static guint off_lock_timeout;
76 static guint padding_timeout;
77 static int prev_count;
79 static GList *request_id_list;
81 static struct _lock_timeout {
85 .release = LOCK_CPU_TIMEOUT_MAX,
86 .padding = LOCK_CPU_PADDING_TIMEOUT,
89 static char *get_state_str(display_state_e state)
92 case DISPLAY_STATE_NORMAL:
94 case DISPLAY_STATE_SCREEN_DIM:
96 case DISPLAY_STATE_SCREEN_OFF:
104 static void remove_off_lock_timeout(void)
106 if (!TIZEN_FEATURE_TRACKER)
108 if (off_lock_timeout) {
109 _I("Power lock timeout handler removed");
110 g_source_remove(off_lock_timeout);
111 off_lock_timeout = 0;
115 static void remove_padding_timeout(void)
117 if (!TIZEN_FEATURE_TRACKER)
119 if (padding_timeout) {
120 _I("Padding timeout handler removed");
121 g_source_remove(padding_timeout);
126 static void notice_lock_expired_done(void *data, GVariant *result, GError *err)
136 g_variant_get(result, "(si)", &id, &val);
139 len = strlen(id) + 1;
140 for (l = request_id_list, l_next = g_list_next(l);
141 l && (elem = l->data) != NULL;
142 l = l_next, l_next = g_list_next(l), elem = NULL) {
143 if (!strncmp(id, elem, len))
149 request_id_list = g_list_remove(request_id_list, elem);
152 if (val == 0) { /* Allow to lock cpu */
153 _I("Continue Power Lock");
155 } else if (val == 1) { /* Release cpu lock */
156 ret = device_power_release_lock(POWER_LOCK_CPU);
157 if (ret != DEVICE_ERROR_NONE)
158 _E("Failed to release power(CPU) (%d)", ret);
162 static char *get_new_request_id(pid_t pid)
165 snprintf(id, sizeof(id), "%d_%lu", pid, time(NULL));
169 static int notice_power_lock_expired(void)
178 req_id = get_new_request_id(pid);
180 _E("Failed to get request id");
185 ret = dbus_method_async_with_reply(
187 DEVICED_PATH_DISPLAY,
188 DEVICED_INTERFACE_DISPLAY,
189 "LockTimeoutExpired",
191 notice_lock_expired_done,
195 _E("Failed to notice power lock expired (%d)", ret);
199 request_id_list = g_list_append(request_id_list, req_id);
200 _I("request ID %s is added", req_id);
205 static gboolean padding_timeout_expired(gpointer data)
210 _I("Padding timeout expired");
212 remove_padding_timeout();
214 ret = tracker_get_power_lock_ref(&ref);
215 if (ret != TRACKER_ERROR_NONE) {
216 _E("Failed to get reference count of power lock");
220 _I("reference count of power lock is (%d)", ref);
222 _I("Power Lock continue (Reference count > 0 !!)");
223 return G_SOURCE_REMOVE;
226 ret = tracker_get_power_lock_total(&count);
227 if (ret != TRACKER_ERROR_NONE) {
228 _E("Failed to get total count of power lock(%d)", ret);
232 if (count != prev_count) {
233 _I("Power Lock continue (Total reference count increased !!)");
234 return G_SOURCE_REMOVE;
238 ret = notice_power_lock_expired();
240 _E("Failed to launch power lock expired popup (%d)", ret);
241 return G_SOURCE_CONTINUE;
244 remove_off_lock_timeout();
246 return G_SOURCE_REMOVE;
249 static void add_padding_timeout(void)
253 remove_padding_timeout();
255 _I("Padding timeout handler added");
257 id = g_timeout_add(lock_timeout.padding,
258 padding_timeout_expired, NULL);
260 padding_timeout = id;
262 _E("Failed to add timeout for padding time");
265 static gboolean off_lock_timeout_expired(gpointer data)
269 _I("Power lock timeout expired");
271 ret = tracker_get_power_lock_ref(&ref);
272 if (ret != TRACKER_ERROR_NONE) {
273 _E("Failed to get reference count of power lock(%d)", ret);
274 remove_off_lock_timeout();
275 return G_SOURCE_REMOVE;
278 _I("reference count of power lock is (%d)", ref);
282 add_padding_timeout();
284 ret = tracker_get_power_lock_total(&prev_count);
285 if (ret != TRACKER_ERROR_NONE)
286 _E("Failed to get total count of power lock(%d)", ret);
289 return G_SOURCE_CONTINUE;
292 static void add_off_lock_timeout(void)
296 if (!TIZEN_FEATURE_TRACKER)
299 remove_off_lock_timeout();
300 remove_padding_timeout();
302 _I("Power lock timeout handler added");
304 id = g_timeout_add(lock_timeout.release,
305 off_lock_timeout_expired, NULL);
307 off_lock_timeout = id;
309 _E("Failed to add Power Lock timeout handler");
312 static void lock_cb(void *data, GVariant *result, GError *err)
317 _E("no message : %s", err->message); //LCOV_EXCL_LINE
321 g_variant_get(result, "(i)", &ret);
322 _D("%s-%s : %d", DEVICED_INTERFACE_DISPLAY, METHOD_LOCK_STATE, ret);
325 remove_off_lock_timeout();
328 static int lock_state(display_state_e state, unsigned int flag, int timeout_ms)
331 char str_timeout[32];
334 arr[0] = get_state_str(state);
338 if (flag & GOTO_STATE_NOW)
339 arr[1] = STR_GOTOSTATENOW;
341 arr[1] = STR_STAYCURSTATE;
343 if (flag & HOLD_KEY_BLOCK)
344 arr[2] = STR_HOLDKEYBLOCK;
345 else if (flag & STANDBY_MODE)
346 arr[2] = STR_STANDBYMODE;
350 snprintf(str_timeout, sizeof(str_timeout), "%d", -1);
351 arr[3] = str_timeout;
352 ret = dbus_method_sync(DEVICED_BUS_NAME,
353 DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
354 METHOD_LOCK_STATE, "sssi", arr);
355 if (ret == -EACCES || ret == -ECOMM || ret == -EPERM)
358 snprintf(str_timeout, sizeof(str_timeout), "%d", timeout_ms);
359 arr[3] = str_timeout;
361 return dbus_method_async_with_reply(DEVICED_BUS_NAME,
362 DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
363 METHOD_LOCK_STATE, "sssi", arr, lock_cb, -1, NULL);
366 static void unlock_cb(void *data, GVariant *result, GError *err)
371 _E("no message : %s", err->message); //LCOV_EXCL_LINE
375 g_variant_get(result, "(i)", &ret);
376 _D("%s-%s : %d", DEVICED_INTERFACE_DISPLAY, METHOD_UNLOCK_STATE, ret);
379 static int unlock_state(display_state_e state, unsigned int flag)
386 ret = dbus_method_sync(DEVICED_BUS_NAME,
387 DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
388 METHOD_UNLOCK_STATE, "ss", arr);
389 if (ret == -EACCES || ret == -ECOMM || ret == -EPERM)
392 arr[0] = get_state_str(state);
396 if (flag == PM_SLEEP_MARGIN)
397 arr[1] = STR_SLEEP_MARGIN;
398 else if (flag == PM_RESET_TIMER)
399 arr[1] = STR_RESET_TIMER;
400 else if (flag == PM_KEEP_TIMER)
401 arr[1] = STR_KEEP_TIMER;
405 return dbus_method_async_with_reply(DEVICED_BUS_NAME,
406 DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
407 METHOD_UNLOCK_STATE, "ss", arr, unlock_cb, -1, NULL);
410 int device_power_request_lock(power_lock_e type, int timeout_ms)
415 return DEVICE_ERROR_INVALID_PARAMETER;
417 if (type == POWER_LOCK_CPU) {
418 ret = lock_state(DISPLAY_STATE_SCREEN_OFF, STAY_CUR_STATE, timeout_ms);
420 (timeout_ms == 0 || timeout_ms > lock_timeout.release))
421 add_off_lock_timeout();
422 } else if (type == POWER_LOCK_DISPLAY) {
423 _W("DEPRECATION WARNING: This power lock enum is deprecated and will be removed from next release. Use efl_util_set_window_screen_mode() instead.");
424 ret = lock_state(DISPLAY_STATE_NORMAL, STAY_CUR_STATE, timeout_ms);
425 } else if (type == POWER_LOCK_DISPLAY_DIM) {
426 _W("DEPRECATION WARNING: This power lock enum is deprecated and will be removed from next release. Use efl_util_set_window_screen_mode() instead.");
427 ret = lock_state(DISPLAY_STATE_SCREEN_DIM, STAY_CUR_STATE, timeout_ms);
429 return DEVICE_ERROR_INVALID_PARAMETER;
431 return errno_to_device_error(ret);
434 int device_power_release_lock(power_lock_e type)
438 if (type == POWER_LOCK_CPU) {
439 ret = unlock_state(DISPLAY_STATE_SCREEN_OFF, PM_SLEEP_MARGIN);
441 remove_off_lock_timeout();
442 remove_padding_timeout();
444 } else if (type == POWER_LOCK_DISPLAY) {
445 _W("DEPRECATION WARNING: This power lock enum is deprecated and will be removed from next release. Use efl_util_set_window_screen_mode() instead.");
446 ret = unlock_state(DISPLAY_STATE_NORMAL, PM_KEEP_TIMER);
447 } else if (type == POWER_LOCK_DISPLAY_DIM) {
448 _W("DEPRECATION WARNING: This power lock enum is deprecated and will be removed from next release. Use efl_util_set_window_screen_mode() instead.");
449 ret = unlock_state(DISPLAY_STATE_SCREEN_DIM, PM_KEEP_TIMER);
451 return DEVICE_ERROR_INVALID_PARAMETER;
453 return errno_to_device_error(ret);
456 int device_power_wakeup(bool dim)
458 _W("DEPRECATION WARNING: device_power_wakeup() is deprecated and will be removed from next release.");
460 return device_display_change_state(DISPLAY_STATE_SCREEN_DIM);
462 return device_display_change_state(DISPLAY_STATE_NORMAL);
465 //LCOV_EXCL_START Not available to test(Reboot during TCT)
466 int device_power_reboot(const char *reason)
473 arr[0] = TYPE_REBOOT;
474 arr[1] = (char *)reason;
475 method = METHOD_REBOOT_WITH_OPTION;
478 arr[0] = REBOOT_REASON_NONE;
479 method = METHOD_REBOOT;
483 ret = dbus_method_sync(DEVICED_BUS_NAME,
485 DEVICED_INTERFACE_REBOOT,
487 return errno_to_device_error(ret);
491 static int power_load_config(struct parse_result *result, void *data)
498 if (strncmp(result->section, "Power", 6))
501 value = strtoul(result->value, NULL, 10);
505 if (!strncmp(result->name, "LockTimeout", 12)) {
506 _I("Power Lock Auto Release Timeout: %ld msec", value);
507 lock_timeout.release = value;
508 } else if (!strncmp(result->name, "LockPaddingTimeout", 12)) {
509 _I("Power Lock Auto Release Padding Timeout: %ld msec", value);
510 lock_timeout.padding = value;
516 static void __CONSTRUCTOR__ power_init(void)
520 ret = config_parse(POWER_CONF, power_load_config, NULL);
522 _E("Failed to load config file (%d)", ret);