From 982e0040a8ed197ea2a35c05052ae3bacd2f6068 Mon Sep 17 00:00:00 2001 From: INSUN PYO Date: Tue, 3 Mar 2020 09:06:06 +0900 Subject: [PATCH 01/16] Add more robust usb error handling The extcon uvent handler usb_state_changed() handles errors for usb connect/disconnect, but adds additional exception handling code for more robust usb error handling. Change-Id: I6c79fa99078ec71a19a2a72a94d28d31c8b9571f --- src/usb/usb-state.c | 4 ++-- src/usb/usb.c | 12 ++++++++++++ 2 files changed, 14 insertions(+), 2 deletions(-) diff --git a/src/usb/usb-state.c b/src/usb/usb-state.c index 5349dd3..3bb666d 100644 --- a/src/usb/usb-state.c +++ b/src/usb/usb-state.c @@ -168,8 +168,8 @@ void usb_state_retrieve_selected_mode(void) * Tizen has no way of having different vconf value in engineer mode and user mode. * So, alternatively, always enable SDB in engineer mode. * - * Expected default sel_mode value in vconf in engineer mode: 1 (MTP + ACM) - * Expected default sel_mode value in vconf in user mode: 2 (MTP + ACM + SDB) + * Expected default sel_mode value in vconf in user mode: 1 (MTP + ACM) + * Expected default sel_mode value in vconf in engineer mode: 2 (MTP + ACM + SDB) */ #ifdef ENGINEER_MODE _I("Engineer mode. usb selected mode 0x%x, debug state %d", usb_selected_mode, get_usb_debug_state()); diff --git a/src/usb/usb.c b/src/usb/usb.c index 5a84d95..a83e995 100644 --- a/src/usb/usb.c +++ b/src/usb/usb.c @@ -317,6 +317,12 @@ static int usb_connected(void) int ret; unsigned int mode = usb_state_get_selected_mode(); + /* Error handling that should never occur. */ + if (usb_state_get_connection() == USB_CONNECTED) { + _E("Fatal: usb cable is already connected"); + return -EINVAL; + } + usb_state_update_state(USB_CONNECTED, USB_FUNCTION_NONE); ret = usb_enable(mode); @@ -330,6 +336,12 @@ static int usb_connected(void) static int usb_disconnected(void) { + /* Error handling that should never occur. */ + if (usb_state_get_connection() == USB_DISCONNECTED) { + _E("Fatal: usb cable is already disconnected"); + return -EINVAL; + } + usb_state_update_state(USB_DISCONNECTED, USB_FUNCTION_NONE); return usb_disable(); -- 2.7.4 From 58f0f01e0d04d2a6f275097738eb4abd9f887b9c Mon Sep 17 00:00:00 2001 From: INSUN PYO Date: Tue, 3 Mar 2020 11:42:50 +0900 Subject: [PATCH 02/16] Add usb configuration exception handling code If an error occurs during usb configuration, change the usb current mode to USB_FUNCTION_NONE. The meaning of usb current mode is that usb is working correctly. If any error occurs, USB operation is not guaranteed. The value of usb current mode should not have a meaningless value and should have USB_FUNCTION_NONE. Change-Id: Ia882f517fe696a03cf1a39f97b382383d970e9d5 --- src/usb/usb.c | 62 +++++++++++++++++++++++++++++++++++++++++------------------ 1 file changed, 43 insertions(+), 19 deletions(-) diff --git a/src/usb/usb.c b/src/usb/usb.c index a83e995..8ad5c7d 100644 --- a/src/usb/usb.c +++ b/src/usb/usb.c @@ -236,8 +236,10 @@ static int usb_change_gadget(unsigned mode) struct usb_gadget *gadget; struct usb_gadget_id gadget_id; - if (!gadget_translator || !usb_client) - goto no_hal; + if (!gadget_translator || !usb_client) { + ret = -ENODEV; + goto out; + } memset(&gadget_id, 0, sizeof(gadget_id)); gadget_id.function_mask = mode; @@ -245,7 +247,7 @@ static int usb_change_gadget(unsigned mode) ret = gadget_translator->id_to_gadget(&gadget_id, &gadget); if (ret) { _E("Unable to translate id into gadget: %d", ret); - return ret; + goto out; } usb_client->disable(usb_client); @@ -253,16 +255,17 @@ static int usb_change_gadget(unsigned mode) gadget_translator->cleanup_gadget(gadget); if (ret) { _E("Unable to configure gadget: %d", ret); - return ret; + goto out; } _I("USB gadget changed to %d.", mode); return ret; -no_hal: +out: /* TODO. Maybe some default action here? */ - return -ENODEV; + usb_state_set_current_mode(USB_FUNCTION_NONE); /* because usb does not work properly */ + return ret; } static int usb_enable(unsigned int mode) @@ -271,7 +274,8 @@ static int usb_enable(unsigned int mode) if (usb_state_get_connection() != USB_CONNECTED) { _E("Failed to enable usb gadget (USB cable is not connected)."); - return -ENOTSUP; + ret = -ENOTSUP; + goto out; } if (usb_state_get_current_mode() != USB_FUNCTION_NONE) @@ -280,7 +284,7 @@ static int usb_enable(unsigned int mode) ret = usb_config_enable(); if (ret < 0) { _E("Failed to enable usb config: %d", ret); - return ret; + goto out; } usb_state_update_state(USB_CONNECTED, mode); @@ -289,6 +293,10 @@ static int usb_enable(unsigned int mode) disp_plgn.pm_lock_internal(INTERNAL_LOCK_USB, LCD_OFF, STAY_CUR_STATE, 0); return 0; + +out: + usb_state_set_current_mode(USB_FUNCTION_NONE); /* because usb does not work properly */ + return ret; } static int usb_disable(void) @@ -303,13 +311,16 @@ static int usb_disable(void) } ret = usb_config_disable(); - if (ret != 0) + if (ret != 0) { + usb_state_set_current_mode(USB_FUNCTION_NONE); /* because usb does not work properly */ _E("Failed to disable usb config: %d", ret); + /* You have to keep going to unlock disp_plgn.pm_unlock_internal */ + } if (disp_plgn.pm_unlock_internal) disp_plgn.pm_unlock_internal(INTERNAL_LOCK_USB, LCD_OFF, STAY_CUR_STATE); - return 0; + return ret; } static int usb_connected(void) @@ -348,35 +359,48 @@ static int usb_disconnected(void) } /* Called by dbus signal and vconf change(tethering, debug mode) */ -int usb_change_mode(unsigned mode) +int usb_change_mode(unsigned new_mode) { int ret; - unsigned int curr = usb_state_get_current_mode(); + const unsigned int curr_mode = usb_state_get_current_mode(); + const unsigned int prev_mode = usb_state_get_selected_mode(); - if (curr != USB_FUNCTION_NONE) { - ret = usb_disable(); + _I("usb change mode (0x%x) -> (0x%x), current running mode 0x%x", prev_mode, new_mode, curr_mode); + + /* + * Even if the usb cable is plugged in, the current mode may be NULL due to usb fail. + * So to find out which mode you are in, you should use the current mode, not the selected mode. + */ + if (curr_mode != USB_FUNCTION_NONE) { + ret = usb_disable(); /* Need to clean up because usb_change_gadget() also do usb_client->disable() */ if (ret < 0) { _E("Failed to disable current usb mode."); return ret; } } - ret = usb_change_gadget(mode); + /* + * You should always change the gadget once when the usb mode is changed. + * In this state, usb_enable() is called when the usb cable is connected. + * A usb_enable() is called when the usb cable is disconnected. + */ + ret = usb_change_gadget(new_mode); if (ret < 0) { _E("Failed to change gadget: %d", ret); - mode = usb_state_get_selected_mode(); + return ret; } - (void)usb_state_set_selected_mode(mode); - if (usb_state_get_connection() == USB_CONNECTED) { - ret = usb_enable(mode); + ret = usb_enable(new_mode); if (ret < 0) { _E("Failed to enable usb mode: %d", ret); return ret; } } + /* If you success to change the runtime usb configuration, do change the selected mode. */ + (void)usb_state_set_selected_mode(new_mode); + return 0; } -- 2.7.4 From fd2eada252ab35dbf64abeb64e75fadb4fd0658a Mon Sep 17 00:00:00 2001 From: INSUN PYO Date: Tue, 3 Mar 2020 14:09:39 +0900 Subject: [PATCH 03/16] Refactoring usb_state_update_state #2 Reimplemented by separating usb_state_set_connection() from usb_state_update_state(). A usb_state_set_connection() is olny changed when the usb cable is connected or disconnected. Change-Id: Ib2f9ca0eb12cb60e9f50f5badcedacaa71f8663b --- src/usb/usb-state.c | 4 +--- src/usb/usb.c | 16 +++++++++------- src/usb/usb.h | 4 +++- 3 files changed, 13 insertions(+), 11 deletions(-) diff --git a/src/usb/usb-state.c b/src/usb/usb-state.c index 3bb666d..8411559 100644 --- a/src/usb/usb-state.c +++ b/src/usb/usb-state.c @@ -245,7 +245,7 @@ extcon_usb_state_e usb_state_get_connection(void) return usb_connection; } -static void usb_state_set_connection(extcon_usb_state_e conn) +void usb_state_set_connection(extcon_usb_state_e conn) { usb_connection = conn; } @@ -334,8 +334,6 @@ void usb_state_update_state(extcon_usb_state_e state, unsigned int mode) { change_usb_state_notification_handler(mode); - usb_state_set_connection(state); - send_usb_state_changed_event(state, mode); (void)usb_state_set_current_mode(mode); diff --git a/src/usb/usb.c b/src/usb/usb.c index 8ad5c7d..911a4ca 100644 --- a/src/usb/usb.c +++ b/src/usb/usb.c @@ -258,7 +258,7 @@ static int usb_change_gadget(unsigned mode) goto out; } - _I("USB gadget changed to %d.", mode); + _I("USB gadget changed to 0x%x", mode); return ret; @@ -268,16 +268,11 @@ out: return ret; } +/* Precondition: USB_CONNECTED, USB_FUNCTION_NONE */ static int usb_enable(unsigned int mode) { int ret; - if (usb_state_get_connection() != USB_CONNECTED) { - _E("Failed to enable usb gadget (USB cable is not connected)."); - ret = -ENOTSUP; - goto out; - } - if (usb_state_get_current_mode() != USB_FUNCTION_NONE) usb_state_update_state(USB_CONNECTED, USB_FUNCTION_NONE); @@ -299,6 +294,7 @@ out: return ret; } +/* Precondition: N/A */ static int usb_disable(void) { int ret; @@ -323,6 +319,7 @@ static int usb_disable(void) return ret; } +/* Precondition: USB_DISCONNECTED */ static int usb_connected(void) { int ret; @@ -334,6 +331,7 @@ static int usb_connected(void) return -EINVAL; } + usb_state_set_connection(USB_CONNECTED); usb_state_update_state(USB_CONNECTED, USB_FUNCTION_NONE); ret = usb_enable(mode); @@ -345,6 +343,7 @@ static int usb_connected(void) return 0; } +/* Precondition: USB_CONNECTED */ static int usb_disconnected(void) { /* Error handling that should never occur. */ @@ -353,6 +352,7 @@ static int usb_disconnected(void) return -EINVAL; } + usb_state_set_connection(USB_DISCONNECTED); usb_state_update_state(USB_DISCONNECTED, USB_FUNCTION_NONE); return usb_disable(); @@ -500,6 +500,8 @@ static void usb_exit(void *data) { remove_usb_debug_handler(); remove_usb_tethering_handler(); + + usb_state_set_connection(USB_DISCONNECTED); usb_state_update_state(USB_DISCONNECTED, USB_FUNCTION_NONE); unregister_udev_uevent_control(&uh); diff --git a/src/usb/usb.h b/src/usb/usb.h index 1b620be..517edd8 100644 --- a/src/usb/usb.h +++ b/src/usb/usb.h @@ -61,13 +61,15 @@ int usb_change_mode(unsigned int mode); void usb_state_update_state(extcon_usb_state_e state, unsigned int mode); void usb_state_retrieve_selected_mode(void); -//char *usb_state_get_mode_str(unsigned int mode, char *str, size_t len); + unsigned int usb_state_get_selected_mode(void); int usb_state_set_selected_mode(unsigned int mode); + unsigned int usb_state_get_current_mode(void); int usb_state_set_current_mode(unsigned int mode); extcon_usb_state_e usb_state_get_connection(void); +void usb_state_set_connection(extcon_usb_state_e conn); /* dbus methods/signals (usb-dbus.c) */ enum { -- 2.7.4 From 5728cd49ed0654dfe235a45f602553401a7686fe Mon Sep 17 00:00:00 2001 From: Youngjae Cho Date: Tue, 3 Mar 2020 14:36:40 +0900 Subject: [PATCH 04/16] Delete critical-log for pmlock/unlock Change-Id: Ia09f99ad4a94adc5e2272cf6650c7832910e07a2 Signed-off-by: Youngjae Cho --- plugins/iot/display/core.c | 4 ++-- plugins/mobile/display/core.c | 4 ++-- plugins/tv/display/core.c | 4 ++-- plugins/wearable/display/core.c | 4 ++-- 4 files changed, 8 insertions(+), 8 deletions(-) diff --git a/plugins/iot/display/core.c b/plugins/iot/display/core.c index 33265e1..bed8f14 100644 --- a/plugins/iot/display/core.c +++ b/plugins/iot/display/core.c @@ -1462,7 +1462,7 @@ static void proc_condition_lock(PMMsg *data) if (state == S_LCDOFF) set_process_active(true, pid); - CRITICAL_LOG("[%s] locked by %5d with %u ms", states[state].name, pid, data->timeout); + _I("[%s] locked by %5d with %u ms", states[state].name, pid, data->timeout); /* for debug */ if (state == S_LCDOFF) lock_type = PM_LCDOFF_STR; @@ -1514,7 +1514,7 @@ static void proc_condition_unlock(PMMsg *data) if (state == S_LCDOFF) set_process_active(false, pid); - CRITICAL_LOG("[%s] unlocked by %5d", states[state].name, pid); + _I("[%s] unlocked by %5d", states[state].name, pid); /* for debug */ if (state == S_LCDOFF) lock_type = PM_LCDOFF_STR; diff --git a/plugins/mobile/display/core.c b/plugins/mobile/display/core.c index 163a1f0..5ff6e16 100644 --- a/plugins/mobile/display/core.c +++ b/plugins/mobile/display/core.c @@ -1472,7 +1472,7 @@ static void proc_condition_lock(PMMsg *data) if (state == S_LCDOFF) set_process_active(true, pid); - CRITICAL_LOG("[%s] locked by %5d with %u ms", states[state].name, pid, data->timeout); + _I("[%s] locked by %5d with %u ms", states[state].name, pid, data->timeout); /* for debug */ if (state == S_LCDOFF) lock_type = PM_LCDOFF_STR; @@ -1524,7 +1524,7 @@ static void proc_condition_unlock(PMMsg *data) if (state == S_LCDOFF) set_process_active(false, pid); - CRITICAL_LOG("[%s] unlocked by %5d", states[state].name, pid); + _I("[%s] unlocked by %5d", states[state].name, pid); /* for debug */ if (state == S_LCDOFF) lock_type = PM_LCDOFF_STR; diff --git a/plugins/tv/display/core.c b/plugins/tv/display/core.c index facb73f..fd131bf 100644 --- a/plugins/tv/display/core.c +++ b/plugins/tv/display/core.c @@ -1459,7 +1459,7 @@ static void proc_condition_lock(PMMsg *data) if (state == S_LCDOFF) set_process_active(true, pid); - CRITICAL_LOG("[%s] locked by %5d with %u ms", states[state].name, pid, data->timeout); + _I("[%s] locked by %5d with %u ms", states[state].name, pid, data->timeout); /* for debug */ if (state == S_LCDOFF) lock_type = PM_LCDOFF_STR; @@ -1511,7 +1511,7 @@ static void proc_condition_unlock(PMMsg *data) if (state == S_LCDOFF) set_process_active(false, pid); - CRITICAL_LOG("[%s] unlocked by %5d", states[state].name, pid); + _I("[%s] unlocked by %5d", states[state].name, pid); /* for debug */ if (state == S_LCDOFF) lock_type = PM_LCDOFF_STR; diff --git a/plugins/wearable/display/core.c b/plugins/wearable/display/core.c index 0e62786..2b88c42 100644 --- a/plugins/wearable/display/core.c +++ b/plugins/wearable/display/core.c @@ -1488,7 +1488,7 @@ static void proc_condition_lock(PMMsg *data) if (state == S_LCDOFF) set_process_active(true, pid); - CRITICAL_LOG("[%s] locked by %5d with %u ms", states[state].name, pid, data->timeout); + _I("[%s] locked by %5d with %u ms", states[state].name, pid, data->timeout); /* for debug */ if (state == S_LCDOFF) lock_type = PM_LCDOFF_STR; @@ -1540,7 +1540,7 @@ static void proc_condition_unlock(PMMsg *data) if (state == S_LCDOFF) set_process_active(false, pid); - CRITICAL_LOG("[%s] unlocked by %5d", states[state].name, pid); + _I("[%s] unlocked by %5d", states[state].name, pid); /* for debug */ if (state == S_LCDOFF) lock_type = PM_LCDOFF_STR; -- 2.7.4 From a8ee05519797725dfed6d91f22a97d431249ba88 Mon Sep 17 00:00:00 2001 From: INSUN PYO Date: Tue, 3 Mar 2020 15:02:40 +0900 Subject: [PATCH 05/16] Refactoring usb_state_update_state #3 Reimplemented by separating usb_state_set_current_mode() from usb_state_update_state(). A usb_state_set_current_mode() is olny changed when the usb gadget is enabled or disabled. Change-Id: I0baaf031f52d2417d9aef84d56ff4b0e4c394b5f --- src/usb/usb-dbus.c | 23 ----------------------- src/usb/usb-state.c | 2 -- src/usb/usb.c | 20 +++++++++----------- src/usb/usb.h | 1 - 4 files changed, 9 insertions(+), 37 deletions(-) diff --git a/src/usb/usb-dbus.c b/src/usb/usb-dbus.c index 402c3e9..407dd4c 100644 --- a/src/usb/usb-dbus.c +++ b/src/usb/usb-dbus.c @@ -95,29 +95,6 @@ void broadcast_usb_state_changed(void) _E("Failed to send dbus signal."); } -void broadcast_usb_mode_changed(void) -{ - int ret; - unsigned int mode; - static unsigned int prev_mode = UINT_MAX; - - mode = usb_state_get_current_mode(); - if (mode == prev_mode) - return; - - prev_mode = mode; - - _I("USB mode(%u) changed.", mode); - - ret = dbus_handle_emit_dbus_signal(NULL, - DEVICED_PATH_USB, - DEVICED_INTERFACE_USB, - SIGNAL_MODE_CHANGED, - g_variant_new("(u)", mode)); - if (ret < 0) - _E("Failed to send dbus signal(%s)", SIGNAL_MODE_CHANGED); -} - static void change_usb_client_mode(GDBusConnection *conn, const gchar *sender, const gchar *path, diff --git a/src/usb/usb-state.c b/src/usb/usb-state.c index 8411559..d9628ed 100644 --- a/src/usb/usb-state.c +++ b/src/usb/usb-state.c @@ -335,6 +335,4 @@ void usb_state_update_state(extcon_usb_state_e state, unsigned int mode) change_usb_state_notification_handler(mode); send_usb_state_changed_event(state, mode); - - (void)usb_state_set_current_mode(mode); } diff --git a/src/usb/usb.c b/src/usb/usb.c index 911a4ca..a2105b4 100644 --- a/src/usb/usb.c +++ b/src/usb/usb.c @@ -36,10 +36,8 @@ #include "usb-tethering.h" #include "usb-debug.h" -static struct usb_gadget_translator *gadget_translator; static struct usb_client *usb_client; - -struct extcon_ops extcon_usb_ops; +static struct usb_gadget_translator *gadget_translator; static struct usb_gadget_translator *gadget_translator_probe(void) { @@ -264,7 +262,7 @@ static int usb_change_gadget(unsigned mode) out: /* TODO. Maybe some default action here? */ - usb_state_set_current_mode(USB_FUNCTION_NONE); /* because usb does not work properly */ + (void)usb_state_set_current_mode(USB_FUNCTION_NONE); /* because usb does not work properly */ return ret; } @@ -273,15 +271,13 @@ static int usb_enable(unsigned int mode) { int ret; - if (usb_state_get_current_mode() != USB_FUNCTION_NONE) - usb_state_update_state(USB_CONNECTED, USB_FUNCTION_NONE); - ret = usb_config_enable(); if (ret < 0) { _E("Failed to enable usb config: %d", ret); goto out; } + (void)usb_state_set_current_mode(mode); usb_state_update_state(USB_CONNECTED, mode); if (disp_plgn.pm_lock_internal) @@ -290,7 +286,7 @@ static int usb_enable(unsigned int mode) return 0; out: - usb_state_set_current_mode(USB_FUNCTION_NONE); /* because usb does not work properly */ + (void)usb_state_set_current_mode(USB_FUNCTION_NONE); /* because usb does not work properly */ return ret; } @@ -306,11 +302,12 @@ static int usb_disable(void) usb_state_update_state(USB_DISCONNECTED, USB_FUNCTION_NONE); } + (void)usb_state_set_current_mode(USB_FUNCTION_NONE); /* run unconditionally */ + ret = usb_config_disable(); if (ret != 0) { - usb_state_set_current_mode(USB_FUNCTION_NONE); /* because usb does not work properly */ _E("Failed to disable usb config: %d", ret); - /* You have to keep going to unlock disp_plgn.pm_unlock_internal */ + /* Important: You have to keep going to unlock disp_plgn.pm_unlock_internal */ } if (disp_plgn.pm_unlock_internal) @@ -319,7 +316,7 @@ static int usb_disable(void) return ret; } -/* Precondition: USB_DISCONNECTED */ +/* Precondition: USB_DISCONNECTED (Implicitly contains USB_FUNCTION_NONE) */ static int usb_connected(void) { int ret; @@ -501,6 +498,7 @@ static void usb_exit(void *data) remove_usb_debug_handler(); remove_usb_tethering_handler(); + (void)usb_state_set_current_mode(USB_FUNCTION_NONE); usb_state_set_connection(USB_DISCONNECTED); usb_state_update_state(USB_DISCONNECTED, USB_FUNCTION_NONE); diff --git a/src/usb/usb.h b/src/usb/usb.h index 517edd8..35a712c 100644 --- a/src/usb/usb.h +++ b/src/usb/usb.h @@ -81,6 +81,5 @@ int usb_dbus_init(void); void broadcast_usb_config_enabled(int state); void broadcast_usb_state_changed(void); -void broadcast_usb_mode_changed(void); #endif /* __USB_CLIENT_H__ */ -- 2.7.4 From 96dddf29adf6f0a0ae5cae3c88b04e512d18dc26 Mon Sep 17 00:00:00 2001 From: INSUN PYO Date: Tue, 3 Mar 2020 06:57:59 +0000 Subject: [PATCH 06/16] Revert "Add more robust usb error handling" This reverts commit 982e0040a8ed197ea2a35c05052ae3bacd2f6068. Change-Id: I634d301d2b22a905e8c2d014076f847eb1b3fa73 --- src/usb/usb.c | 12 ------------ 1 file changed, 12 deletions(-) diff --git a/src/usb/usb.c b/src/usb/usb.c index a2105b4..824d4b6 100644 --- a/src/usb/usb.c +++ b/src/usb/usb.c @@ -322,12 +322,6 @@ static int usb_connected(void) int ret; unsigned int mode = usb_state_get_selected_mode(); - /* Error handling that should never occur. */ - if (usb_state_get_connection() == USB_CONNECTED) { - _E("Fatal: usb cable is already connected"); - return -EINVAL; - } - usb_state_set_connection(USB_CONNECTED); usb_state_update_state(USB_CONNECTED, USB_FUNCTION_NONE); @@ -343,12 +337,6 @@ static int usb_connected(void) /* Precondition: USB_CONNECTED */ static int usb_disconnected(void) { - /* Error handling that should never occur. */ - if (usb_state_get_connection() == USB_DISCONNECTED) { - _E("Fatal: usb cable is already disconnected"); - return -EINVAL; - } - usb_state_set_connection(USB_DISCONNECTED); usb_state_update_state(USB_DISCONNECTED, USB_FUNCTION_NONE); -- 2.7.4 From b3b96cb7407e32d431762b39588f7d6da9521234 Mon Sep 17 00:00:00 2001 From: Youngjae Cho Date: Tue, 3 Mar 2020 17:34:04 +0900 Subject: [PATCH 07/16] Add critical-log for long lasting lock Check locks every 10 minutes. (disp_plgn.lockcheck_timeout = 600) Change-Id: I6cee6df8e46f947131a30c46c373332d456134dd Signed-off-by: Youngjae Cho --- plugins/iot/display/core.c | 33 ++++++++++++++++++++++----------- plugins/mobile/display/core.c | 33 ++++++++++++++++++++++----------- plugins/tv/display/core.c | 33 ++++++++++++++++++++++----------- plugins/wearable/display/core.c | 31 +++++++++++++++++++++---------- 4 files changed, 87 insertions(+), 43 deletions(-) diff --git a/plugins/iot/display/core.c b/plugins/iot/display/core.c index bed8f14..27370fd 100644 --- a/plugins/iot/display/core.c +++ b/plugins/iot/display/core.c @@ -846,21 +846,31 @@ static gboolean del_off_cond(void *data) static void pmlock_check_cb(GVariant *var, void *user_data, GError *err) { pid_t pid; - int ret, state; + int ret, detected; char *app_id; + enum state_t state = (enum state_t) user_data; + PmLockNode *node; + time_t now; + double diff; if (!var) return; - if (!dh_get_param_from_var(var, "(iis)", &pid, &state, &app_id)) { - _E("Failed to notify low: no message(%s)", g_variant_get_type_string(var)); + g_variant_get(var, "(iis)", &pid, &detected, &app_id); + + if (!detected) goto out; - } - if (!state) - return; + node = find_node(state, pid); + if (!node) + goto out; + + time(&now); + diff = difftime(now, node->time); + + CRITICAL_LOG("%s(%d) has held %s lock for a long time(%.0f s).", + app_id, pid, states[state].name + 2, diff); - _W("%s(%d) was requested pmlock for a long time.", app_id, pid); ret = dbus_handle_emit_dbus_signal(NULL, DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY, @@ -870,14 +880,15 @@ static void pmlock_check_cb(GVariant *var, void *user_data, GError *err) _E("Failed to send dbus pmlock_expired"); out: + g_free(app_id); g_variant_unref(var); } /* * Any process is possible many time lock, deviced can not know malicious - * or good process. so infinity or more then 1 min lock process, deviced - * will be checked it to resoured. And then, it will be asked quit or maintain to user. - */ + * or good process. so infinity or more then 10 min lock process, deviced + * will check it through resoured. And then, it will ask the user whether to quit or not. + */ static gboolean pmlock_check(void *data) { const char *arr[2]; @@ -934,7 +945,7 @@ static gboolean pmlock_check(void *data) RESOURCED_PATH_PROCESS, RESOURCED_INTERFACE_PROCESS, METHOD_APP_STATUS, - "is", arr, pmlock_check_cb, -1, NULL); + "is", arr, pmlock_check_cb, -1, (void *)(intptr_t)state); if (ret < 0) _E("Failed to call dbus method"); diff --git a/plugins/mobile/display/core.c b/plugins/mobile/display/core.c index 5ff6e16..db50295 100644 --- a/plugins/mobile/display/core.c +++ b/plugins/mobile/display/core.c @@ -855,21 +855,31 @@ static gboolean del_off_cond(void *data) static void pmlock_check_cb(GVariant *var, void *user_data, GError *err) { pid_t pid; - int ret, state; + int ret, detected; char *app_id; + enum state_t state = (enum state_t) user_data; + PmLockNode *node; + time_t now; + double diff; if (!var) return; - if (!dh_get_param_from_var(var, "(iis)", &pid, &state, &app_id)) { - _E("Failed to notify low: no message(%s)", g_variant_get_type_string(var)); + g_variant_get(var, "(iis)", &pid, &detected, &app_id); + + if (!detected) goto out; - } - if (!state) - return; + node = find_node(state, pid); + if (!node) + goto out; + + time(&now); + diff = difftime(now, node->time); + + CRITICAL_LOG("%s(%d) has held %s lock for a long time(%.0f s).", + app_id, pid, states[state].name + 2, diff); - _W("%s(%d) was requested pmlock for a long time.", app_id, pid); ret = dbus_handle_emit_dbus_signal(NULL, DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY, @@ -879,14 +889,15 @@ static void pmlock_check_cb(GVariant *var, void *user_data, GError *err) _E("Failed to send dbus pmlock_expired"); out: + g_free(app_id); g_variant_unref(var); } /* * Any process is possible many time lock, deviced can not know malicious - * or good process. so infinity or more then 1 min lock process, deviced - * will be checked it to resoured. And then, it will be asked quit or maintain to user. - */ + * or good process. so infinity or more then 10 min lock process, deviced + * will check it through resoured. And then, it will ask the user whether to quit or not. + */ static gboolean pmlock_check(void *data) { const char *arr[2]; @@ -940,7 +951,7 @@ static gboolean pmlock_check(void *data) RESOURCED_PATH_PROCESS, RESOURCED_INTERFACE_PROCESS, METHOD_APP_STATUS, - "is", arr, pmlock_check_cb, -1, NULL); + "is", arr, pmlock_check_cb, -1, (void *)(intptr_t)state); if (ret < 0) _E("Failed to call dbus method"); diff --git a/plugins/tv/display/core.c b/plugins/tv/display/core.c index fd131bf..da4f82c 100644 --- a/plugins/tv/display/core.c +++ b/plugins/tv/display/core.c @@ -846,21 +846,31 @@ static gboolean del_off_cond(void *data) static void pmlock_check_cb(GVariant *var, void *user_data, GError *err) { pid_t pid; - int ret, state; + int ret, detected; char *app_id; + enum state_t state = (enum state_t) user_data; + PmLockNode *node; + time_t now; + double diff; if (!var) return; - if (!dh_get_param_from_var(var, "(iis)", &pid, &state, &app_id)) { - _E("Failed to notify low: no message(%s)", g_variant_get_type_string(var)); + g_variant_get(var, "(iis)", &pid, &detected, &app_id); + + if (!detected) goto out; - } - if (!state) - return; + node = find_node(state, pid); + if (!node) + goto out; + + time(&now); + diff = difftime(now, node->time); + + CRITICAL_LOG("%s(%d) has held %s lock for a long time(%.0f s).", + app_id, pid, states[state].name + 2, diff); - _W("%s(%d) was requested pmlock for a long time.", app_id, pid); ret = dbus_handle_emit_dbus_signal(NULL, DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY, @@ -870,14 +880,15 @@ static void pmlock_check_cb(GVariant *var, void *user_data, GError *err) _E("Failed to send dbus pmlock_expired"); out: + g_free(app_id); g_variant_unref(var); } /* * Any process is possible many time lock, deviced can not know malicious - * or good process. so infinity or more then 1 min lock process, deviced - * will be checked it to resoured. And then, it will be asked quit or maintain to user. - */ + * or good process. so infinity or more then 10 min lock process, deviced + * will check it through resoured. And then, it will ask the user whether to quit or not. + */ static gboolean pmlock_check(void *data) { const char *arr[2]; @@ -931,7 +942,7 @@ static gboolean pmlock_check(void *data) RESOURCED_PATH_PROCESS, RESOURCED_INTERFACE_PROCESS, METHOD_APP_STATUS, - "is", arr, pmlock_check_cb, -1, NULL); + "is", arr, pmlock_check_cb, -1, (void *)(intptr_t)state); if (ret < 0) _E("Failed to call dbus method"); diff --git a/plugins/wearable/display/core.c b/plugins/wearable/display/core.c index 2b88c42..7fb61ff 100644 --- a/plugins/wearable/display/core.c +++ b/plugins/wearable/display/core.c @@ -860,21 +860,31 @@ static gboolean del_off_cond(void *data) static void pmlock_check_cb(GVariant *var, void *user_data, GError *err) { pid_t pid; - int ret, state; + int ret, detected; char *app_id; + enum state_t state = (enum state_t) user_data; + PmLockNode *node; + time_t now; + double diff; if (!var) return; - if (!dh_get_param_from_var(var, "(iis)", &pid, &state, &app_id)) { - _E("Failed to notify low: no message(%s)", g_variant_get_type_string(var)); + g_variant_get(var, "(iis)", &pid, &detected, &app_id); + + if (!detected) goto out; - } - if (!state) - return; + node = find_node(state, pid); + if (!node) + goto out; + + time(&now); + diff = difftime(now, node->time); + + CRITICAL_LOG("%s(%d) has held %s lock for a long time(%.0f s).", + app_id, pid, states[state].name + 2, diff); - _W("%s(%d) was requested pmlock for a long time.", app_id, pid); ret = dbus_handle_emit_dbus_signal(NULL, DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY, @@ -884,13 +894,14 @@ static void pmlock_check_cb(GVariant *var, void *user_data, GError *err) _E("Failed to send dbus pmlock_expired"); out: + g_free(app_id); g_variant_unref(var); } /* * Any process is possible many time lock, deviced can not know malicious - * or good process. so infinity or more then 1 min lock process, deviced - * will be checked it to resoured. And then, it will be asked quit or maintain to user. + * or good process. so infinity or more then 10 min lock process, deviced + * will check it through resoured. And then, it will ask the user whether to quit or not. */ static gboolean pmlock_check(void *data) { @@ -945,7 +956,7 @@ static gboolean pmlock_check(void *data) RESOURCED_PATH_PROCESS, RESOURCED_INTERFACE_PROCESS, METHOD_APP_STATUS, - "is", arr, pmlock_check_cb, -1, NULL); + "is", arr, pmlock_check_cb, -1, (void *)(intptr_t)state); if (ret < 0) _E("Failed to call dbus method"); -- 2.7.4 From 84fa7a86c6d3e68f865e6b179e953adaadbb7d85 Mon Sep 17 00:00:00 2001 From: INSUN PYO Date: Wed, 4 Mar 2020 12:25:48 +0900 Subject: [PATCH 08/16] Refactoring usb_state_update_state #4 Reimplemented by separating send_usb_state_changed_event() from usb_state_update_state(). USB_DISCONNECTED : VCONFKEY_SYSMAN_USB_DISCONNECTED USB_CONNECTED + USB_FUNCTION_NONE : VCONFKEY_SYSMAN_USB_CONNECTED USB_CONNECTED + USB_FUNCTION_OOOO : VCONFKEY_SYSMAN_USB_AVAILABLE When connecting the usb cable : "disconnected"(previous value) -> "connected" -> "available" When disconnecting the usb cable : "available"(previous value) -> "dosconnected" When changing usb mode : "available"(previous value) -> "connected" -> "available" When USB cable is connected but USB initialization fails : It stays "connected" without going to "available" Change-Id: I8a9d84884388bb0dcf24f44735224c695d2f10ec --- src/usb/usb-state.c | 31 ++++++++++++++++++++----------- src/usb/usb.c | 14 +++++++++++--- src/usb/usb.h | 1 + 3 files changed, 32 insertions(+), 14 deletions(-) diff --git a/src/usb/usb-state.c b/src/usb/usb-state.c index d9628ed..158995d 100644 --- a/src/usb/usb-state.c +++ b/src/usb/usb-state.c @@ -304,18 +304,28 @@ static void change_usb_state_notification_handler(unsigned int mode) remove_notification_handler(); } -static void send_usb_state_changed_event(extcon_usb_state_e state, unsigned int mode) +/* + * USB_DISCONNECTED : VCONFKEY_SYSMAN_USB_DISCONNECTED + * USB_CONNECTED + USB_FUNCTION_NONE : VCONFKEY_SYSMAN_USB_CONNECTED + * USB_CONNECTED + USB_FUNCTION_OOOO : VCONFKEY_SYSMAN_USB_AVAILABLE + * + * When connecting the usb cable : "disconnected"(previous value) -> "connected" -> "available" + * When disconnecting the usb cable : "available"(previous value) -> "dosconnected" + * When changing usb mode : "available"(previous value) -> "connected" -> "available" + * + * When USB cable is connected but USB initialization fails : It stays "connected" without going to "available" + * + */ +void send_usb_state_changed_event(int status) { - int status; static int old_status = -1; - if (state == USB_CONNECTED) { - if (mode == USB_FUNCTION_NONE) - status = VCONFKEY_SYSMAN_USB_CONNECTED; - else - status = VCONFKEY_SYSMAN_USB_AVAILABLE; - } else - status = VCONFKEY_SYSMAN_USB_DISCONNECTED; + if ((status != VCONFKEY_SYSMAN_USB_CONNECTED) && + (status != VCONFKEY_SYSMAN_USB_AVAILABLE) && + (status != VCONFKEY_SYSMAN_USB_DISCONNECTED)) { + _E("Invalid usb state changed event (%d)", status); + return; + } if (old_status == status) return; @@ -327,12 +337,11 @@ static void send_usb_state_changed_event(extcon_usb_state_e state, unsigned int if (vconf_set_int(VCONFKEY_SYSMAN_USB_STATUS, status) != VCONF_OK) _E("Failed to set vconf value for usb status: %d", vconf_get_ext_errno()); + /* Caution: calls after vconf_set_int(VCONFKEY_SYSMAN_USB_STATUS) */ broadcast_usb_state_changed(); } void usb_state_update_state(extcon_usb_state_e state, unsigned int mode) { change_usb_state_notification_handler(mode); - - send_usb_state_changed_event(state, mode); } diff --git a/src/usb/usb.c b/src/usb/usb.c index 824d4b6..7a21af7 100644 --- a/src/usb/usb.c +++ b/src/usb/usb.c @@ -256,7 +256,7 @@ static int usb_change_gadget(unsigned mode) goto out; } - _I("USB gadget changed to 0x%x", mode); + _I("USB gadget changed to (0x%x)", mode); return ret; @@ -277,6 +277,7 @@ static int usb_enable(unsigned int mode) goto out; } + send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_AVAILABLE); (void)usb_state_set_current_mode(mode); usb_state_update_state(USB_CONNECTED, mode); @@ -302,6 +303,11 @@ static int usb_disable(void) usb_state_update_state(USB_DISCONNECTED, USB_FUNCTION_NONE); } + if (usb_state_get_connection() == USB_CONNECTED) + send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_CONNECTED); /* Transitions from available to connected */ + else + ; /* Do nothing: A send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_DISCONNECTED) has already called by caller */ + (void)usb_state_set_current_mode(USB_FUNCTION_NONE); /* run unconditionally */ ret = usb_config_disable(); @@ -323,6 +329,7 @@ static int usb_connected(void) unsigned int mode = usb_state_get_selected_mode(); usb_state_set_connection(USB_CONNECTED); + send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_CONNECTED); usb_state_update_state(USB_CONNECTED, USB_FUNCTION_NONE); ret = usb_enable(mode); @@ -338,19 +345,20 @@ static int usb_connected(void) static int usb_disconnected(void) { usb_state_set_connection(USB_DISCONNECTED); + send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_DISCONNECTED); usb_state_update_state(USB_DISCONNECTED, USB_FUNCTION_NONE); return usb_disable(); } /* Called by dbus signal and vconf change(tethering, debug mode) */ -int usb_change_mode(unsigned new_mode) +int usb_change_mode(unsigned int new_mode) { int ret; const unsigned int curr_mode = usb_state_get_current_mode(); const unsigned int prev_mode = usb_state_get_selected_mode(); - _I("usb change mode (0x%x) -> (0x%x), current running mode 0x%x", prev_mode, new_mode, curr_mode); + _I("usb change mode (0x%x) -> (0x%x), current running mode (0x%x)", prev_mode, new_mode, curr_mode); /* * Even if the usb cable is plugged in, the current mode may be NULL due to usb fail. diff --git a/src/usb/usb.h b/src/usb/usb.h index 35a712c..675ff91 100644 --- a/src/usb/usb.h +++ b/src/usb/usb.h @@ -58,6 +58,7 @@ void remove_usb_config(const struct usb_config_ops *ops); unsigned int get_mode_bitmap_from_vconf(int mode_v); int usb_change_mode(unsigned int mode); +void send_usb_state_changed_event(int status); void usb_state_update_state(extcon_usb_state_e state, unsigned int mode); void usb_state_retrieve_selected_mode(void); -- 2.7.4 From 9369a315115abbca2659ae485814559f6a23099d Mon Sep 17 00:00:00 2001 From: INSUN PYO Date: Wed, 4 Mar 2020 13:53:53 +0900 Subject: [PATCH 09/16] Refactoring usb_state_update_state #5 Reimplemented by separating change_usb_state_notification_handler() from usb_state_update_state(). A change_usb_state_notification_handler() is only changed when the usb gadget is enabled or disabled. Change-Id: I58a30bf3a41abe082ed5f91da2cddd232ed0c6e4 --- src/usb/usb-state.c | 6 +----- src/usb/usb.c | 17 +++++------------ src/usb/usb.h | 2 +- 3 files changed, 7 insertions(+), 18 deletions(-) diff --git a/src/usb/usb-state.c b/src/usb/usb-state.c index 158995d..c5a3913 100644 --- a/src/usb/usb-state.c +++ b/src/usb/usb-state.c @@ -296,7 +296,7 @@ static void remove_notification_handler(void) } } -static void change_usb_state_notification_handler(unsigned int mode) +void change_usb_state_notification_handler(unsigned int mode) { if (mode & USB_FUNCTION_MTP) add_notification_handler(); @@ -341,7 +341,3 @@ void send_usb_state_changed_event(int status) broadcast_usb_state_changed(); } -void usb_state_update_state(extcon_usb_state_e state, unsigned int mode) -{ - change_usb_state_notification_handler(mode); -} diff --git a/src/usb/usb.c b/src/usb/usb.c index 7a21af7..b926a74 100644 --- a/src/usb/usb.c +++ b/src/usb/usb.c @@ -279,7 +279,7 @@ static int usb_enable(unsigned int mode) send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_AVAILABLE); (void)usb_state_set_current_mode(mode); - usb_state_update_state(USB_CONNECTED, mode); + change_usb_state_notification_handler(mode); if (disp_plgn.pm_lock_internal) disp_plgn.pm_lock_internal(INTERNAL_LOCK_USB, LCD_OFF, STAY_CUR_STATE, 0); @@ -296,19 +296,13 @@ static int usb_disable(void) { int ret; - if (usb_state_get_current_mode() != USB_FUNCTION_NONE) { - if (usb_state_get_connection() == USB_CONNECTED) - usb_state_update_state(USB_CONNECTED, USB_FUNCTION_NONE); - else - usb_state_update_state(USB_DISCONNECTED, USB_FUNCTION_NONE); - } - if (usb_state_get_connection() == USB_CONNECTED) send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_CONNECTED); /* Transitions from available to connected */ else ; /* Do nothing: A send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_DISCONNECTED) has already called by caller */ (void)usb_state_set_current_mode(USB_FUNCTION_NONE); /* run unconditionally */ + change_usb_state_notification_handler(USB_FUNCTION_NONE); ret = usb_config_disable(); if (ret != 0) { @@ -330,7 +324,6 @@ static int usb_connected(void) usb_state_set_connection(USB_CONNECTED); send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_CONNECTED); - usb_state_update_state(USB_CONNECTED, USB_FUNCTION_NONE); ret = usb_enable(mode); if (ret < 0) { @@ -346,7 +339,6 @@ static int usb_disconnected(void) { usb_state_set_connection(USB_DISCONNECTED); send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_DISCONNECTED); - usb_state_update_state(USB_DISCONNECTED, USB_FUNCTION_NONE); return usb_disable(); } @@ -494,9 +486,10 @@ static void usb_exit(void *data) remove_usb_debug_handler(); remove_usb_tethering_handler(); - (void)usb_state_set_current_mode(USB_FUNCTION_NONE); usb_state_set_connection(USB_DISCONNECTED); - usb_state_update_state(USB_DISCONNECTED, USB_FUNCTION_NONE); + send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_DISCONNECTED); + (void)usb_state_set_current_mode(USB_FUNCTION_NONE); + change_usb_state_notification_handler(USB_FUNCTION_NONE); unregister_udev_uevent_control(&uh); usb_config_deinit(); diff --git a/src/usb/usb.h b/src/usb/usb.h index 675ff91..933b1be 100644 --- a/src/usb/usb.h +++ b/src/usb/usb.h @@ -59,7 +59,7 @@ unsigned int get_mode_bitmap_from_vconf(int mode_v); int usb_change_mode(unsigned int mode); void send_usb_state_changed_event(int status); -void usb_state_update_state(extcon_usb_state_e state, unsigned int mode); +void change_usb_state_notification_handler(unsigned int mode); void usb_state_retrieve_selected_mode(void); -- 2.7.4 From 41613081cf9bfc32bf5f126241a0da0e67f83c86 Mon Sep 17 00:00:00 2001 From: INSUN PYO Date: Wed, 4 Mar 2020 15:17:33 +0900 Subject: [PATCH 10/16] Rearrange display lock and unlock in the usb module If an error occurs during usb enable, do not acquire display lock. Target may enter sleep mode with the USB cable is connected To prevent this situation, acquire the lock when usb cable is connected, and release the lock when usb cable is disconnected. Change-Id: I9850e593957e182a415298eeb63361d09c21dc3a --- src/usb/usb.c | 40 +++++++++++++++++++++++++--------------- 1 file changed, 25 insertions(+), 15 deletions(-) diff --git a/src/usb/usb.c b/src/usb/usb.c index b926a74..581c0ae 100644 --- a/src/usb/usb.c +++ b/src/usb/usb.c @@ -228,6 +228,7 @@ no_hal: return -ENODEV; } +/* Precondition: USB_FUNCTION_NONE */ static int usb_change_gadget(unsigned mode) { int ret; @@ -261,7 +262,7 @@ static int usb_change_gadget(unsigned mode) return ret; out: - /* TODO. Maybe some default action here? */ + /* Although this function has a USB_FUNCTION_NONE precondition, it is to protect against coding mistakes. */ (void)usb_state_set_current_mode(USB_FUNCTION_NONE); /* because usb does not work properly */ return ret; } @@ -281,12 +282,10 @@ static int usb_enable(unsigned int mode) (void)usb_state_set_current_mode(mode); change_usb_state_notification_handler(mode); - if (disp_plgn.pm_lock_internal) - disp_plgn.pm_lock_internal(INTERNAL_LOCK_USB, LCD_OFF, STAY_CUR_STATE, 0); - return 0; out: + /* Although this function has a USB_FUNCTION_NONE precondition, it is to protect against coding mistakes. */ (void)usb_state_set_current_mode(USB_FUNCTION_NONE); /* because usb does not work properly */ return ret; } @@ -301,19 +300,16 @@ static int usb_disable(void) else ; /* Do nothing: A send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_DISCONNECTED) has already called by caller */ - (void)usb_state_set_current_mode(USB_FUNCTION_NONE); /* run unconditionally */ + (void)usb_state_set_current_mode(USB_FUNCTION_NONE); change_usb_state_notification_handler(USB_FUNCTION_NONE); ret = usb_config_disable(); - if (ret != 0) { + if (ret < 0) { _E("Failed to disable usb config: %d", ret); - /* Important: You have to keep going to unlock disp_plgn.pm_unlock_internal */ + return ret; } - if (disp_plgn.pm_unlock_internal) - disp_plgn.pm_unlock_internal(INTERNAL_LOCK_USB, LCD_OFF, STAY_CUR_STATE); - - return ret; + return 0; } /* Precondition: USB_DISCONNECTED (Implicitly contains USB_FUNCTION_NONE) */ @@ -322,12 +318,15 @@ static int usb_connected(void) int ret; unsigned int mode = usb_state_get_selected_mode(); + if (disp_plgn.pm_lock_internal) + disp_plgn.pm_lock_internal(INTERNAL_LOCK_USB, LCD_OFF, STAY_CUR_STATE, 0); + usb_state_set_connection(USB_CONNECTED); send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_CONNECTED); ret = usb_enable(mode); if (ret < 0) { - _E("Failed to enable usb gadget(%d): %d", mode, ret); + _E("Failed to enable usb gadget(0x%x): %d", mode, ret); return ret; } @@ -337,10 +336,21 @@ static int usb_connected(void) /* Precondition: USB_CONNECTED */ static int usb_disconnected(void) { + int ret; + usb_state_set_connection(USB_DISCONNECTED); send_usb_state_changed_event(VCONFKEY_SYSMAN_USB_DISCONNECTED); - return usb_disable(); + ret = usb_disable(); + if(ret < 0) { + _E("Failed to disable usb gadget: %d", ret); + /* Important: You have to keep going to unlock disp_plgn.pm_unlock_internal */ + } + + if (disp_plgn.pm_unlock_internal) + disp_plgn.pm_unlock_internal(INTERNAL_LOCK_USB, LCD_OFF, STAY_CUR_STATE); + + return ret; } /* Called by dbus signal and vconf change(tethering, debug mode) */ @@ -366,8 +376,8 @@ int usb_change_mode(unsigned int new_mode) /* * You should always change the gadget once when the usb mode is changed. - * In this state, usb_enable() is called when the usb cable is connected. - * A usb_enable() is called when the usb cable is disconnected. + * In this state, usb_enable() is called when the usb cable is connected + * and usb_disable() is called when the usb cable is disconnected. */ ret = usb_change_gadget(new_mode); if (ret < 0) { -- 2.7.4 From 61ed460b16ba7c09e652065d3c63c3e7a80d2de7 Mon Sep 17 00:00:00 2001 From: Hyotaek Shim Date: Wed, 4 Mar 2020 16:43:06 +0900 Subject: [PATCH 11/16] Add is_app() as a common api Change-Id: I5d195ffea25602af85276145a41a4d849696e7d8 Signed-off-by: Hyotaek Shim --- src/core/common.c | 26 ++++++++++++++++++++++++ src/core/common.h | 1 + src/tzip/tzip.c | 59 +++++++++++++------------------------------------------ 3 files changed, 41 insertions(+), 45 deletions(-) diff --git a/src/core/common.c b/src/core/common.c index 04bfaa3..c393c14 100644 --- a/src/core/common.c +++ b/src/core/common.c @@ -111,6 +111,32 @@ int is_vip(int pid) return 0; } +int is_app(pid_t pid) +{ + char attr[64]; + size_t len; + int ret; + + ret = get_privilege(pid, attr, sizeof(attr)); + if (ret < 0) { + _E("Failed to get privilege of PID(%d).", pid); + return -1; + } + + len = strlen(attr) + 1; + + if (!strncmp("System", attr, len)) + return 0; + + if (!strncmp("User", attr, len)) + return 0; + + if (!strncmp("System::Privileged", attr, len)) + return 0; + + return 1; +} + static int remove_dir_internal(int fd) { DIR *dir; diff --git a/src/core/common.h b/src/core/common.h index 7f471e0..9971752 100644 --- a/src/core/common.h +++ b/src/core/common.h @@ -171,6 +171,7 @@ FILE * open_proc_oom_score_adj_file(int pid, const char *mode); int get_exec_pid(const char *execpath); int get_cmdline_name(pid_t pid, char *cmdline, size_t cmdline_size); int is_vip(int pid); +int is_app(pid_t pid); int run_child(int argc, const char *argv[]); int remove_dir(const char *path, int del_dir); int sys_check_node(char *path); diff --git a/src/tzip/tzip.c b/src/tzip/tzip.c index b638740..030f196 100644 --- a/src/tzip/tzip.c +++ b/src/tzip/tzip.c @@ -67,32 +67,6 @@ static int tzip_is_mounted(const char *mount_point); static int tzip_unmount_zipfs(const char *mount_point); static int tzip_mount_zipfs(const char *src_file, const char *mount_point, const char *smack); -static int check_smack_label(pid_t pid) -{ - char attr[64]; - size_t len; - int ret; - - ret = get_privilege(pid, attr, sizeof(attr)); - if (ret < 0) { - _E("Failed to get privilege of PID(%d).", pid); - return 0; - } - - len = strlen(attr) + 1; - - if (!strncmp("System", attr, len)) - return 1; - - if (!strncmp("User", attr, len)) - return 1; - - if (!strncmp("System::Privileged", attr, len)) - return 1; - - return 0; -} - static int check_path_available(char *mountpath) { const char *path; @@ -111,23 +85,6 @@ static int check_path_available(char *mountpath) return 0; } -static int is_app_privileged(pid_t pid, char *mountpath) -{ - int priv; - - priv = check_path_available(mountpath); - if (priv == 0) { - _E("TZIP mount path(%s) is invalid.", mountpath); - return priv; - } - - priv = check_smack_label(pid); - if (priv == 0) - _E("PID(%d) cannot use TZIP due to smack label.", (int)pid); - - return priv; -} - static int tzip_getattr(const char *path, struct stat *stbuf) { int res = 0; @@ -798,8 +755,14 @@ static GVariant *dbus_request_mount_tzip_internal(GDBusConnection *conn, const g goto out; } + if (!check_path_available(mountpath)) { + _E("TZIP mount path(%s) is invalid.", mountpath); + ret = -EAGAIN; + goto out; + } + pid = dbus_connection_get_sender_pid(conn, sender); - if (!is_app_privileged(pid, mountpath)) { + if (is_app(pid) != 0) { _E("PID(%d) is not privileged to use tzip.", pid); ret = -EPERM; goto out; @@ -877,8 +840,14 @@ static GVariant *dbus_request_unmount_tzip_internal(GDBusConnection *conn, const goto out; } + if (!check_path_available(mountpath)) { + _E("TZIP mount path(%s) is invalid.", mountpath); + ret = -EAGAIN; + goto out; + } + pid = dbus_connection_get_sender_pid(conn, sender); - if (!is_app_privileged(pid, mountpath)) { + if (is_app(pid) != 0) { _E("PID(%d) is not privileged to use tzip.", pid); ret = -EPERM; goto out; -- 2.7.4 From 60f17c71d35ec655d3cdf2af12e086da17315ea9 Mon Sep 17 00:00:00 2001 From: Hyotaek Shim Date: Wed, 4 Mar 2020 16:55:51 +0900 Subject: [PATCH 12/16] Fix critical log for long lasting lock Change-Id: Ibd9d1e8bbf5e0409f5879614d46f90f795c5b68a Signed-off-by: Hyotaek Shim --- plugins/iot/display/core.c | 2 +- plugins/mobile/display/core.c | 2 +- plugins/tv/display/core.c | 2 +- plugins/wearable/display/core.c | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/plugins/iot/display/core.c b/plugins/iot/display/core.c index 27370fd..8f90f84 100644 --- a/plugins/iot/display/core.c +++ b/plugins/iot/display/core.c @@ -858,7 +858,7 @@ static void pmlock_check_cb(GVariant *var, void *user_data, GError *err) g_variant_get(var, "(iis)", &pid, &detected, &app_id); - if (!detected) + if (is_app(pid) == 1 && !detected) goto out; node = find_node(state, pid); diff --git a/plugins/mobile/display/core.c b/plugins/mobile/display/core.c index db50295..f6b756a 100644 --- a/plugins/mobile/display/core.c +++ b/plugins/mobile/display/core.c @@ -867,7 +867,7 @@ static void pmlock_check_cb(GVariant *var, void *user_data, GError *err) g_variant_get(var, "(iis)", &pid, &detected, &app_id); - if (!detected) + if (is_app(pid) == 1 && !detected) goto out; node = find_node(state, pid); diff --git a/plugins/tv/display/core.c b/plugins/tv/display/core.c index da4f82c..dba2cef 100644 --- a/plugins/tv/display/core.c +++ b/plugins/tv/display/core.c @@ -858,7 +858,7 @@ static void pmlock_check_cb(GVariant *var, void *user_data, GError *err) g_variant_get(var, "(iis)", &pid, &detected, &app_id); - if (!detected) + if (is_app(pid) == 1 && !detected) goto out; node = find_node(state, pid); diff --git a/plugins/wearable/display/core.c b/plugins/wearable/display/core.c index 7fb61ff..27f68cb 100644 --- a/plugins/wearable/display/core.c +++ b/plugins/wearable/display/core.c @@ -872,7 +872,7 @@ static void pmlock_check_cb(GVariant *var, void *user_data, GError *err) g_variant_get(var, "(iis)", &pid, &detected, &app_id); - if (!detected) + if (is_app(pid) == 1 && !detected) goto out; node = find_node(state, pid); -- 2.7.4 From 137a71fe50381c286134b6f43b1c3833df34ca8f Mon Sep 17 00:00:00 2001 From: INSUN PYO Date: Wed, 4 Mar 2020 16:44:13 +0900 Subject: [PATCH 13/16] Remove duplicate code and clean up in usb module usb_config_init and usb_change_gadget are duplicated with the exact same code. Change-Id: Ie3899df4ccb8d2c861b9af80ed4e652e7bb7a489 --- src/usb/usb-dbus.c | 27 ++++----------- src/usb/usb-debug.c | 30 +++++++---------- src/usb/usb-debug.h | 3 +- src/usb/usb-state.c | 33 ++++++++---------- src/usb/usb-tethering.c | 24 ++++++------- src/usb/usb-tethering.h | 4 --- src/usb/usb.c | 90 ++++++++++++++++++++----------------------------- src/usb/usb.h | 49 +++------------------------ 8 files changed, 86 insertions(+), 174 deletions(-) diff --git a/src/usb/usb-dbus.c b/src/usb/usb-dbus.c index 407dd4c..86415e1 100644 --- a/src/usb/usb-dbus.c +++ b/src/usb/usb-dbus.c @@ -17,15 +17,14 @@ */ -#include #include -#include + #include +#include #include #include "core/log.h" -#include "core/common.h" -#include "core/devices.h" + #include "usb.h" #include "usb-debug.h" @@ -57,22 +56,6 @@ static int get_usb_state(void) return result; } -/* dbus signals */ -void broadcast_usb_config_enabled(int state) -{ - int ret; - - _I("USB config(%d) enabled.", state); - - ret = dbus_handle_emit_dbus_signal(NULL, - DEVICED_PATH_USB, - DEVICED_INTERFACE_USB, - SIGNAL_CONFIG_ENABLED, - g_variant_new("(i)", state)); - if (ret < 0) - _E("Failed to send dbus signal."); -} - void broadcast_usb_state_changed(void) { int ret; @@ -114,6 +97,8 @@ static void change_usb_client_mode(GDBusConnection *conn, return; } + _I("USB mode is changed by dbus signal to %d.", req_vconf); + mode = get_mode_bitmap_from_vconf(req_vconf); if (mode == USB_FUNCTION_INVALID) { @@ -129,7 +114,7 @@ static void change_usb_client_mode(GDBusConnection *conn, ret = usb_change_mode(mode); if (ret < 0) - _E("Failed to change usb mode: %d", ret); + _E("Failed to change USB mode: %d", ret); /* Get selected_mode once more, just in case usb_change_mode() fails */ mode = usb_state_get_selected_mode(); diff --git a/src/usb/usb-debug.c b/src/usb/usb-debug.c index 9c5bf01..eb417d4 100644 --- a/src/usb/usb-debug.c +++ b/src/usb/usb-debug.c @@ -17,30 +17,26 @@ */ -#include -#include +#include + #include +#include #include "core/log.h" -#include "core/common.h" -#include "core/config-parser.h" -#include "core/launch.h" #include "core/device-notifier.h" + #include "usb.h" static bool debug_state; -bool usb_debug_state(void) -{ - return debug_state; -} - int get_usb_debug_state(void) { int state; + /* Never use debug_state variable, anyone other than deviced can change this vconf. */ + if (vconf_get_bool(VCONFKEY_SETAPPL_USB_DEBUG_MODE_BOOL, &state) != VCONF_OK) { - _E("Failed to get vconf value for usb debug mode: %d", vconf_get_ext_errno()); + _E("Failed to get vconf value for USB debug mode: %d", vconf_get_ext_errno()); return -1; } @@ -58,7 +54,7 @@ void set_usb_debug_state(bool on) if (vconf_set_bool(VCONFKEY_SETAPPL_USB_DEBUG_MODE_BOOL, state) == VCONF_OK) debug_state = on; else - _E("Failed to set vconf value for usb debug mode: %d", vconf_get_ext_errno()); + _E("Failed to set vconf value for USB debug mode: %d", vconf_get_ext_errno()); } static void usb_debug_changed(keynode_t *key, void *data) @@ -72,13 +68,13 @@ static void usb_debug_changed(keynode_t *key, void *data) /* This also prevents vconf self-loop by set_usb_debug_state(). */ if (mode == debug_state) { - _I("USB debug is already %s.", mode ? "ON" : "OFF"); + _I("USB debug mode is already %s.", mode ? "ON" : "OFF"); return; } debug_state = mode; - _I("USB debug %s.", mode ? "ON" : "OFF"); + _I("USB debug mode is changed to %s.", mode ? "ON" : "OFF"); device_notify(DEVICE_NOTIFIER_USB_DEBUG_MODE, (void *)&mode); } @@ -94,7 +90,7 @@ static int usb_debug_mode_changed(void *data) /* * It is not always possible to add sdb mode to an existing mode. * The newly changed mode is not always possible and meaningful. - * So, You use the predefined mode for sdb mode only. + * So, you use the predefined mode for debug mode only. * * Example: * - Current mode: USB_FUNCTION_RNDIS | USB_FUNCTION_DIAG @@ -108,7 +104,7 @@ static int usb_debug_mode_changed(void *data) if (usb_state_get_selected_mode() != mode) { ret = usb_change_mode(mode); if (ret < 0) - _E("Failed to change usb mode to (%d).", mode); + _E("Failed to change USB mode to (%d).", mode); } else _I("already mode(%d) was enabled", mode); @@ -128,7 +124,7 @@ void add_usb_debug_handler(void) if (vconf_get_bool(VCONFKEY_SETAPPL_USB_DEBUG_MODE_BOOL, &state) == VCONF_OK) debug_state = (state == 0 ? false : true); else - _E("Failed to get vconf value for usb debug mode: %d", vconf_get_ext_errno()); + _E("Failed to get vconf value for USB debug mode: %d", vconf_get_ext_errno()); } void remove_usb_debug_handler(void) diff --git a/src/usb/usb-debug.h b/src/usb/usb-debug.h index cd3239b..bab0392 100644 --- a/src/usb/usb-debug.h +++ b/src/usb/usb-debug.h @@ -19,7 +19,8 @@ #ifndef __USB_DEBUG_H__ #define __USB_DEBUG_H__ -bool usb_debug_state(void); +#include + int get_usb_debug_state(void); void set_usb_debug_state(bool on); void add_usb_debug_handler(void); diff --git a/src/usb/usb-state.c b/src/usb/usb-state.c index c5a3913..0b466a3 100644 --- a/src/usb/usb-state.c +++ b/src/usb/usb-state.c @@ -17,21 +17,16 @@ */ -#include -#include #include #include #include +#include #include "core/log.h" -#include "core/list.h" -#include "core/common.h" -#include "core/device-notifier.h" -#include "display/poll.h" -#include "extcon/extcon.h" #include "apps/apps.h" +#include "extcon/extcon.h" + #include "usb.h" -#include "usb-tethering.h" #include "usb-debug.h" static int noti_id = -1; @@ -48,8 +43,8 @@ static extcon_usb_state_e usb_connection = USB_DISCONNECTED; * There may be several mode_v for a mode. * In this case, the representative value should be placed on top. * - * In case of SET_USB_SDB_DIAG and SET_USB_DIAG_SDB, SET_USB_SDB_DIAG should be above. - * As another example, SEt_USB_RNDIS_SDB should be at the top of them. + * In case of SET_USB_SDB_DIAG and SET_USB_DIAG_SDB, the SET_USB_SDB_DIAG should be above. + * As another example, SET_USB_RNDIS_SDB should be at the top of them. */ static const struct _usb_mode_mapping_table { int mode_v; /* Integer defined by vconf */ @@ -138,7 +133,7 @@ void usb_state_retrieve_selected_mode(void) /* Never return here because deviced must never run in USB_FUNCTION_NONE mode */ if (vconf_get_int(VCONFKEY_USB_SEL_MODE, &mode_v) != VCONF_OK) - _E("Failed to get vconf value for usb sel mode: %d", vconf_get_ext_errno()); + _E("Failed to get vconf value for USB sel mode: %d", vconf_get_ext_errno()); mode = get_mode_bitmap_from_vconf(mode_v); @@ -150,17 +145,17 @@ void usb_state_retrieve_selected_mode(void) switch (mode) { case USB_FUNCTION_INVALID: /* Invalid vconf */ usb_selected_mode = default_mode; - _E("Failed to convert vconf to mode. There is no mode matches up with vconf %d. Use default mode=0x%x.", mode_v, default_mode); + _E("Failed to convert vconf to USB mode. There is no mode matches up with vconf %d. Use default mode=0x%x.", mode_v, default_mode); break; case USB_FUNCTION_NONE: /* Invalid vconf */ usb_selected_mode = default_mode; - _E("There is USB_FUNCTION_NONE mode matches up with vconf %d. Use default mode=0x%x.", mode_v, default_mode); + _E("There is USB_FUNCTION_NONE USB mode matches up with vconf %d. Use default mode=0x%x.", mode_v, default_mode); break; default: /* Success */ usb_selected_mode = mode; - _I("Succeeded to convert vconf to mode. vconf=%d, mode=0x%x.", mode_v, mode); + _I("Succeeded to convert vconf to USB mode. vconf=%d, mode=0x%x.", mode_v, mode); break; } @@ -172,7 +167,7 @@ void usb_state_retrieve_selected_mode(void) * Expected default sel_mode value in vconf in engineer mode: 2 (MTP + ACM + SDB) */ #ifdef ENGINEER_MODE - _I("Engineer mode. usb selected mode 0x%x, debug state %d", usb_selected_mode, get_usb_debug_state()); + _I("Engineer mode. USB mode 0x%x, debug state %d", usb_selected_mode, get_usb_debug_state()); if (!(usb_selected_mode & USB_FUNCTION_SDB)) { usb_selected_mode = USB_FUNCTION_MTP | USB_FUNCTION_ACM | USB_FUNCTION_SDB; @@ -204,7 +199,7 @@ int usb_state_set_selected_mode(unsigned int mode) ret = vconf_set_int(VCONFKEY_USB_SEL_MODE, mode_v); if (ret != VCONF_OK) - _E("Failed to set vconf value for usb selected mode: %d", vconf_get_ext_errno()); + _E("Failed to set vconf value for USB selected mode: %d", vconf_get_ext_errno()); return ret; } @@ -234,7 +229,7 @@ int usb_state_set_current_mode(unsigned int mode) old_mode_v = mode_v; ret = vconf_set_int(VCONFKEY_USB_CUR_MODE, mode_v); if (ret < 0) - _E("Failed to set vconf value for usb current mode: %d", vconf_get_ext_errno()); + _E("Failed to set vconf value for USB current mode: %d", vconf_get_ext_errno()); } return ret; @@ -323,7 +318,7 @@ void send_usb_state_changed_event(int status) if ((status != VCONFKEY_SYSMAN_USB_CONNECTED) && (status != VCONFKEY_SYSMAN_USB_AVAILABLE) && (status != VCONFKEY_SYSMAN_USB_DISCONNECTED)) { - _E("Invalid usb state changed event (%d)", status); + _E("Invalid USB state changed event (%d)", status); return; } @@ -335,7 +330,7 @@ void send_usb_state_changed_event(int status) usb_state_send_system_event(status); if (vconf_set_int(VCONFKEY_SYSMAN_USB_STATUS, status) != VCONF_OK) - _E("Failed to set vconf value for usb status: %d", vconf_get_ext_errno()); + _E("Failed to set vconf value for USB status: %d", vconf_get_ext_errno()); /* Caution: calls after vconf_set_int(VCONFKEY_SYSMAN_USB_STATUS) */ broadcast_usb_state_changed(); diff --git a/src/usb/usb-tethering.c b/src/usb/usb-tethering.c index b74e87c..5b22da0 100644 --- a/src/usb/usb-tethering.c +++ b/src/usb/usb-tethering.c @@ -17,24 +17,18 @@ */ -#include -#include +#include + #include +#include #include "core/log.h" -#include "core/common.h" -#include "core/config-parser.h" -#include "core/launch.h" #include "core/device-notifier.h" + #include "usb.h" static bool tethering_state; -bool usb_tethering_state(void) -{ - return tethering_state; -} - static void usb_tethering_changed(keynode_t *key, void *data) { int mode; @@ -46,12 +40,14 @@ static void usb_tethering_changed(keynode_t *key, void *data) mode = vconf_keynode_get_int(key); curr = mode & VCONFKEY_MOBILE_HOTSPOT_MODE_USB; - if (curr == tethering_state) + if (curr == tethering_state) { + _I("USB tethering mode is already %s.", curr ? "ON" : "OFF"); return; + } tethering_state = curr; - _I("USB tethering %s.", curr ? "ON" : "OFF"); + _I("USB tethering mode is changed to %s.", curr ? "ON" : "OFF"); device_notify(DEVICE_NOTIFIER_USB_TETHERING_MODE, (void *)curr); } @@ -83,7 +79,7 @@ static int usb_tethering_mode_changed(void *data) if (usb_state_get_selected_mode() != mode) { ret = usb_change_mode(mode); if (ret < 0) - _E("Failed to change usb mode to (%d).", mode); + _E("Failed to change USB mode to (%d).", mode); } else _I("already mode(%d) was enabled", mode); @@ -93,7 +89,7 @@ static int usb_tethering_mode_changed(void *data) void add_usb_tethering_handler(void) { if (vconf_notify_key_changed(VCONFKEY_MOBILE_HOTSPOT_MODE, usb_tethering_changed, NULL) != VCONF_OK) - _E("Failed to add usb tethering handler."); + _E("Failed to add USB tethering handler."); register_notifier(DEVICE_NOTIFIER_USB_TETHERING_MODE, usb_tethering_mode_changed); } diff --git a/src/usb/usb-tethering.h b/src/usb/usb-tethering.h index 998be13..d7a40ec 100644 --- a/src/usb/usb-tethering.h +++ b/src/usb/usb-tethering.h @@ -19,10 +19,6 @@ #ifndef __USB_TETHERING_H__ #define __USB_TETHERING_H__ -#include - -bool usb_tethering_state(void); - void add_usb_tethering_handler(void); void remove_usb_tethering_handler(void); diff --git a/src/usb/usb.c b/src/usb/usb.c index 581c0ae..7e417e1 100644 --- a/src/usb/usb.c +++ b/src/usb/usb.c @@ -17,24 +17,21 @@ */ -#include #include -#include -#include +#include +#include #include #include "core/log.h" -#include "core/list.h" #include "core/udev.h" -#include "core/common.h" -#include "core/device-notifier.h" #include "display/poll.h" #include "display/display-ops.h" -#include "extcon/extcon.h" -#include "apps/apps.h" + #include "usb.h" -#include "usb-tethering.h" #include "usb-debug.h" +#include "usb-tethering.h" + +static int usb_change_gadget(unsigned mode); static struct usb_client *usb_client; static struct usb_gadget_translator *gadget_translator; @@ -46,23 +43,23 @@ static struct usb_gadget_translator *gadget_translator_probe(void) struct usb_gadget_translator *gadget; if (hw_get_info(USB_GADGET_DEVICE_ID, (const struct hw_info **)&info)) { - _E("No usb gadget translator."); + _E("No USB gadget translator."); return NULL; } if (!info->open) { - _E("Failed to open usb gadget translator: open(NULL)"); + _E("Failed to open USB gadget translator: open(NULL)"); return NULL; } if (info->open(info, NULL, &common) < 0) { - _E("Failed to open usb gadget translator."); + _E("Failed to open USB gadget translator."); return NULL; } gadget = container_of(common, struct usb_gadget_translator, common); if (!gadget->id_to_gadget || !gadget->cleanup_gadget) { - _E("Invalid usb gadget translator."); + _E("Invalid USB gadget translator."); if (gadget->common.info) gadget->common.info->close(&gadget->common); @@ -79,7 +76,7 @@ static struct usb_client *usb_client_probe(const char *id) struct hw_common *common; struct usb_client *client; - _I("Loading usb client. id=%s", id); + _I("Loading USB client. id=%s", id); if (hw_get_info(id, (const struct hw_info **)&info)) { _I("No usb_client. id=%s", id); @@ -87,18 +84,18 @@ static struct usb_client *usb_client_probe(const char *id) } if (!info->open) { - _E("Failed to open usb client(%s): open(NULL)", id); + _E("Failed to open USB client(%s): open(NULL)", id); return NULL; } if (info->open(info, NULL, &common) < 0) { - _E("Failed to open usb client. id=%s", id); + _E("Failed to open USB client. id=%s", id); return NULL; } client = container_of(common, struct usb_client, common); if (!client->reconfigure_gadget || !client->enable || !client->disable) { - _E("Invalid usb client. id=%s", id); + _E("Invalid USB client. id=%s", id); if (client->common.info->close) client->common.info->close(&client->common); @@ -106,7 +103,7 @@ static struct usb_client *usb_client_probe(const char *id) return NULL; } - _I("Success lodging usb client. id=%s", id); + _I("Success lodging USB client. id=%s", id); return client; } @@ -159,33 +156,9 @@ static void usb_release() static int usb_config_init(void) { - int ret; - struct usb_gadget *gadget; - struct usb_gadget_id gadget_id; - - if (!gadget_translator || !usb_client) - goto no_hal; - - memset(&gadget_id, 0, sizeof(gadget_id)); - - gadget_id.function_mask = usb_state_get_selected_mode(); - ret = gadget_translator->id_to_gadget(&gadget_id, &gadget); - if (ret) { - _E("Unable to translate id into gadget: %d", ret); - return ret; - } - - usb_client->disable(usb_client); - ret = usb_client->reconfigure_gadget(usb_client, gadget); - gadget_translator->cleanup_gadget(gadget); - if (ret) - _E("Unable to configure gadget: %d", ret); - - return ret; + unsigned int mode = usb_state_get_selected_mode(); -no_hal: - /* TODO. Maybe some default action here? */ - return -ENODEV; + return usb_change_gadget(mode); } static void usb_config_deinit(void) @@ -274,7 +247,7 @@ static int usb_enable(unsigned int mode) ret = usb_config_enable(); if (ret < 0) { - _E("Failed to enable usb config: %d", ret); + _E("Failed to enable USB config: %d", ret); goto out; } @@ -326,7 +299,7 @@ static int usb_connected(void) ret = usb_enable(mode); if (ret < 0) { - _E("Failed to enable usb gadget(0x%x): %d", mode, ret); + _E("Failed to enable USB gadget(0x%x): %d", mode, ret); return ret; } @@ -343,7 +316,7 @@ static int usb_disconnected(void) ret = usb_disable(); if(ret < 0) { - _E("Failed to disable usb gadget: %d", ret); + _E("Failed to disable USB gadget: %d", ret); /* Important: You have to keep going to unlock disp_plgn.pm_unlock_internal */ } @@ -360,16 +333,25 @@ int usb_change_mode(unsigned int new_mode) const unsigned int curr_mode = usb_state_get_current_mode(); const unsigned int prev_mode = usb_state_get_selected_mode(); - _I("usb change mode (0x%x) -> (0x%x), current running mode (0x%x)", prev_mode, new_mode, curr_mode); + _I("USB change mode (0x%x) -> (0x%x), current running mode (0x%x)", prev_mode, new_mode, curr_mode); + + /* + * Information: Because the user explicitly calls this through dbus or vconf, + * you should not check whether the current and new modes are different. + * + * if (curr_mode == new_mode) return; + */ /* + * When you change the gadget(usb_change_gadget) for new usb mode, you must disable the gadget first. + * * Even if the usb cable is plugged in, the current mode may be NULL due to usb fail. * So to find out which mode you are in, you should use the current mode, not the selected mode. */ if (curr_mode != USB_FUNCTION_NONE) { - ret = usb_disable(); /* Need to clean up because usb_change_gadget() also do usb_client->disable() */ + ret = usb_disable(); /* Need to clean up because usb_change_gadget() also calls usb_client->disable() */ if (ret < 0) { - _E("Failed to disable current usb mode."); + _E("Failed to disable current USB mode."); return ret; } } @@ -388,7 +370,7 @@ int usb_change_mode(unsigned int new_mode) if (usb_state_get_connection() == USB_CONNECTED) { ret = usb_enable(new_mode); if (ret < 0) { - _E("Failed to enable usb mode: %d", ret); + _E("Failed to enable USB mode: %d", ret); return ret; } } @@ -406,7 +388,7 @@ static int usb_state_changed(int new_status) static int old_status = -1; /* For debugging. Do not move the location. */ - _I("USB state is changed from (%d) to (%d).", old_status, new_status); + _I("USB state is changed by extcon from (%d) to (%d).", old_status, new_status); if (old_status == new_status) return 0; @@ -426,7 +408,7 @@ static int usb_state_changed(int new_status) } if (ret < 0) { - _E("Failed to operate usb connection: %d", ret); + _E("Failed to operate USB connection: %d", ret); return ret; } @@ -477,7 +459,7 @@ static void usb_init(void *data) ret = usb_config_init(); if (ret < 0) - _E("Failed to initialize usb configuation."); + _E("Failed to initialize USB configuation."); ret = register_udev_uevent_control(&uh); if (ret < 0) diff --git a/src/usb/usb.h b/src/usb/usb.h index 933b1be..9afd7cf 100644 --- a/src/usb/usb.h +++ b/src/usb/usb.h @@ -19,50 +19,22 @@ #ifndef __DEVICED_USB_H__ #define __DEVICED_USB_H__ -//#include -#include +#include #include "extcon/extcon.h" #define USB_FUNCTION_INVALID UINT_MAX #define SET_USB_INVALID INT_MAX -#define USB_CONFIG_OPS_REGISTER(dev) \ -static void __CONSTRUCTOR__ usb_config_init(void) \ -{ \ - add_usb_config(dev); \ -} \ -static void __DESTRUCTOR__ usb_config_exit(void) \ -{ \ - remove_usb_config(dev); \ -} - -struct usb_config_ops { - bool (*is_valid)(void); - const struct usb_config_plugin_ops *(*load)(void); - void (*release)(void); -}; - -/* TODO - * move it to proper location */ -struct usb_config_plugin_ops { - int (*init)(char *name); - void (*deinit)(char *name); - int (*enable)(char *name); - int (*disable)(char *name); - int (*change)(char *name); -}; - -void add_usb_config(const struct usb_config_ops *ops); -void remove_usb_config(const struct usb_config_ops *ops); +int usb_dbus_init(void); -unsigned int get_mode_bitmap_from_vconf(int mode_v); int usb_change_mode(unsigned int mode); +void usb_state_retrieve_selected_mode(void); +unsigned int get_mode_bitmap_from_vconf(int mode_v); +void broadcast_usb_state_changed(void); void send_usb_state_changed_event(int status); void change_usb_state_notification_handler(unsigned int mode); -void usb_state_retrieve_selected_mode(void); - unsigned int usb_state_get_selected_mode(void); int usb_state_set_selected_mode(unsigned int mode); @@ -72,15 +44,4 @@ int usb_state_set_current_mode(unsigned int mode); extcon_usb_state_e usb_state_get_connection(void); void usb_state_set_connection(extcon_usb_state_e conn); -/* dbus methods/signals (usb-dbus.c) */ -enum { - DISABLED, - ENABLED, -}; - -int usb_dbus_init(void); - -void broadcast_usb_config_enabled(int state); -void broadcast_usb_state_changed(void); - #endif /* __USB_CLIENT_H__ */ -- 2.7.4 From 76a0e5f0de47a7149c269eb746054b983201df07 Mon Sep 17 00:00:00 2001 From: INSUN PYO Date: Thu, 5 Mar 2020 12:51:49 +0900 Subject: [PATCH 14/16] Fix to shutdown usb0 interface when USB cable is disconnected in rndis mode When the usb cable is disconnected, it just disables the gadget, but keeps the gadget's configuration. So usb0 is left and rndis.service fails the next time you plug the usb cable. Change-Id: I4245f4cbfcc71b6f42dd9332de2b6e7f564e1358 --- scripts/rndis.sh | 7 +++---- systemd/rndis.service | 1 + 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/scripts/rndis.sh b/scripts/rndis.sh index 66f8294..f5e389b 100755 --- a/scripts/rndis.sh +++ b/scripts/rndis.sh @@ -1,6 +1,5 @@ #!/bin/sh - DEFAULT_IP_ADDR="192.168.129.3" ######################################################################################### @@ -24,11 +23,11 @@ else fi ######################################################################################### -echo "rndis network inteface =" $IFNAME -echo "rndis ip address =" $IP_ADDR - if [ x$1 == "xstart" ] then + echo "rndis network inteface =" $IFNAME + echo "rndis ip address =" $IP_ADDR + /sbin/ifconfig $IFNAME $IP_ADDR up else /sbin/ifconfig $IFNAME down diff --git a/systemd/rndis.service b/systemd/rndis.service index 0ea2fc6..3072061 100644 --- a/systemd/rndis.service +++ b/systemd/rndis.service @@ -7,6 +7,7 @@ User=network_fw Group=network_fw SmackProcessLabel=System ExecStart=/usr/bin/rndis.sh start +ExecStop=/usr/bin/rndis.sh stop Capabilities=cap_net_admin=i SecureBits=keep-caps RemainAfterExit=yes -- 2.7.4 From ab757f94727da8eab22dbf43f654ef02ed20d12f Mon Sep 17 00:00:00 2001 From: INSUN PYO Date: Fri, 6 Mar 2020 08:50:32 +0900 Subject: [PATCH 15/16] Fixed the vconf values in usb debug mode and usb selected mode to always match 1. When usb mode is changed, debug mode should be 1 if sdb is enabled and 0 if disabled. 2. If sdb is enabled in selected mode when deviced starts, enable debug mode; otherwise disable. Change-Id: I8b85bc2d31c0febfccf844619b6ad53a160161ac --- src/usb/usb-dbus.c | 4 ---- src/usb/usb-state.c | 10 +++++++--- src/usb/usb.c | 3 +++ 3 files changed, 10 insertions(+), 7 deletions(-) diff --git a/src/usb/usb-dbus.c b/src/usb/usb-dbus.c index 86415e1..977f592 100644 --- a/src/usb/usb-dbus.c +++ b/src/usb/usb-dbus.c @@ -115,10 +115,6 @@ static void change_usb_client_mode(GDBusConnection *conn, ret = usb_change_mode(mode); if (ret < 0) _E("Failed to change USB mode: %d", ret); - - /* Get selected_mode once more, just in case usb_change_mode() fails */ - mode = usb_state_get_selected_mode(); - set_usb_debug_state((bool)(mode & USB_FUNCTION_SDB)); } /* dbus methods */ diff --git a/src/usb/usb-state.c b/src/usb/usb-state.c index 0b466a3..5c78903 100644 --- a/src/usb/usb-state.c +++ b/src/usb/usb-state.c @@ -127,13 +127,15 @@ static void usb_state_send_system_event(int status) void usb_state_retrieve_selected_mode(void) { - int mode_v = -1; /* -1 is important */ + int mode_v; unsigned int mode; const unsigned int default_mode = USB_FUNCTION_MTP | USB_FUNCTION_ACM; /* Never return here because deviced must never run in USB_FUNCTION_NONE mode */ - if (vconf_get_int(VCONFKEY_USB_SEL_MODE, &mode_v) != VCONF_OK) + if (vconf_get_int(VCONFKEY_USB_SEL_MODE, &mode_v) != VCONF_OK) { + mode_v = SET_USB_INVALID; _E("Failed to get vconf value for USB sel mode: %d", vconf_get_ext_errno()); + } mode = get_mode_bitmap_from_vconf(mode_v); @@ -172,9 +174,11 @@ void usb_state_retrieve_selected_mode(void) if (!(usb_selected_mode & USB_FUNCTION_SDB)) { usb_selected_mode = USB_FUNCTION_MTP | USB_FUNCTION_ACM | USB_FUNCTION_SDB; (void)usb_state_set_selected_mode(usb_selected_mode); - set_usb_debug_state(true); } #endif + + /* To sync with vconf for debug mode */ + set_usb_debug_state((bool)(usb_selected_mode & USB_FUNCTION_SDB)); } /* Cache of vconf_get_int(VCONFKEY_USB_SEL_MODE) */ diff --git a/src/usb/usb.c b/src/usb/usb.c index 7e417e1..fda154b 100644 --- a/src/usb/usb.c +++ b/src/usb/usb.c @@ -378,6 +378,9 @@ int usb_change_mode(unsigned int new_mode) /* If you success to change the runtime usb configuration, do change the selected mode. */ (void)usb_state_set_selected_mode(new_mode); + /* To sync with vconf for debug mode */ + set_usb_debug_state((bool)(new_mode & USB_FUNCTION_SDB)); + return 0; } -- 2.7.4 From c75c4c43ebf91ffdf78f21dd04dc437730a8c45b Mon Sep 17 00:00:00 2001 From: Youngjae Cho Date: Thu, 5 Mar 2020 17:26:14 +0900 Subject: [PATCH 16/16] Turn off display when display is detached Change-Id: I09a203694da1af7bb564cf4faa5839c119839b21 Signed-off-by: Youngjae Cho --- plugins/wearable/display/core.c | 58 ++++++++++++++++++++++++++++++++--------- src/core/devices.h | 1 + src/core/udev.h | 3 +++ src/display/device-interface.h | 1 + 4 files changed, 50 insertions(+), 13 deletions(-) diff --git a/plugins/wearable/display/core.c b/plugins/wearable/display/core.c index 27f68cb..5821dc9 100644 --- a/plugins/wearable/display/core.c +++ b/plugins/wearable/display/core.c @@ -75,18 +75,19 @@ #define PID_MAX 6 -#define GESTURE_STR "gesture" -#define POWER_KEY_STR "powerkey" -#define BACK_KEY_STR "backkey" -#define TOUCH_STR "touch" -#define EVENT_STR "event" -#define BEZEL_STR "bezel" -#define TIMEOUT_STR "timeout" -#define PROXI_STR "proximity" -#define PALM_STR "palm" -#define UNKNOWN_STR "unknown" - -#define METHOD_APP_STATUS "CheckAppStatus" +#define GESTURE_STR "gesture" +#define POWER_KEY_STR "powerkey" +#define BACK_KEY_STR "backkey" +#define TOUCH_STR "touch" +#define EVENT_STR "event" +#define BEZEL_STR "bezel" +#define TIMEOUT_STR "timeout" +#define PROXI_STR "proximity" +#define PALM_STR "palm" +#define DISPLAY_DETACH_STR "display_detach" +#define UNKNOWN_STR "unknown" + +#define METHOD_APP_STATUS "CheckAppStatus" #define PM_WAKEUP 0 #define PM_SUSPEND 1 @@ -429,6 +430,8 @@ static void broadcast_lcd_off(enum signal_type type, enum device_flags flags) str = PROXI_STR; else if (flags & LCD_OFF_BY_PALM) str = PALM_STR; + else if (flags & LCD_OFF_BY_DISPLAY_DETACH) + str = DISPLAY_DETACH_STR; else if (flags & LCD_OFF_BY_GESTURE) str = GESTURE_STR; else @@ -1350,8 +1353,13 @@ int display_off_by_reason(const char *reason) delete_condition(S_LCDDIM); flag = LCD_OFF_BY_PALM; + } else if (!strncmp(reason, DISPLAY_DETACH_STR, str_len)) { + delete_condition(S_NORMAL); + delete_condition(S_LCDDIM); + + flag = LCD_OFF_BY_DISPLAY_DETACH; } else { - _E("Reason is unkown(%s)", reason); + _E("Reason is unknown(%s)", reason); return -EINVAL; } @@ -2809,12 +2817,34 @@ static void lcd_uevent_changed(struct udev_device *dev) } } +static void sec_dsim_uevent_changed(struct udev_device *dev) +{ + const char *devpath; + const char *action; + + devpath = udev_device_get_devpath(dev); + if (!devpath) + return; + + if (!fnmatch(SEC_DSIM_PATH, devpath, 0)) { + action = udev_device_get_action(dev); + if (!strcmp(action, UDEV_CHANGE)) + display_off_by_reason(DISPLAY_DETACH_STR); + } +} + static const struct uevent_handler lcd_uevent_ops = { .subsystem = LCD_EVENT_SUBSYSTEM, .uevent_func = lcd_uevent_changed, .data = NULL, }; +static const struct uevent_handler sec_dsim_uevent_ops = { + .subsystem = SEC_DSIM_EVENT_SUBSYSTEM, + .uevent_func = sec_dsim_uevent_changed, + .data = NULL, +}; + static void display_init(void *data) { int ret, i; @@ -2834,6 +2864,7 @@ static void display_init(void *data) DISPLAY_CONF_FILE, ret); register_kernel_uevent_control(&lcd_uevent_ops); + register_kernel_uevent_control(&sec_dsim_uevent_ops); register_notifier(DEVICE_NOTIFIER_BOOTING_DONE, booting_done); register_notifier(DEVICE_NOTIFIER_PROCESS_BACKGROUND, process_background); @@ -2956,6 +2987,7 @@ static void display_exit(void *data) keyfilter_ops->exit(); unregister_kernel_uevent_control(&lcd_uevent_ops); + unregister_kernel_uevent_control(&sec_dsim_uevent_ops); display_ops_exit(NULL); diff --git a/src/core/devices.h b/src/core/devices.h index 8e79009..7b48710 100644 --- a/src/core/devices.h +++ b/src/core/devices.h @@ -43,6 +43,7 @@ enum device_flags { LCD_ON_BY_EVENT = 0x00080000, LCD_ON_BY_TOUCH = 0x00100000, LCD_ON_BY_BEZEL = 0x00200000, + LCD_OFF_BY_DISPLAY_DETACH = 0x01000000, LCD_OFF_BY_POWER_KEY = 0x02000000, LCD_OFF_BY_TIMEOUT = 0x04000000, LCD_OFF_BY_EVENT = 0x08000000, diff --git a/src/core/udev.h b/src/core/udev.h index 267a892..8375c1f 100644 --- a/src/core/udev.h +++ b/src/core/udev.h @@ -63,6 +63,9 @@ #define LCD_EVENT_SUBSYSTEM "lcd_event" #define LCD_ESD_PATH "*/lcd_event/esd" +#define SEC_DSIM_EVENT_SUBSYSTEM "sec" +#define SEC_DSIM_PATH "*/sec/lcd" + /* power supply status */ enum { POWER_SUPPLY_STATUS_UNKNOWN = 0, diff --git a/src/display/device-interface.h b/src/display/device-interface.h index 2806bc0..e0fc089 100644 --- a/src/display/device-interface.h +++ b/src/display/device-interface.h @@ -124,6 +124,7 @@ enum dpms_state { DPMS_SUSPEND, /* Blanked, lower power */ DPMS_OFF, /* Shut off, awaiting activity */ DPMS_FORCE_OFF,/* Force Shut off */ + DPMS_DETACH, /* Display detached */ }; enum mainlock_state { -- 2.7.4