Merge ~whershberger/ubuntu/+source/glib2.0:ubuntu/noble-devel-lp2072586 into ubuntu/+source/glib2.0:ubuntu/noble-devel

Proposed by Wesley Hershberger
Status: Work in progress
Proposed branch: ~whershberger/ubuntu/+source/glib2.0:ubuntu/noble-devel-lp2072586
Merge into: ubuntu/+source/glib2.0:ubuntu/noble-devel
Diff against target: 156 lines (+134/-0)
3 files modified
debian/changelog (+8/-0)
debian/patches/lp2072586-gfileutils-Preserve-mode-during-atomic-updates.patch (+125/-0)
debian/patches/series (+1/-0)
Reviewer Review Type Date Requested Status
Ubuntu Sponsors Pending
git-ubuntu import Pending
Review via email: mp+485047@code.launchpad.net

Commit message

gfileutils: Preserve mode during atomic file writes (LP: #2072586)

Description of the change

Backport 45a36e52

To post a comment you must log in.

Unmerged commits

46e0c19... by Wesley Hershberger

gfileutils: Preserve mode during atomic file writes (LP: #2072586)

* gfileutils: Preserve mode during atomic file writes to prevent high umask
  from rendering dconf database files unreadable (LP: #2072586).
  - d/p/lp2072586-gfileutils-Preserve-mode-during-atomic-updates.patch

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
diff --git a/debian/changelog b/debian/changelog
index 4999ee8..e1645da 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -1,3 +1,11 @@
1glib2.0 (2.80.0-6ubuntu3.3) jammy; urgency=medium
2
3 * gfileutils: Preserve mode during atomic file writes to prevent high umask
4 from rendering dconf database files unreadable (LP: #2072586).
5 - d/p/lp2072586-gfileutils-Preserve-mode-during-atomic-updates.patch
6
7 -- Wesley Hershberger <wesley.hershberger@canonical.com> Fri, 25 Apr 2025 16:53:19 -0500
8
1glib2.0 (2.80.0-6ubuntu3.2) noble-security; urgency=medium9glib2.0 (2.80.0-6ubuntu3.2) noble-security; urgency=medium
210
3 * SECURITY UPDATE: Buffer overflow11 * SECURITY UPDATE: Buffer overflow
diff --git a/debian/patches/lp2072586-gfileutils-Preserve-mode-during-atomic-updates.patch b/debian/patches/lp2072586-gfileutils-Preserve-mode-during-atomic-updates.patch
4new file mode 10064412new file mode 100644
index 0000000..bc83847
--- /dev/null
+++ b/debian/patches/lp2072586-gfileutils-Preserve-mode-during-atomic-updates.patch
@@ -0,0 +1,125 @@
1From: Wesley Hershberger <wesley.hershberger@canonical.com>
2Date: Tue, 22 Apr 2025 16:37:49 -0500
3Subject: gfileutils: Preserve mode during atomic updates
4
5If g_file_set_contents{_full,} is replacing an existing file, require
6that the tmpfile have the same mode as the existing file.
7
8This prevents the umask from taking effect for consistent writes to
9existing files.
10
11Closes GNOME/dconf#76
12
13Bug: https://gitlab.gnome.org/GNOME/dconf/-/issues/76
14Bug-Ubuntu: https://bugs.launchpad.net/bugs/2072586
15Origin: upstream, https://gitlab.gnome.org/GNOME/glib/-/commit/45a36e52b570cf86ce2599b657e63a83d284cb46
16---
17 glib/gfileutils.c | 25 +++++++++++++++++++++++--
18 glib/tests/fileutils.c | 14 ++++++++++----
19 2 files changed, 33 insertions(+), 6 deletions(-)
20
21diff --git a/glib/gfileutils.c b/glib/gfileutils.c
22index 2801777..7811016 100644
23--- a/glib/gfileutils.c
24+++ b/glib/gfileutils.c
25@@ -1318,8 +1318,8 @@ g_file_set_contents (const gchar *filename,
26 * to 7 characters to @filename.
27 *
28 * If the file didn’t exist before and is created, it will be given the
29- * permissions from @mode. Otherwise, the permissions of the existing file may
30- * be changed to @mode depending on @flags, or they may remain unchanged.
31+ * permissions from @mode. Otherwise, the permissions of the existing file will
32+ * remain unchanged.
33 *
34 * Returns: %TRUE on success, %FALSE if an error occurred
35 *
36@@ -1362,6 +1362,7 @@ g_file_set_contents_full (const gchar *filename,
37 gboolean retval;
38 int fd;
39 gboolean do_fsync;
40+ GStatBuf old_stat;
41
42 tmp_filename = g_strdup_printf ("%s.XXXXXX", filename);
43
44@@ -1379,6 +1380,26 @@ g_file_set_contents_full (const gchar *filename,
45 goto consistent_out;
46 }
47
48+ /* Maintain the permissions of the file if it exists */
49+ if (!g_stat (filename, &old_stat))
50+ {
51+#ifndef G_OS_WIN32
52+ if (fchmod (fd, old_stat.st_mode))
53+#else /* G_OS_WIN32 */
54+ if (chmod (tmp_filename, old_stat.st_mode))
55+#endif /* G_OS_WIN32 */
56+ {
57+ int saved_errno = errno;
58+ if (error)
59+ set_file_error (error,
60+ tmp_filename, _ ("Failed to set permissions of “%s”: %s"),
61+ saved_errno);
62+ g_unlink (tmp_filename);
63+ retval = FALSE;
64+ goto consistent_out;
65+ }
66+ }
67+
68 do_fsync = fd_should_be_fsynced (fd, filename, flags);
69 if (!write_to_file (contents, length, g_steal_fd (&fd), tmp_filename, do_fsync, error))
70 {
71diff --git a/glib/tests/fileutils.c b/glib/tests/fileutils.c
72index 56be804..b7b77e1 100644
73--- a/glib/tests/fileutils.c
74+++ b/glib/tests/fileutils.c
75@@ -1686,7 +1686,9 @@ test_set_contents_full (void)
76 EXISTING_FILE_DIRECTORY,
77 }
78 existing_file;
79- int new_mode; /* only relevant if @existing_file is %EXISTING_FILE_NONE */
80+ /* only relevant if @existing_file is
81+ * %EXISTING_FILE_NONE or %EXISTING_FILE_REGULAR */
82+ int mode;
83 gboolean use_strlen;
84
85 gboolean expected_success;
86@@ -1697,6 +1699,8 @@ test_set_contents_full (void)
87 { EXISTING_FILE_NONE, 0644, FALSE, TRUE, 0 },
88 { EXISTING_FILE_NONE, 0644, TRUE, TRUE, 0 },
89 { EXISTING_FILE_NONE, 0600, FALSE, TRUE, 0 },
90+ // Assume umask is 022, ensures that we preserve perms with, eg. 077
91+ { EXISTING_FILE_REGULAR, 0666, FALSE, TRUE, 0 },
92 { EXISTING_FILE_REGULAR, 0644, FALSE, TRUE, 0 },
93 #ifndef G_OS_WIN32
94 { EXISTING_FILE_SYMLINK, 0644, FALSE, TRUE, 0 },
95@@ -1741,6 +1745,8 @@ test_set_contents_full (void)
96 g_assert_no_errno (g_fsync (fd));
97 close (fd);
98
99+ g_assert_no_errno (chmod (file_name, tests[i].mode));
100+
101 #ifndef G_OS_WIN32
102 /* Pass an existing symlink to g_file_set_contents_full() to see
103 * what it does. */
104@@ -1784,7 +1790,7 @@ test_set_contents_full (void)
105 /* Set the file contents */
106 ret = g_file_set_contents_full (set_contents_name, "b",
107 tests[i].use_strlen ? -1 : 1,
108- flags, tests[i].new_mode, &error);
109+ flags, tests[i].mode, &error);
110
111 if (!tests[i].expected_success)
112 {
113@@ -1808,10 +1814,10 @@ test_set_contents_full (void)
114
115 g_assert_no_errno (g_lstat (set_contents_name, &statbuf));
116
117- if (tests[i].existing_file == EXISTING_FILE_NONE)
118+ if (tests[i].existing_file & (EXISTING_FILE_NONE | EXISTING_FILE_REGULAR))
119 {
120 int mode = statbuf.st_mode & ~S_IFMT;
121- int new_mode = tests[i].new_mode;
122+ int new_mode = tests[i].mode;
123 #ifdef G_OS_WIN32
124 /* on windows, group and others perms handling is different */
125 /* only check the rwx user permissions */
diff --git a/debian/patches/series b/debian/patches/series
index 2deb54b..5d89fd6 100644
--- a/debian/patches/series
+++ b/debian/patches/series
@@ -38,3 +38,4 @@ CVE-2024-34397-15.patch
38CVE-2024-34397-16.patch38CVE-2024-34397-16.patch
39CVE-2024-34397-regression.patch39CVE-2024-34397-regression.patch
40CVE-2024-52533.patch40CVE-2024-52533.patch
41lp2072586-gfileutils-Preserve-mode-during-atomic-updates.patch

Subscribers

People subscribed via source and target branches