LEAKS! GONE!
authorIván Briano <sachieru@gmail.com>
Fri, 11 May 2012 20:12:56 +0000 (20:12 +0000)
committerIván Briano <sachieru@gmail.com>
Fri, 11 May 2012 20:12:56 +0000 (20:12 +0000)
 - Cleanup cache2 things on shutdown
 - Use Eina_File instead of straight shm_open + mmap when loading things from cserve2
 - Do free the mapped images when we don't need them

SVN revision: 70936

legacy/evas/src/lib/cache2/evas_cache2.c
legacy/evas/src/lib/cserve2/evas_cs2_client.c
legacy/evas/src/lib/cserve2/evas_cs2_private.h

index 8a15b3d..bc43052 100644 (file)
@@ -488,9 +488,40 @@ evas_cache2_init(const Evas_Cache2_Image_Func *cb)
    return cache;
 }
 
+static Eina_Bool
+_evas_cache_image_free_cb(__UNUSED__ const Eina_Hash *hash, __UNUSED__ const void *key, void *data, void *fdata)
+{
+   Eina_List **delete_list = fdata;
+   *delete_list = eina_list_prepend(*delete_list, data);
+   return EINA_TRUE;
+}
+
 EAPI void
 evas_cache2_shutdown(Evas_Cache2 *cache)
 {
+   Eina_List *delete_list;
+   Image_Entry *im;
+
+   while (cache->lru)
+     {
+        im = (Image_Entry *)cache->lru;
+        _evas_cache_image_entry_delete(cache, im);
+     }
+   /* This is mad, I am about to destroy image still alive, but we need to prevent leak. */
+   while (cache->dirty)
+     {
+        im = (Image_Entry *)cache->dirty;
+        _evas_cache_image_entry_delete(cache, im);
+     }
+
+   delete_list = NULL;
+   eina_hash_foreach(cache->activ, _evas_cache_image_free_cb, &delete_list);
+   while (delete_list)
+     {
+        _evas_cache_image_entry_delete(cache, eina_list_data_get(delete_list));
+        delete_list = eina_list_remove_list(delete_list, delete_list);
+     }
+
    eina_hash_free(cache->activ);
    eina_hash_free(cache->inactiv);
 
index 3f6ef4b..00485d7 100644 (file)
@@ -312,7 +312,6 @@ _image_loaded_cb(void *data, const void *msg_received)
    Image_Entry *ie = data;
    Data_Entry *dentry = ie->data2;
    const char *shmpath;
-   int fd;
 
    ie->load_rid = 0;
 
@@ -337,25 +336,25 @@ _image_loaded_cb(void *data, const void *msg_received)
    dentry->shm.mmap_size = msg->shm.mmap_size;
    dentry->shm.image_size = msg->shm.image_size;
 
-   fd = shm_open(shmpath, O_RDONLY, S_IRUSR);
-   if (fd < 0)
+   dentry->shm.f = eina_file_open(shmpath, EINA_TRUE);
+   if (!dentry->shm.f)
      {
         free(dentry);
         ie->data2 = NULL;
         return;
      }
 
-   dentry->shm.data = mmap(NULL, dentry->shm.mmap_size, PROT_READ,
-                           MAP_SHARED, fd, dentry->shm.mmap_offset);
+   dentry->shm.data = eina_file_map_new(dentry->shm.f, EINA_FILE_WILLNEED,
+                                        dentry->shm.mmap_offset,
+                                        dentry->shm.mmap_size);
 
-   if (dentry->shm.data == MAP_FAILED)
+   if (!dentry->shm.data)
      {
+        eina_file_close(dentry->shm.f);
         free(dentry);
         ie->data2 = NULL;
      }
 
-   close(fd);
-
    if (ie->data2)
      {
         ie->flags.loaded = EINA_TRUE;
@@ -589,6 +588,11 @@ _image_close_server_send(Image_Entry *ie)
 
    if (ie->data2)
      {
+        Data_Entry *dentry = ie->data2;
+        if (dentry->shm.data)
+          eina_file_map_free(dentry->shm.f, dentry->shm.data);
+        if (dentry->shm.f)
+          eina_file_close(dentry->shm.f);
         free(ie->data2);
         ie->data2 = NULL;
      }
@@ -621,6 +625,11 @@ _image_unload_server_send(Image_Entry *ie)
 
    dentry = ie->data2;
 
+   if (dentry->shm.data)
+     eina_file_map_free(dentry->shm.f, dentry->shm.data);
+   if (dentry->shm.f)
+     eina_file_close(dentry->shm.f);
+
    // if (dentry->shm.path)
    //   free(dentry->shm.path);
    memset(&msg, 0, sizeof(msg));
index 5521fd8..c0dde77 100644 (file)
@@ -12,6 +12,7 @@ struct _Data_Entry {
       int use_offset;
       int mmap_size;
       int image_size;
+      Eina_File *f;
       void *data;
    } shm;
 };