[gegl] buffer: remove cloned tiles with lower probability when trimming cache



commit 10622d7a8871b74aab815aa060bc276db3e385a4
Author: Ell <ell_se yahoo com>
Date:   Sun Dec 2 09:33:08 2018 -0500

    buffer: remove cloned tiles with lower probability when trimming cache
    
    A set of n cloned tiles is counted only once toward the total cache
    size, so each inidividual tile can be thought of as contributing
    only 1/n of its size to the total cache size.  On the other hand,
    the cost of stroing a tile is independent of the number of clones
    it has.
    
    When trimming the cache, remove an unstored tile with n cached
    clones with a probability of 1/n, instead of 1, to avoid saturating
    the swap queue with cloned tiles, causing stalls.

 gegl/buffer/gegl-tile-handler-cache.c | 19 +++++++++++++++++--
 1 file changed, 17 insertions(+), 2 deletions(-)
---
diff --git a/gegl/buffer/gegl-tile-handler-cache.c b/gegl/buffer/gegl-tile-handler-cache.c
index ae7c4e962..547c9cf65 100644
--- a/gegl/buffer/gegl-tile-handler-cache.c
+++ b/gegl/buffer/gegl-tile-handler-cache.c
@@ -512,8 +512,8 @@ gegl_tile_handler_cache_has_tile (GeglTileHandlerCache *cache,
 static gboolean
 gegl_tile_handler_cache_trim (GeglTileHandlerCache *cache)
 {
-
-  GList *link;
+  GList        *link;
+  static guint  counter;
 
   cache = NULL;
   link  = NULL;
@@ -575,6 +575,21 @@ gegl_tile_handler_cache_trim (GeglTileHandlerCache *cache)
           if (tile->ref_count > 1)
             continue;
 
+          /* a set of cloned tiles is only counted once toward the total cache
+           * size, so the entire set has to be removed from the cache in order
+           * to reclaim the memory of a single tile.  in other words, in a set
+           * of n cloned tiles, we can assume that each individual tile
+           * contributes only 1/n of its size to the total cache size.  on the
+           * other hand, storing a cloned tile is as expensive as storing an
+           * uncloned tile.  therefore, if the tile needs to be stored, we only
+           * remove it with a probability of 1/n.
+           */
+          if (gegl_tile_needs_store (tile) &&
+              counter++ % *gegl_tile_n_cached_clones (tile))
+            {
+              continue;
+            }
+
           break;
         }
 


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]