From 9810803358445e47a6ee5cfe1385f7de551be852 Mon Sep 17 00:00:00 2001 From: Matthias Clasen Date: Fri, 13 Jan 2023 22:21:01 -0500 Subject: [PATCH] string: Optimize g_string_append(_len) Add static inline versions of these functions that boil down to just an memcpy. ag_string_append_len is used quite a bit in GMarkup and GTK's css parser. --- glib/gstring.c | 15 +++++++-------- glib/gstring.h | 31 +++++++++++++++++++++++++++++++ 2 files changed, 38 insertions(+), 8 deletions(-) diff --git a/glib/gstring.c b/glib/gstring.c index e3a491f81..ed6f03123 100644 --- a/glib/gstring.c +++ b/glib/gstring.c @@ -539,8 +539,8 @@ g_string_append_uri_escaped (GString *string, * Returns: (transfer none): @string */ GString * -g_string_append (GString *string, - const gchar *val) +(g_string_append) (GString *string, + const gchar *val) { return g_string_insert_len (string, -1, val, -1); } @@ -564,9 +564,9 @@ g_string_append (GString *string, * Returns: (transfer none): @string */ GString * -g_string_append_len (GString *string, - const gchar *val, - gssize len) +(g_string_append_len) (GString *string, + const gchar *val, + gssize len) { return g_string_insert_len (string, -1, val, len); } @@ -581,10 +581,9 @@ g_string_append_len (GString *string, * * Returns: (transfer none): @string */ -#undef g_string_append_c GString * -g_string_append_c (GString *string, - gchar c) +(g_string_append_c) (GString *string, + gchar c) { g_return_val_if_fail (string != NULL, NULL); diff --git a/glib/gstring.h b/glib/gstring.h index 8e4cc5657..70888217c 100644 --- a/glib/gstring.h +++ b/glib/gstring.h @@ -35,6 +35,7 @@ #include #include #include /* for G_CAN_INLINE */ +#include G_BEGIN_DECLS @@ -178,6 +179,36 @@ g_string_append_c_inline (GString *gstring, return gstring; } #define g_string_append_c(gstr,c) g_string_append_c_inline (gstr, c) + +static inline GString * +g_string_append_len_inline (GString *gstring, + const char *val, + gssize len) +{ + if (len < 0) + len = strlen (val); + + if (G_LIKELY (gstring->len + len < gstring->allocated_len)) + { + char *end = gstring->str + gstring->len; + if (G_LIKELY (val + len <= end || val > end + len)) + memcpy (end, val, len); + else + memmove (end, val, len); + gstring->len += len; + gstring->str[gstring->len] = 0; + return gstring; + } + else + return g_string_insert_len (gstring, -1, val, len); +} +#define g_string_append_len(gstr,val,len) g_string_append_len_inline (gstr, val, len) + +#if G_GNUC_CHECK_VERSION (2, 0) + +#define g_string_append(gstr,val) g_string_append_len (gstr, val, __builtin_constant_p (val) ? (gssize) strlen (val) : (gssize) -1) +#endif + #endif /* G_CAN_INLINE */