elm_widget: fix widget signal callback memory leak.

Thanks to bluezery D228 for pointing out the issue.
This commit is contained in:
Cedric Bail 2013-09-25 16:41:12 +09:00
parent 29af5e1e43
commit fa2ce3c547
1 changed files with 43 additions and 37 deletions

View File

@ -4956,6 +4956,40 @@ _track_obj_del(void *data, Evas *e EINA_UNUSED,
_track_obj_view_del);
}
static void
_elm_widget_item_signal_cb(void *data, Evas_Object *obj __UNUSED__, const char *emission,
const char *source)
{
Elm_Widget_Item_Signal_Data *wisd = data;
wisd->func(wisd->data, wisd->item, emission, source);
}
static void *
_elm_widget_item_signal_callback_list_get(Elm_Widget_Item *item, Eina_List *position)
{
Elm_Widget_Item_Signal_Data *wisd = eina_list_data_get(position);
void *data;
item->signals = eina_list_remove_list(item->signals, position);
data = wisd->data;
if (_elm_widget_is(item->view))
elm_object_signal_callback_del(item->view,
wisd->emission, wisd->source,
_elm_widget_item_signal_cb);
else if (!strcmp(eo_class_name_get(eo_class_get(item->view)),
"edje"))
edje_object_signal_callback_del_full(item->view,
wisd->emission, wisd->source,
_elm_widget_item_signal_cb, wisd);
eina_stringshare_del(wisd->emission);
eina_stringshare_del(wisd->source);
free(wisd);
return data;
}
/**
* @internal
@ -5000,7 +5034,6 @@ EAPI void
_elm_widget_item_free(Elm_Widget_Item *item)
{
Elm_Translate_String_Data *ts;
Elm_Widget_Item_Signal_Data *wisd;
ELM_WIDGET_ITEM_CHECK_OR_RETURN(item);
@ -5013,12 +5046,8 @@ _elm_widget_item_free(Elm_Widget_Item *item)
if (item->access_info)
eina_stringshare_del(item->access_info);
EINA_LIST_FREE(item->signals, wisd)
{
eina_stringshare_del(wisd->emission);
eina_stringshare_del(wisd->source);
free(wisd);
}
while (item->signals)
_elm_widget_item_signal_callback_list_get(item, item->signals);
while (item->translate_strings)
{
@ -5913,14 +5942,6 @@ _elm_widget_item_signal_emit_hook_set(Elm_Widget_Item *item,
item->signal_emit_func = func;
}
static void
_elm_widget_item_signal_cb(void *data, Evas_Object *obj __UNUSED__, const char *emission,
const char *source)
{
Elm_Widget_Item_Signal_Data *wisd = data;
wisd->func(wisd->data, wisd->item, emission, source);
}
EAPI void
_elm_widget_item_signal_callback_add(Elm_Widget_Item *item,
const char *emission,
@ -5963,36 +5984,21 @@ _elm_widget_item_signal_callback_del(Elm_Widget_Item *item,
const char *source,
Elm_Widget_Item_Signal_Cb func)
{
Elm_Widget_Item_Signal_Data *wisd;
Eina_List *l;
ELM_WIDGET_ITEM_CHECK_OR_RETURN(item, NULL);
EINA_SAFETY_ON_NULL_RETURN_VAL(func, NULL);
Elm_Widget_Item_Signal_Data *wisd;
Eina_List *l;
void *data = NULL;
EINA_LIST_FOREACH(item->signals, l, wisd)
{
if ((wisd->func == func) && !strcmp(wisd->emission, emission) &&
if ((wisd->func == func) &&
!strcmp(wisd->emission, emission) &&
!strcmp(wisd->source, source))
{
item->signals = eina_list_remove_list(item->signals, l);
eina_stringshare_del(wisd->emission);
eina_stringshare_del(wisd->source);
data = wisd->data;
if (_elm_widget_is(item->view))
elm_object_signal_callback_del(item->view, emission, source,
_elm_widget_item_signal_cb);
else if (!strcmp(eo_class_name_get(eo_class_get(item->view)),
"edje"))
edje_object_signal_callback_del_full(item->view, emission,
source,
_elm_widget_item_signal_cb,
wisd);
}
return _elm_widget_item_signal_callback_list_get(item, l);
}
return data;
return NULL;
}
EAPI void