Commit 20abe602 authored by spiiroin's avatar spiiroin

[config] Fix handling of hidden modes setting

The make_hidden_modes_string() function claims to return const string,
but that is true only as an exception to the rule. Since the callers of
the function do not release dynamic memory, this leads to leakage. Also
if no mode is hidden, request to unhide something least to that mode
getting hidden and hiding something already hidden returns NULL which
is rather unintuitive.

Fix make_hidden_modes_string() and make all callers of it to release
dynamically reserved memory / deal with possible null return value.
Signed-off-by: spiiroin's avatarSimo Piiroinen <simo.piiroinen@jollamobile.com>
parent ddc29426
......@@ -416,75 +416,102 @@ set_config_result_t set_mode_setting(const char *mode)
/* Builds the string used for hidden modes, when hide set to one builds the
new string of hidden modes when adding one, otherwise it will remove one */
static const char * make_hidden_modes_string(const char *hidden, int hide)
static char * make_hidden_modes_string(const char *mode_name, int hide)
{
GString *modelist_str;
char *hidden_modes_list;
gchar **hidden_mode_split;
char *hidden_new = 0;
char *hidden_old = 0;
gchar **hidden_arr = 0;
GString *hidden_tmp = 0;
int i;
hidden_modes_list = get_hidden_modes();
if(hidden_modes_list)
{
hidden_mode_split = g_strsplit(hidden_modes_list, ",", 0);
}
else
/* Get current comma separated list of hidden modes */
hidden_old = get_hidden_modes();
if(!hidden_old)
{
/* no hidden modes yet. So just return the original string */
return hidden;
hidden_old = g_strdup("");
}
modelist_str = g_string_new(NULL);
hidden_arr = g_strsplit(hidden_old, ",", 0);
for(i = 0; hidden_mode_split[i] != NULL; i++)
hidden_tmp = g_string_new(NULL);
for(i = 0; hidden_arr[i] != NULL; i++)
{
if(strlen(hidden_mode_split[i]) == 0)
continue;
if(!strcmp(hidden_mode_split[i], hidden))
{
/* if hiding a mode that is already hidden do nothing */
if(hide)
return(NULL);
if(!hide)
continue;
}
if(strlen(modelist_str->str) != 0)
modelist_str = g_string_append(modelist_str, ",");
modelist_str = g_string_append(modelist_str, hidden_mode_split[i]);
if(strlen(hidden_arr[i]) == 0)
{
/* Skip any empty strings */
continue;
}
if(!strcmp(hidden_arr[i], mode_name))
{
/* When unhiding, just skip all matching entries */
if(!hide)
continue;
/* When hiding, keep the 1st match and ignore the rest */
hide = 0;
}
if(hidden_tmp->len > 0)
hidden_tmp = g_string_append(hidden_tmp, ",");
hidden_tmp = g_string_append(hidden_tmp, hidden_arr[i]);
}
if(hide)
{
if(strlen(modelist_str->str) != 0)
modelist_str = g_string_append(modelist_str, ",");
modelist_str = g_string_append(modelist_str, hidden);
/* Adding a hidden mode and no matching entry was found */
if(hidden_tmp->len > 0)
hidden_tmp = g_string_append(hidden_tmp, ",");
hidden_tmp = g_string_append(hidden_tmp, mode_name);
}
g_strfreev(hidden_mode_split);
return(g_string_free(modelist_str, FALSE));
hidden_new = g_string_free(hidden_tmp, FALSE), hidden_tmp = 0;
g_strfreev(hidden_arr), hidden_arr = 0;
g_free(hidden_old), hidden_old = 0;
return hidden_new;
}
set_config_result_t set_hide_mode_setting(const char *mode)
{
set_config_result_t ret;
set_config_result_t ret = SET_CONFIG_UNCHANGED;
char *hidden_modes = make_hidden_modes_string(mode, 1);
if( hidden_modes ) {
ret = set_config_setting(MODE_SETTING_ENTRY, MODE_HIDE_KEY, hidden_modes);
}
ret = set_config_setting(MODE_SETTING_ENTRY, MODE_HIDE_KEY, make_hidden_modes_string(mode, 1));
if(ret == SET_CONFIG_UPDATED) {
send_hidden_modes_signal();
send_supported_modes_signal();
}
g_free(hidden_modes);
return(ret);
}
set_config_result_t set_unhide_mode_setting(const char *mode)
{
set_config_result_t ret;
set_config_result_t ret = SET_CONFIG_UNCHANGED;
char *hidden_modes = make_hidden_modes_string(mode, 0);
if( hidden_modes ) {
ret = set_config_setting(MODE_SETTING_ENTRY, MODE_HIDE_KEY, hidden_modes);
}
ret = set_config_setting(MODE_SETTING_ENTRY, MODE_HIDE_KEY, make_hidden_modes_string(mode, 0));
if(ret == SET_CONFIG_UPDATED) {
send_hidden_modes_signal();
send_supported_modes_signal();
}
g_free(hidden_modes);
return(ret);
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment