raster pushed a commit to branch master.

http://git.enlightenment.org/core/enlightenment.git/commit/?id=5404adc54fb7f49b435e736e375bf7368321a1b0

commit 5404adc54fb7f49b435e736e375bf7368321a1b0
Author: Carsten Haitzler (Rasterman) <ras...@rasterman.com>
Date:   Fri Aug 21 15:33:50 2015 +0900

    deskmirror - fix dangling reference to mirror by refcounting it
    
    add deskmirror refs to avoid segv on shutdown/restart due to mb->m
    becoming a pointer to freed (now garbage) memory, so trace every
    ref/unref and count them to get it right. crash gone!
---
 src/bin/e_deskmirror.c | 23 ++++++++++++++++++++++-
 1 file changed, 22 insertions(+), 1 deletion(-)

diff --git a/src/bin/e_deskmirror.c b/src/bin/e_deskmirror.c
index fee6f30..e781ab8 100644
--- a/src/bin/e_deskmirror.c
+++ b/src/bin/e_deskmirror.c
@@ -41,6 +41,7 @@ typedef struct Mirror
    Evas_Object *comp_object;
    Evas_Object *mirror;
    int x, y, w, h;
+   int ref;
    Eina_Bool added : 1;
 } Mirror;
 
@@ -110,6 +111,20 @@ _mirror_scale_set(Mirror *m, float sc)
 }
 
 static void
+_mirror_ref(Mirror *m)
+{
+   m->ref++;
+}
+
+static void
+_mirror_unref(Mirror *m)
+{
+   m->ref--;
+   if (m->ref > 0) return;
+   free(m);
+}
+
+static void
 _e_deskmirror_smart_reconfigure(E_Smart_Data *sd)
 {
    e_layout_freeze(sd->layout);
@@ -337,7 +352,10 @@ _mirror_client_smart_del(Evas_Object *obj)
         evas_object_smart_callback_del_full(mb->m->ec->frame, "shadow_change", 
_mirror_client_shadow_change, mb->frame);
      }
    evas_object_del(mb->frame);
+   mb->frame = NULL;
    evas_object_del(mb->mirror);
+   mb->mirror = NULL;
+   _mirror_unref(mb->m);
    free(mb);
 }
 
@@ -474,12 +492,13 @@ _e_deskmirror_mirror_del_hash(Mirror *m)
    evas_object_smart_callback_del_full(m->comp_object, "frame_recalc_done", 
_e_deskmirror_mirror_frame_recalc_cb, m);
    evas_object_event_callback_del_full(m->comp_object, EVAS_CALLBACK_DEL, 
_e_deskmirror_mirror_del_cb, m);
    evas_object_del(m->mirror);
+   m->mirror = NULL;
    evas_object_event_callback_del_full(m->comp_object, EVAS_CALLBACK_SHOW, 
(Evas_Object_Event_Cb)_comp_object_show, m);
    evas_object_event_callback_del_full(m->comp_object, EVAS_CALLBACK_HIDE, 
(Evas_Object_Event_Cb)_comp_object_hide, m);
    evas_object_event_callback_del_full(m->comp_object, EVAS_CALLBACK_RESTACK, 
(Evas_Object_Event_Cb)_comp_object_stack, m);
    evas_object_event_callback_del_full(m->comp_object, EVAS_CALLBACK_RESIZE, 
(Evas_Object_Event_Cb)_comp_object_configure, m);
    evas_object_event_callback_del_full(m->comp_object, EVAS_CALLBACK_MOVE, 
(Evas_Object_Event_Cb)_comp_object_configure, m);
-   free(m);
+   _mirror_unref(m);
 }
 
 static Evas_Object *
@@ -492,6 +511,7 @@ _mirror_client_new(Mirror *m)
    o = evas_object_smart_add(m->sd->e, _mirror_client_smart);
    mb = evas_object_smart_data_get(o);
    mb->m = m;
+   _mirror_ref(m);
    mb->frame = edje_object_add(m->sd->e);
    evas_object_name_set(mb->frame, "mirror_border");
    _mirror_client_theme_setup(mb, mb->frame);
@@ -656,6 +676,7 @@ _e_deskmirror_mirror_add(E_Smart_Data *sd, Evas_Object *obj)
    m->ec = ec;
    m->sd = sd;
    m->mirror = o;
+   m->ref = 1;
    evas_object_event_callback_add(obj, EVAS_CALLBACK_SHOW, 
(Evas_Object_Event_Cb)_comp_object_show, m);
    evas_object_event_callback_add(obj, EVAS_CALLBACK_HIDE, 
(Evas_Object_Event_Cb)_comp_object_hide, m);
    evas_object_event_callback_add(obj, EVAS_CALLBACK_RESTACK, 
(Evas_Object_Event_Cb)_comp_object_stack, m);

-- 


Reply via email to