From 72f217e25a1a11fbdecaa03521bb4432425a0abd Mon Sep 17 00:00:00 2001 From: Christian Hergert Date: Fri, 20 Sep 2024 10:32:09 -0700 Subject: [PATCH] gvarianttype: avoid walking type string twice to hash We already need to walk the string to determine the length of it, so just hash the string at the same time. --- glib/gvarianttype-private.h | 32 ++++++++++++++++++++++++++++++++ glib/gvarianttype.c | 13 +------------ 2 files changed, 33 insertions(+), 12 deletions(-) diff --git a/glib/gvarianttype-private.h b/glib/gvarianttype-private.h index 08cbd5cb8..982bd0665 100644 --- a/glib/gvarianttype-private.h +++ b/glib/gvarianttype-private.h @@ -64,4 +64,36 @@ _g_variant_type_equal (const GVariantType *type1, return TRUE; } +static inline guint +_g_variant_type_hash (gconstpointer type) +{ + const gchar *type_string = type; + guint value = 0; + gsize index = 0; + int brackets = 0; + + do + { + value = (value << 5) - value + type_string[index]; + + while (type_string[index] == 'a' || type_string[index] == 'm') + { + index++; + + value = (value << 5) - value + type_string[index]; + } + + if (type_string[index] == '(' || type_string[index] == '{') + brackets++; + + else if (type_string[index] == ')' || type_string[index] == '}') + brackets--; + + index++; + } + while (brackets); + + return value; +} + G_END_DECLS diff --git a/glib/gvarianttype.c b/glib/gvarianttype.c index 0bb784a47..40dc6f713 100644 --- a/glib/gvarianttype.c +++ b/glib/gvarianttype.c @@ -777,20 +777,9 @@ g_variant_type_is_variant (const GVariantType *type) guint g_variant_type_hash (gconstpointer type) { - const gchar *type_string; - guint value = 0; - gsize length; - gsize i; - g_return_val_if_fail (g_variant_type_check (type), 0); - type_string = g_variant_type_peek_string (type); - length = g_variant_type_get_string_length (type); - - for (i = 0; i < length; i++) - value = (value << 5) - value + type_string[i]; - - return value; + return _g_variant_type_hash (type); } /**