Index: pangofc-fontmap.cI
===================================================================
RCS file: /cvs/gnome/pango/pango/pangofc-fontmap.cI,v
retrieving revision 1.6
diff -u -p -r1.6 pangofc-fontmap.cI
--- pangofc-fontmap.cI	17 Dec 2002 02:07:36 -0000	1.6
+++ pangofc-fontmap.cI	15 Feb 2003 19:46:41 -0000
@@ -24,8 +24,8 @@
  * after making appropriate #defines for public symbols.
  */
 
-/* Number of freed fonts  to keep around */
-#define MAX_FREED_FONTS 128
+/* Size of fontset cache */
+#define FONTSET_CACHE_SIZE 16
 
 typedef struct _PangoFcCoverageKey PangoFcCoverageKey;
 typedef struct _PangoFcFace         PangoFcFace;
@@ -68,6 +68,8 @@ struct _PangoFcPatternSet
 {
   int n_patterns;
   FcPattern **patterns;
+  PangoFontset *fontset;
+  GList *cache_link;
 };
 
 GType           pango_fc_font_map_get_type   (void);
@@ -92,8 +94,6 @@ static void          pango_fc_font_map_l
 static void pango_fc_font_set_free         (PangoFcPatternSet *font_set);
 
 static void pango_fc_font_map_cache_clear  (PangoFcFontMap    *fcfontmap);
-static void pango_fc_font_map_cache_remove (PangoFontMap       *fontmap,
-					     PangoFcFont       *xfont);
 static void pango_fc_default_substitute    (PangoFcFontMap    *fontmap,
 					     FcPattern          *pattern);
 static void pango_fc_do_finalize           (PangoFcFontMap    *fontmap);
@@ -145,9 +145,8 @@ pango_fc_font_map_init (PangoFcFontMap *
 						     (GEqualFunc)pango_fc_coverage_key_equal,
 						     (GDestroyNotify)g_free,
 						     (GDestroyNotify)pango_coverage_unref);
-  fcfontmap->freed_fonts = g_queue_new ();
+  fcfontmap->fontset_cache = g_queue_new ();
 }
-
 static void
 pango_fc_font_map_class_init (PangoFontMapClass *class)
 {
@@ -298,7 +297,7 @@ pango_fc_font_map_finalize (GObject *obj
     fcfontmap->substitute_destroy (fcfontmap->substitute_data);
 
   pango_fc_font_map_cache_clear (fcfontmap);
-  g_queue_free (fcfontmap->freed_fonts);
+  g_queue_free (fcfontmap->fontset_cache);
   pango_fc_clear_fontset_hash_list (fcfontmap);
   g_hash_table_destroy (fcfontmap->coverage_hash);
 
@@ -512,15 +511,7 @@ pango_fc_font_map_new_font (PangoFontMap
   font = g_hash_table_lookup (fcfontmap->fonts, match);
   
   if (font)
-    {
-      g_object_ref (font);
-
-      /* Revive font from cache */
-      if (font->in_cache)
-	pango_fc_font_map_cache_remove (fontmap, font);
-
-      return (PangoFont *)font;
-    }
+    return g_object_ref (font);
 
   FcPatternReference (match);
   return  (PangoFont *)_pango_fc_font_new (fontmap, match);
@@ -602,6 +593,8 @@ pango_fc_font_map_get_patterns (PangoFon
       patterns = g_new (PangoFcPatternSet, 1);
       patterns->patterns = g_new (FcPattern *, font_patterns->nfont);
       patterns->n_patterns = 0;
+      patterns->fontset = NULL;
+      patterns->cache_link = NULL;
 
       for (f = 0; f < font_patterns->nfont; f++)
       {
@@ -657,78 +650,94 @@ pango_fc_font_set_free (PangoFcPatternSe
   g_free (font_set);
 }
 
+static void
+pango_fc_font_map_cache_fontset (PangoFcFontMap    *fcfontmap,
+				 PangoFcPatternSet *patterns)
+{
+  GQueue *cache = fcfontmap->fontset_cache;
+  
+  if (patterns->cache_link)
+    {
+      /* Already in cache, move to head
+       */
+      if (patterns->cache_link == cache->tail)
+	cache->tail = patterns->cache_link->prev;
+
+      cache->head = g_list_remove_link (cache->head, patterns->cache_link);
+      cache->length--;
+    }
+  else
+    {
+      /* Add to cache initially
+       */
+      if (cache->length == FONTSET_CACHE_SIZE)
+	{
+	  PangoFcPatternSet *tmp_patterns = g_queue_pop_tail (cache);
+	  tmp_patterns->cache_link = NULL;
+	  g_object_unref (tmp_patterns->fontset);
+	}
+	
+      g_object_ref (patterns->fontset);
+      patterns->cache_link = g_list_prepend (NULL, patterns);
+    }
+
+  g_queue_push_head_link (cache, patterns->cache_link);
+}
 
 static PangoFontset *
 pango_fc_font_map_load_fontset (PangoFontMap                 *fontmap,
-				 PangoContext                 *context,
-				 const PangoFontDescription   *desc,
-				 PangoLanguage                *language)
+				PangoContext                 *context,
+				const PangoFontDescription   *desc,
+				PangoLanguage                *language)
 {
-  PangoFontsetSimple *simple;
   int i;
   PangoFcPatternSet *patterns = pango_fc_font_map_get_patterns (fontmap, context, desc, language);
+  PangoFcFontMap *fcfontmap = PANGO_FC_FONT_MAP (fontmap);
   if (!patterns)
     return NULL;
-	  
-  simple = pango_fontset_simple_new (language);
 
-  for (i = 0; i < patterns->n_patterns; i++)
+  if (!patterns->fontset)
     {
-      PangoFont *font = pango_fc_font_map_new_font (fontmap, patterns->patterns[i]);
-      if (font)
-	pango_fontset_simple_append (simple, font);
+      PangoFontsetSimple *simple;
+      simple = pango_fontset_simple_new (language);
+      
+      for (i = 0; i < patterns->n_patterns; i++)
+	{
+	  PangoFont *font = pango_fc_font_map_new_font (fontmap, patterns->patterns[i]);
+	  if (font)
+	    pango_fontset_simple_append (simple, font);
+	}
+  
+      patterns->fontset = PANGO_FONTSET (simple);
+      g_object_add_weak_pointer (G_OBJECT (patterns->fontset),
+				 (gpointer *)&patterns->fontset);
     }
+  else
+    g_object_ref (patterns->fontset);
   
-  return PANGO_FONTSET (simple);
-}
-
-
-void
-_pango_fc_font_map_cache_add (PangoFontMap *fontmap,
-			       PangoFcFont *xfont)
-{
-  PangoFcFontMap *fcfontmap = PANGO_FC_FONT_MAP (fontmap);
+  if (!patterns->cache_link ||
+      patterns->cache_link != fcfontmap->fontset_cache->head)
+    pango_fc_font_map_cache_fontset (fcfontmap, patterns);
 
-  g_object_ref (G_OBJECT (xfont));
-  g_queue_push_head (fcfontmap->freed_fonts, xfont);
-  xfont->in_cache = TRUE;
-
-  if (fcfontmap->freed_fonts->length > MAX_FREED_FONTS)
-    {
-      GObject *old_font = g_queue_pop_tail (fcfontmap->freed_fonts);
-      g_object_unref (old_font);
-    }
+  return patterns->fontset;
 }
 
 static void
-pango_fc_font_map_cache_remove (PangoFontMap *fontmap,
-				 PangoFcFont *xfont)
+uncache_patterns (PangoFcPatternSet *patterns)
 {
-  PangoFcFontMap *fcfontmap = PANGO_FC_FONT_MAP (fontmap);
-
-  GList *link = g_list_find (fcfontmap->freed_fonts->head, xfont);
-  if (link == fcfontmap->freed_fonts->tail)
-    {
-      fcfontmap->freed_fonts->tail = fcfontmap->freed_fonts->tail->prev;
-      if (fcfontmap->freed_fonts->tail)
-	fcfontmap->freed_fonts->tail->next = NULL;
-    }
-  
-  fcfontmap->freed_fonts->head = g_list_delete_link (fcfontmap->freed_fonts->head, link);
-  fcfontmap->freed_fonts->length--;
-  xfont->in_cache = FALSE;
-
-  g_object_unref (G_OBJECT (xfont));
+  g_object_unref (patterns->fontset);
 }
 
 static void
 pango_fc_font_map_cache_clear (PangoFcFontMap   *fcfontmap)
 {
-  g_list_foreach (fcfontmap->freed_fonts->head, (GFunc)g_object_unref, NULL);
-  g_list_free (fcfontmap->freed_fonts->head);
-  fcfontmap->freed_fonts->head = NULL;
-  fcfontmap->freed_fonts->tail = NULL;
-  fcfontmap->freed_fonts->length = 0;
+  GQueue *cache = fcfontmap->fontset_cache;
+  
+  g_list_foreach (cache->head, (GFunc)uncache_patterns, NULL);
+  g_list_free (cache->head);
+  cache->head = NULL;
+  cache->tail = NULL;
+  cache->length = 0;
 }
 
 static void
Index: pangoft2-fontmap.c
===================================================================
RCS file: /cvs/gnome/pango/pango/pangoft2-fontmap.c,v
retrieving revision 1.44
diff -u -p -r1.44 pangoft2-fontmap.c
--- pangoft2-fontmap.c	3 Dec 2002 06:43:10 -0000	1.44
+++ pangoft2-fontmap.c	15 Feb 2003 19:46:42 -0000
@@ -62,7 +62,8 @@ struct _PangoFT2FontMap
   GHashTable *coverage_hash; /* Maps font file name -> PangoCoverage */
 
   GHashTable *fonts; /* Maps XftPattern -> PangoFT2Font */
-  GQueue *freed_fonts; /* Fonts in fonts that has been freed */
+	
+  GQueue *fontset_cache;	/* Recently used fontsets */
 
   /* List of all families availible */
   PangoFT2Family **families;
@@ -95,8 +96,6 @@ struct _PangoFT2FontMap
 #define pango_fc_font_map_get_type pango_ft2_font_map_get_type
 #define _pango_fc_font_map_add _pango_ft2_font_map_add
 #define _pango_fc_font_map_remove _pango_ft2_font_map_remove
-#define _pango_fc_font_map_cache_add _pango_ft2_font_map_cache_add
-#define _pango_fc_font_map_cache_remove _pango_ft2_font_map_cache_remove
 #define _pango_fc_font_map_get_coverage _pango_ft2_font_map_get_coverage
 #define _pango_fc_font_map_set_coverage _pango_ft2_font_map_set_coverage
 #define _pango_fc_font_desc_from_pattern _pango_ft2_font_desc_from_pattern
Index: pangoft2-private.h
===================================================================
RCS file: /cvs/gnome/pango/pango/pangoft2-private.h,v
retrieving revision 1.19
diff -u -p -r1.19 pangoft2-private.h
--- pangoft2-private.h	16 Aug 2002 22:00:28 -0000	1.19
+++ pangoft2-private.h	15 Feb 2003 19:46:42 -0000
@@ -72,9 +72,9 @@ struct _PangoFT2Font
   
   GSList *metrics_by_lang;
 
-  /* If TRUE, font is in cache of recently unused fonts and not otherwise
+  /* If set, font is in cache of recently unused fonts and not otherwise
    * in use. */
-  gboolean in_cache;
+  GList *cache_link;
 
   GHashTable *glyph_info;
   GDestroyNotify glyph_cache_destroy;
@@ -93,10 +93,6 @@ PangoMap      *_pango_ft2_get_shaper_map
 PangoCoverage *_pango_ft2_font_map_get_coverage   (PangoFontMap                *fontmap,
 						   FcPattern                   *pattern);
 FT_Library     _pango_ft2_font_map_get_library    (PangoFontMap      *fontmap);
-void           _pango_ft2_font_map_cache_add      (PangoFontMap      *fontmap,
-						   PangoFT2Font      *ft2font);
-void           _pango_ft2_font_map_cache_remove    (PangoFontMap      *fontmap,
-						   PangoFT2Font      *ft2font);
 void           _pango_ft2_font_map_add            (PangoFontMap      *fontmap,
 						   PangoFT2Font      *ft2font);
 void           _pango_ft2_font_map_remove         (PangoFontMap      *fontmap,
Index: pangoft2.c
===================================================================
RCS file: /cvs/gnome/pango/pango/pangoft2.c,v
retrieving revision 1.50
diff -u -p -r1.50 pangoft2.c
--- pangoft2.c	7 Dec 2002 06:08:39 -0000	1.50
+++ pangoft2.c	15 Feb 2003 19:46:42 -0000
@@ -66,7 +66,6 @@ static PangoFontClass *parent_class;	/* 
 
 static void pango_ft2_font_class_init (PangoFT2FontClass *class);
 static void pango_ft2_font_init       (PangoFT2Font      *ft2font);
-static void pango_ft2_font_dispose    (GObject         *object);
 static void pango_ft2_font_finalize   (GObject         *object);
 
 static PangoFontDescription *pango_ft2_font_describe          (PangoFont            *font);
@@ -315,7 +314,6 @@ pango_ft2_font_class_init (PangoFT2FontC
   parent_class = g_type_class_peek_parent (class);
   
   object_class->finalize = pango_ft2_font_finalize;
-  object_class->dispose = pango_ft2_font_dispose;
   
   font_class->describe = pango_ft2_font_describe;
   font_class->get_coverage = pango_ft2_font_get_coverage;
@@ -667,22 +665,6 @@ pango_ft2_font_get_metrics (PangoFont   
 
   return pango_font_metrics_ref (info->metrics);
 }
-
-static void
-pango_ft2_font_dispose (GObject *object)
-{
-  PangoFT2Font *ft2font = PANGO_FT2_FONT (object);
-
-  /* If the font is not already in the freed-fonts cache, add it,
-   * if it is already there, do nothing and the font will be
-   * freed.
-   */
-  if (!ft2font->in_cache && ft2font->fontmap)
-    _pango_ft2_font_map_cache_add (ft2font->fontmap, ft2font);
-
-  G_OBJECT_CLASS (parent_class)->dispose (object);
-}
-
 
 static gboolean
 pango_ft2_free_glyph_info_callback (gpointer key, gpointer value, gpointer data)
Index: pangoxft-font.c
===================================================================
RCS file: /cvs/gnome/pango/pango/pangoxft-font.c,v
retrieving revision 1.41
diff -u -p -r1.41 pangoxft-font.c
--- pangoxft-font.c	7 Dec 2002 04:21:10 -0000	1.41
+++ pangoxft-font.c	15 Feb 2003 19:46:42 -0000
@@ -53,7 +53,6 @@ static PangoFontClass *parent_class;	/* 
 
 static void pango_xft_font_class_init (PangoXftFontClass *class);
 static void pango_xft_font_init       (PangoXftFont      *xfont);
-static void pango_xft_font_dispose    (GObject         *object);
 static void pango_xft_font_finalize   (GObject         *object);
 
 static PangoFontDescription *pango_xft_font_describe          (PangoFont        *font);
@@ -103,7 +102,7 @@ static void 
 pango_xft_font_init (PangoXftFont *xfont)
 {
   xfont->metrics_by_lang = NULL;
-  xfont->in_cache = FALSE;
+  xfont->cache_link = NULL;
 }
 
 static void
@@ -115,7 +114,6 @@ pango_xft_font_class_init (PangoXftFontC
   parent_class = g_type_class_peek_parent (class);
   
   object_class->finalize = pango_xft_font_finalize;
-  object_class->dispose = pango_xft_font_dispose;
   
   font_class->describe = pango_xft_font_describe;
   font_class->get_coverage = pango_xft_font_get_coverage;
@@ -492,21 +490,6 @@ pango_xft_font_get_metrics (PangoFont   
     }
 
   return pango_font_metrics_ref (info->metrics);
-}
-
-static void
-pango_xft_font_dispose (GObject *object)
-{
-  PangoXftFont *xfont = PANGO_XFT_FONT (object);
-
-  /* If the font is not already in the freed-fonts cache, add it,
-   * if it is already there, do nothing and the font will be
-   * freed.
-   */
-  if (!xfont->in_cache && xfont->fontmap)
-    _pango_xft_font_map_cache_add (xfont->fontmap, xfont);
-
-  G_OBJECT_CLASS (parent_class)->dispose (object);
 }
 
 static void
Index: pangoxft-fontmap.c
===================================================================
RCS file: /cvs/gnome/pango/pango/pangoxft-fontmap.c,v
retrieving revision 1.38
diff -u -p -r1.38 pangoxft-fontmap.c
--- pangoxft-fontmap.c	7 Dec 2002 06:08:39 -0000	1.38
+++ pangoxft-fontmap.c	15 Feb 2003 19:46:42 -0000
@@ -52,7 +52,8 @@ struct _PangoXftFontMap
   GHashTable *coverage_hash; /* Maps font file name/id -> PangoCoverage */
 
   GHashTable *fonts; /* Maps XftPattern -> PangoXftFont */
-  GQueue *freed_fonts; /* Fonts in fonts that has been freed */
+
+  GQueue *fontset_cache;	/* Recently used fontsets */
 
   /* List of all families availible */
   PangoXftFamily **families;
@@ -84,8 +85,6 @@ struct _PangoXftFontMap
 #define pango_fc_font_map_get_type pango_xft_font_map_get_type
 #define _pango_fc_font_map_add _pango_xft_font_map_add
 #define _pango_fc_font_map_remove _pango_xft_font_map_remove
-#define _pango_fc_font_map_cache_add _pango_xft_font_map_cache_add
-#define _pango_fc_font_map_cache_remove _pango_xft_font_map_cache_remove
 #define _pango_fc_font_map_get_coverage _pango_xft_font_map_get_coverage
 #define _pango_fc_font_map_set_coverage _pango_xft_font_map_set_coverage
 #define _pango_fc_font_desc_from_pattern _pango_xft_font_desc_from_pattern
Index: pangoxft-private.h
===================================================================
RCS file: /cvs/gnome/pango/pango/pangoxft-private.h,v
retrieving revision 1.9
diff -u -p -r1.9 pangoxft-private.h
--- pangoxft-private.h	16 Aug 2002 22:00:28 -0000	1.9
+++ pangoxft-private.h	15 Feb 2003 19:46:42 -0000
@@ -44,14 +44,12 @@ struct _PangoXftFont
   guint16 mini_width;		    /* metrics for missing glyph drawing */
   guint16 mini_height;
   guint16 mini_pad; 
-  
-  gboolean in_cache;
+
+  GList *cache_link;
 };
 
 PangoXftFont * _pango_xft_font_new              (PangoFontMap                *font,
 						 FcPattern                  *pattern);
-void           _pango_xft_font_map_cache_add    (PangoFontMap                *fontmap,
-						 PangoXftFont                *xfont);
 void           _pango_xft_font_map_add          (PangoFontMap                *fontmap,
 						 PangoXftFont                *xfont);
 void           _pango_xft_font_map_remove       (PangoFontMap                *fontmap,
