3ced12
From b6036e23b0477be147211b4e21a6b49cd4d6c9a0 Mon Sep 17 00:00:00 2001
3ced12
From: Jamie Bainbridge <jamie.bainbridge@gmail.com>
3ced12
Date: Wed, 8 Sep 2021 12:08:17 +1000
3ced12
Subject: [PATCH] gutils: Avoid segfault in g_get_user_database_entry
3ced12
3ced12
g_get_user_database_entry() uses variable pwd to store the contents of
3ced12
the call to getpwnam_r(), then capitalises the first letter of pw_name
3ced12
with g_ascii_toupper (pw->pw_name[0]).
3ced12
3ced12
However, as per the getpwnam manpage, the result of that call "may point
3ced12
to a static area". When this happens, GLib is trying to edit static
3ced12
memory which belongs to a shared library, so segfaults.
3ced12
3ced12
Instead, copy pw_name off to a temporary variable, set uppercase on
3ced12
that variable, and use the variable to join into the desired string.
3ced12
Free the new variable after it is no longer needed.
3ced12
3ced12
Signed-off-by: Jamie Bainbridge <jamie.bainbridge@gmail.com>
3ced12
---
3ced12
 glib/gutils.c | 7 +++++--
3ced12
 1 file changed, 5 insertions(+), 2 deletions(-)
3ced12
3ced12
diff --git a/glib/gutils.c b/glib/gutils.c
3ced12
index b7a2113d4..4bccd7229 100644
3ced12
--- a/glib/gutils.c
3ced12
+++ b/glib/gutils.c
3ced12
@@ -692,14 +692,17 @@ g_get_user_database_entry (void)
3ced12
               {
3ced12
                 gchar **gecos_fields;
3ced12
                 gchar **name_parts;
3ced12
+                gchar *uppercase_pw_name;
3ced12
 
3ced12
                 /* split the gecos field and substitute '&' */
3ced12
                 gecos_fields = g_strsplit (pw->pw_gecos, ",", 0);
3ced12
                 name_parts = g_strsplit (gecos_fields[0], "&", 0);
3ced12
-                pw->pw_name[0] = g_ascii_toupper (pw->pw_name[0]);
3ced12
-                e.real_name = g_strjoinv (pw->pw_name, name_parts);
3ced12
+                uppercase_pw_name = g_strdup (pw->pw_name);
3ced12
+                uppercase_pw_name[0] = g_ascii_toupper (uppercase_pw_name[0]);
3ced12
+                e.real_name = g_strjoinv (uppercase_pw_name, name_parts);
3ced12
                 g_strfreev (gecos_fields);
3ced12
                 g_strfreev (name_parts);
3ced12
+                g_free (uppercase_pw_name);
3ced12
               }
3ced12
 #endif
3ced12
 
3ced12
-- 
3ced12
GitLab
3ced12