From e34d7d07b1ec41b21f1772005d00359c17a08d55 Mon Sep 17 00:00:00 2001 From: Matthias Clasen Date: Mon, 10 Feb 2020 18:22:17 -0500 Subject: lookup: Don't store flat arrays Most lookups have no or just a few values. We can drastically reduce the amount of memory used for lookups, and then we can afford to keep them around and avoid some lookups in the future. --- gtk/gtkcsslookup.c | 28 +++++++++++++++++++++++++--- gtk/gtkcsslookupprivate.h | 17 +++++++++++++++-- 2 files changed, 40 insertions(+), 5 deletions(-) diff --git a/gtk/gtkcsslookup.c b/gtk/gtkcsslookup.c index 11f15e837f..d621604957 100644 --- a/gtk/gtkcsslookup.c +++ b/gtk/gtkcsslookup.c @@ -24,6 +24,16 @@ #include "gtkprivatetypebuiltins.h" #include "gtkprivate.h" +static void +free_value (gpointer data) +{ + GtkCssLookupValue *value = data; + + gtk_css_value_unref (value->value); + if (value->section) + gtk_css_section_unref (value->section); +} + GtkCssLookup * gtk_css_lookup_new (void) { @@ -39,6 +49,8 @@ static void gtk_css_lookup_free (GtkCssLookup *lookup) { _gtk_bitmask_free (lookup->set_values); + if (lookup->values) + g_array_unref (lookup->values); g_free (lookup); } @@ -93,11 +105,21 @@ gtk_css_lookup_set (GtkCssLookup *lookup, GtkCssSection *section, GtkCssValue *value) { + GtkCssLookupValue v; + gtk_internal_return_if_fail (lookup != NULL); gtk_internal_return_if_fail (value != NULL); - gtk_internal_return_if_fail (lookup->values[id].value == NULL); - lookup->values[id].value = value; - lookup->values[id].section = section; + v.value = gtk_css_value_ref (value); + v.section = section ? gtk_css_section_ref (section) : NULL; + v.id = id; + + if (!lookup->values) + { + lookup->values = g_array_sized_new (FALSE, FALSE, sizeof (GtkCssLookupValue), 16); + g_array_set_clear_func (lookup->values, free_value); + } + + g_array_append_val (lookup->values, v); lookup->set_values = _gtk_bitmask_set (lookup->set_values, id, TRUE); } diff --git a/gtk/gtkcsslookupprivate.h b/gtk/gtkcsslookupprivate.h index 49c2c0b1e9..7fcd530d7e 100644 --- a/gtk/gtkcsslookupprivate.h +++ b/gtk/gtkcsslookupprivate.h @@ -33,12 +33,13 @@ typedef struct _GtkCssLookup GtkCssLookup; typedef struct { GtkCssSection *section; GtkCssValue *value; + guint id; } GtkCssLookupValue; struct _GtkCssLookup { int ref_count; GtkBitmask *set_values; - GtkCssLookupValue values[GTK_CSS_PROPERTY_N_PROPERTIES]; + GArray *values; }; GtkCssLookup * gtk_css_lookup_new (void); @@ -62,7 +63,19 @@ static inline GtkCssLookupValue * gtk_css_lookup_get (GtkCssLookup *lookup, guint id) { - return &lookup->values[id]; + if (_gtk_bitmask_get (lookup->set_values, id)) + { + int i; + + for (i = 0; i < lookup->values->len; i++) + { + GtkCssLookupValue *value = &g_array_index (lookup->values, GtkCssLookupValue, i); + if (value->id == id) + return value; + } + } + + return NULL; } G_END_DECLS -- cgit v1.2.1