kimcinoo pushed a commit to branch master.

http://git.enlightenment.org/core/efl.git/commit/?id=34b0d0e973274c1a3df2386a30ad2a31bfcfe0d7

commit 34b0d0e973274c1a3df2386a30ad2a31bfcfe0d7
Author: Shinwoo Kim <cinoo....@samsung.com>
Date:   Thu Jan 14 13:47:06 2021 +0900

    gl: remove invalid read and write
    
    Summary:
    There could be 2 evas_gl_image referencing 1 evas_gl_texture.
    evas_object_image_orient_set could make this case.
    In this case, when one evas_gl_image is removed(free), the evas_gl_texture
    is not removed because its reference count.
    After this point, if the other evas_gl_image is removed without drawing
    (see function evas_gl_common_image_draw, line "im->tex->im = im")
    then evas_gl_texture is reading invalid adress when it is removed.
    
    Reviewers: Hermet, jsuya, herb, devilhorns
    
    Reviewed By: devilhorns
    
    Subscribers: devilhorns, cedric, #reviewers, #committers
    
    Tags: #efl
    
    Differential Revision: https://phab.enlightenment.org/D12229
---
 src/modules/evas/engines/gl_common/evas_gl_common.h  |  2 +-
 src/modules/evas/engines/gl_common/evas_gl_image.c   | 10 +++++++++-
 src/modules/evas/engines/gl_common/evas_gl_texture.c |  7 ++++---
 3 files changed, 14 insertions(+), 5 deletions(-)

diff --git a/src/modules/evas/engines/gl_common/evas_gl_common.h 
b/src/modules/evas/engines/gl_common/evas_gl_common.h
index c7b4d22150..2d9d825a75 100644
--- a/src/modules/evas/engines/gl_common/evas_gl_common.h
+++ b/src/modules/evas/engines/gl_common/evas_gl_common.h
@@ -723,7 +723,7 @@ Evas_GL_Texture  
*evas_gl_common_texture_render_noscale_new(Evas_Engine_GL_Conte
 Evas_GL_Texture  *evas_gl_common_texture_dynamic_new(Evas_Engine_GL_Context 
*gc, Evas_GL_Image *im);
 void              evas_gl_common_texture_update(Evas_GL_Texture *tex, 
RGBA_Image *im);
 void              evas_gl_common_texture_upload(Evas_GL_Texture *tex, 
RGBA_Image *im, unsigned int bytes_count);
-void              evas_gl_common_texture_free(Evas_GL_Texture *tex, Eina_Bool 
force);
+Eina_Bool         evas_gl_common_texture_free(Evas_GL_Texture *tex, Eina_Bool 
force);
 Evas_GL_Texture  *evas_gl_common_texture_alpha_new(Evas_Engine_GL_Context *gc, 
DATA8 *pixels, unsigned int w, unsigned int h, int fh);
 void              evas_gl_common_texture_alpha_update(Evas_GL_Texture *tex, 
DATA8 *pixels, unsigned int w, unsigned int h, int fh);
 Evas_GL_Texture  *evas_gl_common_texture_yuv_new(Evas_Engine_GL_Context *gc, 
DATA8 **rows, unsigned int w, unsigned int h);
diff --git a/src/modules/evas/engines/gl_common/evas_gl_image.c 
b/src/modules/evas/engines/gl_common/evas_gl_image.c
index 2d9383305a..13ca077cac 100644
--- a/src/modules/evas/engines/gl_common/evas_gl_image.c
+++ b/src/modules/evas/engines/gl_common/evas_gl_image.c
@@ -720,7 +720,15 @@ evas_gl_common_image_free(Evas_GL_Image *im)
      {
         if (_evas_gl_image_cache_add(im)) return;
      }
-   if (im->tex) evas_gl_common_texture_free(im->tex, EINA_TRUE);
+   if (im->tex)
+     {
+        if (!evas_gl_common_texture_free(im->tex, EINA_TRUE))
+          {
+             /* if texture is not freed, we need to assign im to NULL
+                because after this point im will be freed */
+             im->tex->im = NULL;
+          }
+     }
    if (im->im)
      evas_cache_image_drop(&im->im->cache_entry);
 
diff --git a/src/modules/evas/engines/gl_common/evas_gl_texture.c 
b/src/modules/evas/engines/gl_common/evas_gl_texture.c
index 47dd8305a8..049e4236cb 100644
--- a/src/modules/evas/engines/gl_common/evas_gl_texture.c
+++ b/src/modules/evas/engines/gl_common/evas_gl_texture.c
@@ -1550,10 +1550,10 @@ evas_gl_common_texture_update(Evas_GL_Texture *tex, 
RGBA_Image *im)
    im->cache_entry.flags.textured = 1;
 }
 
-void
+Eina_Bool
 evas_gl_common_texture_free(Evas_GL_Texture *tex, Eina_Bool force)
 {
-   if (!tex) return;
+   if (!tex) return EINA_FALSE;
    if (force)
      {
         evas_gl_preload_pop(tex);
@@ -1562,7 +1562,7 @@ evas_gl_common_texture_free(Evas_GL_Texture *tex, 
Eina_Bool force)
           evas_gl_preload_target_unregister(tex, 
eina_list_data_get(tex->targets));
      }
    tex->references--;
-   if (tex->references != 0) return;
+   if (tex->references != 0) return EINA_FALSE;
    if (tex->fglyph)
      {
         tex->gc->font_glyph_textures_size -= tex->w * tex->h * 4;
@@ -1617,6 +1617,7 @@ evas_gl_common_texture_free(Evas_GL_Texture *tex, 
Eina_Bool force)
      }
 
    evas_gl_common_texture_light_free(tex);
+   return EINA_TRUE;
 }
 
 Evas_GL_Texture *

-- 


Reply via email to