Compare commits
No commits in common. "c8s" and "c9-beta" have entirely different histories.
3
.gitignore
vendored
3
.gitignore
vendored
@ -1,2 +1 @@
|
|||||||
SOURCES/glib-2.70.1.tar.xz
|
SOURCES/glib-2.78.6.tar.xz
|
||||||
/glib-2.70.1.tar.xz
|
|
||||||
|
|||||||
1
.mingw-glib2.metadata
Normal file
1
.mingw-glib2.metadata
Normal file
@ -0,0 +1 @@
|
|||||||
|
99b8a81357314c6fa279003ce1b95b5d708ba7a8 SOURCES/glib-2.78.6.tar.xz
|
||||||
@ -1,28 +1,242 @@
|
|||||||
From 7f4f4354540440c0a8a37beaccbec8bc7fc15ec7 Mon Sep 17 00:00:00 2001
|
diff -rupN --no-dereference glib-2.78.0/gio/tests/org.gtk.test.gschema.override.orig glib-2.78.0-new/gio/tests/org.gtk.test.gschema.override.orig
|
||||||
From: Erik van Pienbroek <epienbro@fedoraproject.org>
|
--- glib-2.78.0/gio/tests/org.gtk.test.gschema.override.orig 2023-09-08 15:42:18.000000000 +0200
|
||||||
Date: Mon, 27 Aug 2012 23:28:54 +0200
|
+++ glib-2.78.0-new/gio/tests/org.gtk.test.gschema.override.orig 1970-01-01 01:00:00.000000000 +0100
|
||||||
Subject: [PATCH] Use CreateFile on Win32 to make sure g_unlink always works
|
@@ -1,2 +0,0 @@
|
||||||
|
-[org.gtk.test.per-desktop:GNOME-Classic]
|
||||||
The functions g_open(), g_creat() and g_fopen() defer to _wopen(),
|
-desktop = "GNOME Classic"
|
||||||
_wcreat() and _wfopen() respectively. This is very similar to
|
diff -rupN --no-dereference glib-2.78.0/gio/tests/org.gtk.test.gschema.xml.orig glib-2.78.0-new/gio/tests/org.gtk.test.gschema.xml.orig
|
||||||
the corresponding arrangement for Linux. However, those Windows
|
--- glib-2.78.0/gio/tests/org.gtk.test.gschema.xml.orig 2023-09-08 15:42:18.000000000 +0200
|
||||||
functions do not support renaming a file whilst it's open. As a
|
+++ glib-2.78.0-new/gio/tests/org.gtk.test.gschema.xml.orig 1970-01-01 01:00:00.000000000 +0100
|
||||||
result, g_rename() behaves differently on the Windows platform
|
@@ -1,225 +0,0 @@
|
||||||
compared to its Linux behaviour, where files can be renamed even
|
-<schemalist>
|
||||||
while there are file handles still open. Resolved this by using
|
-
|
||||||
the Win32 API function CreateFile() instead of _wopen(), _wcreat()
|
- <schema id="org.gtk.test" path="/tests/" gettext-domain="test">
|
||||||
and _wfopen()
|
- <key name="greeting" type="s">
|
||||||
|
- <default l10n="messages">"Hello, earthlings"</default>
|
||||||
Patch initially created by John Emmas
|
- <summary>A greeting</summary>
|
||||||
---
|
- <description>
|
||||||
glib/gstdio.c | 259 ++++++++++++++++++++++++++++++++++++++++++++++++++++------
|
- Greeting of the invading martians
|
||||||
1 file changed, 233 insertions(+), 26 deletions(-)
|
- </description>
|
||||||
|
- </key>
|
||||||
diff --git a/glib/gstdio.c b/glib/gstdio.c
|
- <key name="farewell" type="s">
|
||||||
index 6d763e1..c1d072f 100644
|
- <default l10n="messages">"So long"</default>
|
||||||
--- a/glib/gstdio.c
|
- </key>
|
||||||
+++ b/glib/gstdio.c
|
-
|
||||||
@@ -1045,6 +1045,11 @@ g_open (const gchar *filename,
|
- <child name='basic-types' schema='org.gtk.test.basic-types'/>
|
||||||
|
- <child name='complex-types' schema='org.gtk.test.complex-types'/>
|
||||||
|
- <child name='localized' schema='org.gtk.test.localized'/>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id="org.gtk.test.no-path">
|
||||||
|
- <key name="test-boolean" type="b">
|
||||||
|
- <default>true</default>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id="org.gtk.test.basic-types" path="/tests/basic-types/">
|
||||||
|
- <key name="test-boolean" type="b">
|
||||||
|
- <default>true</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="test-byte" type="y">
|
||||||
|
- <default>25</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="test-int16" type="n">
|
||||||
|
- <default>-1234</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="test-uint16" type="q">
|
||||||
|
- <default>1234</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="test-int32" type="i">
|
||||||
|
- <default>-123456</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="test-uint32" type="u">
|
||||||
|
- <default>123456</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="test-int64" type="x">
|
||||||
|
- <default>-123456789</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="test-uint64" type="t">
|
||||||
|
- <default>123456789</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="test-double" type="d">
|
||||||
|
- <default>123.456</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="test-string" type="s">
|
||||||
|
- <default>"a string, it seems"</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="test-objectpath" type="o">
|
||||||
|
- <default>"/a/object/path"</default>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id="org.gtk.test.complex-types" path="/tests/complex-types/">
|
||||||
|
- <key name="test-tuple" type="(s(ii))">
|
||||||
|
- <default>("one",(2,3))</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="test-array" type="ai">
|
||||||
|
- <default>[0,1,2,3,4,5]</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="test-dict" type="a{sau}">
|
||||||
|
- <default>
|
||||||
|
- {
|
||||||
|
- "AC": [0,0, 0,0,0,0,0,0],
|
||||||
|
- "IV": [0,0, 0,0,0,0,0,0]
|
||||||
|
- }
|
||||||
|
- </default>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id="org.gtk.test.localized" path="/tests/localized/" gettext-domain="test">
|
||||||
|
- <key name="error-message" type="s">
|
||||||
|
- <default l10n="messages">"Unnamed"</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="backspace" type="s">
|
||||||
|
- <default l10n="messages" context="keyboard label">"BackSpace"</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="midnight" type="s">
|
||||||
|
- <default l10n="time">"12:00 AM"</default>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id="org.gtk.test.binding" path="/tests/binding/">
|
||||||
|
- <key name="bool" type="b">
|
||||||
|
- <default>false</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="anti-bool" type="b">
|
||||||
|
- <default>false</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="byte" type="y">
|
||||||
|
- <default>0</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="int16" type="n">
|
||||||
|
- <default>0</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="uint16" type="q">
|
||||||
|
- <default>0</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="int" type="i">
|
||||||
|
- <default>0</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="uint" type="u">
|
||||||
|
- <default>0</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="int64" type="x">
|
||||||
|
- <default>0</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="uint64" type="t">
|
||||||
|
- <default>0</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="double" type="d">
|
||||||
|
- <default>0</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="string" type="s">
|
||||||
|
- <default>""</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="chararray" type="ay">
|
||||||
|
- <default>[48, 49]</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="strv" type="as">
|
||||||
|
- <default>[]</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="enum" enum="org.gtk.test.TestEnum">
|
||||||
|
- <default>'foo'</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="flags" flags="org.gtk.test.TestFlags">
|
||||||
|
- <default>['mourning', 'laughing']</default>
|
||||||
|
- </key>
|
||||||
|
- <key name="range" type='u'>
|
||||||
|
- <default>33</default>
|
||||||
|
- <range min="2" max="44"/>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id='org.gtk.test.enums' path='/tests/enums/'>
|
||||||
|
- <key name='test' enum='org.gtk.test.TestEnum'>
|
||||||
|
- <default>'bar'</default>
|
||||||
|
- <aliases>
|
||||||
|
- <alias value='qux' target='quux'/>
|
||||||
|
- </aliases>
|
||||||
|
- </key>
|
||||||
|
- <key name='f-test' flags='org.gtk.test.TestFlags'>
|
||||||
|
- <default>[]</default>
|
||||||
|
- <aliases>
|
||||||
|
- <alias value='speaking' target='talking'/>
|
||||||
|
- </aliases>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id='org.gtk.test.enums.direct' path='/tests/enums/'>
|
||||||
|
- <key name='f-test' type='as'>
|
||||||
|
- <default>[]</default>
|
||||||
|
- </key>
|
||||||
|
- <key name='test' type='s'>
|
||||||
|
- <default>'bar'</default>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id='org.gtk.test.range' path='/tests/range/'>
|
||||||
|
- <key name='val' type='i'>
|
||||||
|
- <default>33</default>
|
||||||
|
- <range min='2' max='44'/>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id='org.gtk.test.range.direct' path='/tests/range/'>
|
||||||
|
- <key name='val' type='i'>
|
||||||
|
- <default>33</default>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id='org.gtk.test.mapped' path='/tests/mapped/'>
|
||||||
|
- <key name='val' type='i'>
|
||||||
|
- <default>0</default>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id="org.gtk.test.descriptions" path="/a/">
|
||||||
|
- <key name='a' type='i'>
|
||||||
|
- <summary>
|
||||||
|
- a paragraph.
|
||||||
|
-
|
||||||
|
- with some whitespace.
|
||||||
|
-
|
||||||
|
- because not everyone has a great editor.
|
||||||
|
-
|
||||||
|
-
|
||||||
|
-
|
||||||
|
-
|
||||||
|
- lots of space is as one.
|
||||||
|
- </summary>
|
||||||
|
- <default>0</default>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id='org.gtk.test.extends.base'>
|
||||||
|
- <key name='int32' type='i'>
|
||||||
|
- <default>0</default>
|
||||||
|
- </key>
|
||||||
|
- <key name='string' type='s'>
|
||||||
|
- <default>''</default>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
- <schema id='org.gtk.test.extends.extended' extends='org.gtk.test.extends.base'>
|
||||||
|
- <override name="int32">42</override>
|
||||||
|
- <key name='another-int32' type='i'>
|
||||||
|
- <default>0</default>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
- <schema id="org.gtk.test.per-desktop" path="/tests/per-desktop/">
|
||||||
|
- <key name="desktop" type="s">
|
||||||
|
- <default>"GNOME"</default>
|
||||||
|
- </key>
|
||||||
|
- </schema>
|
||||||
|
-
|
||||||
|
-</schemalist>
|
||||||
|
diff -rupN --no-dereference glib-2.78.0/glib/gstdio.c glib-2.78.0-new/glib/gstdio.c
|
||||||
|
--- glib-2.78.0/glib/gstdio.c 2023-09-08 15:42:18.000000000 +0200
|
||||||
|
+++ glib-2.78.0-new/glib/gstdio.c 2023-09-19 11:45:02.396539056 +0200
|
||||||
|
@@ -1052,6 +1052,11 @@ g_open (const gchar *filename,
|
||||||
int mode)
|
int mode)
|
||||||
{
|
{
|
||||||
#ifdef G_OS_WIN32
|
#ifdef G_OS_WIN32
|
||||||
@ -34,7 +248,7 @@ index 6d763e1..c1d072f 100644
|
|||||||
wchar_t *wfilename = g_utf8_to_utf16 (filename, -1, NULL, NULL, NULL);
|
wchar_t *wfilename = g_utf8_to_utf16 (filename, -1, NULL, NULL, NULL);
|
||||||
int retval;
|
int retval;
|
||||||
int save_errno;
|
int save_errno;
|
||||||
@@ -1055,12 +1060,114 @@ g_open (const gchar *filename,
|
@@ -1062,12 +1067,114 @@ g_open (const gchar *filename,
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -55,8 +269,7 @@ index 6d763e1..c1d072f 100644
|
|||||||
+ g_free (wfilename);
|
+ g_free (wfilename);
|
||||||
+ return -1;
|
+ return -1;
|
||||||
+ }
|
+ }
|
||||||
|
+
|
||||||
- g_free (wfilename);
|
|
||||||
+ dwDesiredAccess |= GENERIC_READ;
|
+ dwDesiredAccess |= GENERIC_READ;
|
||||||
+ dwSharedAccess |= FILE_SHARE_WRITE;
|
+ dwSharedAccess |= FILE_SHARE_WRITE;
|
||||||
+ }
|
+ }
|
||||||
@ -68,7 +281,7 @@ index 6d763e1..c1d072f 100644
|
|||||||
+ g_free (wfilename);
|
+ g_free (wfilename);
|
||||||
+ return -1;
|
+ return -1;
|
||||||
+ }
|
+ }
|
||||||
|
+
|
||||||
+ dwDesiredAccess |= GENERIC_WRITE;
|
+ dwDesiredAccess |= GENERIC_WRITE;
|
||||||
+ }
|
+ }
|
||||||
+ if (flags & _O_RDWR)
|
+ if (flags & _O_RDWR)
|
||||||
@ -133,7 +346,8 @@ index 6d763e1..c1d072f 100644
|
|||||||
+ }
|
+ }
|
||||||
+ else
|
+ else
|
||||||
+ retval = _open_osfhandle((long)hFile, flags);
|
+ retval = _open_osfhandle((long)hFile, flags);
|
||||||
+
|
|
||||||
|
- g_free (wfilename);
|
||||||
+ if ((-1) != retval)
|
+ if ((-1) != retval)
|
||||||
+ {
|
+ {
|
||||||
+ /* We have a valid file handle. Set its translation mode to text or binary, as appropriate */
|
+ /* We have a valid file handle. Set its translation mode to text or binary, as appropriate */
|
||||||
@ -144,7 +358,7 @@ index 6d763e1..c1d072f 100644
|
|||||||
+ else
|
+ else
|
||||||
+ _setmode(retval, _O_BINARY);
|
+ _setmode(retval, _O_BINARY);
|
||||||
+ }
|
+ }
|
||||||
+
|
|
||||||
+ save_errno = errno;
|
+ save_errno = errno;
|
||||||
+ g_free (wfilename);
|
+ g_free (wfilename);
|
||||||
errno = save_errno;
|
errno = save_errno;
|
||||||
@ -152,7 +366,7 @@ index 6d763e1..c1d072f 100644
|
|||||||
return retval;
|
return retval;
|
||||||
#else
|
#else
|
||||||
int fd;
|
int fd;
|
||||||
@@ -1108,6 +1215,8 @@ g_creat (const gchar *filename,
|
@@ -1115,6 +1222,8 @@ g_creat (const gchar *filename,
|
||||||
int mode)
|
int mode)
|
||||||
{
|
{
|
||||||
#ifdef G_OS_WIN32
|
#ifdef G_OS_WIN32
|
||||||
@ -161,7 +375,7 @@ index 6d763e1..c1d072f 100644
|
|||||||
wchar_t *wfilename = g_utf8_to_utf16 (filename, -1, NULL, NULL, NULL);
|
wchar_t *wfilename = g_utf8_to_utf16 (filename, -1, NULL, NULL, NULL);
|
||||||
int retval;
|
int retval;
|
||||||
int save_errno;
|
int save_errno;
|
||||||
@@ -1118,12 +1227,41 @@ g_creat (const gchar *filename,
|
@@ -1125,12 +1234,41 @@ g_creat (const gchar *filename,
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -172,8 +386,7 @@ index 6d763e1..c1d072f 100644
|
|||||||
+ if (! (mode & _S_IWRITE))
|
+ if (! (mode & _S_IWRITE))
|
||||||
+ dwFlagsAndAttributes = FILE_ATTRIBUTE_READONLY; /* Sets file to 'read only' after the file gets closed */
|
+ dwFlagsAndAttributes = FILE_ATTRIBUTE_READONLY; /* Sets file to 'read only' after the file gets closed */
|
||||||
+ }
|
+ }
|
||||||
|
+
|
||||||
- g_free (wfilename);
|
|
||||||
+ hFile = CreateFileW(wfilename, (GENERIC_READ | GENERIC_WRITE), (FILE_SHARE_READ | FILE_SHARE_DELETE),
|
+ hFile = CreateFileW(wfilename, (GENERIC_READ | GENERIC_WRITE), (FILE_SHARE_READ | FILE_SHARE_DELETE),
|
||||||
+ NULL, CREATE_ALWAYS, dwFlagsAndAttributes, NULL);
|
+ NULL, CREATE_ALWAYS, dwFlagsAndAttributes, NULL);
|
||||||
+
|
+
|
||||||
@ -200,13 +413,14 @@ index 6d763e1..c1d072f 100644
|
|||||||
+ retval = _open_osfhandle((long)hFile, _O_RDWR);
|
+ retval = _open_osfhandle((long)hFile, _O_RDWR);
|
||||||
|
|
||||||
+ save_errno = errno;
|
+ save_errno = errno;
|
||||||
+ g_free (wfilename);
|
g_free (wfilename);
|
||||||
|
-
|
||||||
errno = save_errno;
|
errno = save_errno;
|
||||||
+
|
+
|
||||||
return retval;
|
return retval;
|
||||||
#else
|
#else
|
||||||
return creat (filename, mode);
|
return creat (filename, mode);
|
||||||
@@ -1565,34 +1703,102 @@ g_fopen (const gchar *filename,
|
@@ -1572,34 +1710,102 @@ g_fopen (const gchar *filename,
|
||||||
const gchar *mode)
|
const gchar *mode)
|
||||||
{
|
{
|
||||||
#ifdef G_OS_WIN32
|
#ifdef G_OS_WIN32
|
||||||
@ -263,7 +477,7 @@ index 6d763e1..c1d072f 100644
|
|||||||
+ if (('c' == priv_mode[2]) || ('n' == priv_mode[2]))
|
+ if (('c' == priv_mode[2]) || ('n' == priv_mode[2]))
|
||||||
+ priv_mode[2] = '\0';
|
+ priv_mode[2] = '\0';
|
||||||
+ else
|
+ else
|
||||||
+ {
|
+ {
|
||||||
+ if (0 == strcmp(priv_mode, "a+b"))
|
+ if (0 == strcmp(priv_mode, "a+b"))
|
||||||
+ flags = _O_RDWR | _O_CREAT | _O_APPEND | _O_BINARY;
|
+ flags = _O_RDWR | _O_CREAT | _O_APPEND | _O_BINARY;
|
||||||
+ else if (0 == strcmp(priv_mode, "a+t"))
|
+ else if (0 == strcmp(priv_mode, "a+t"))
|
||||||
@ -281,14 +495,14 @@ index 6d763e1..c1d072f 100644
|
|||||||
+ errno = EINVAL;
|
+ errno = EINVAL;
|
||||||
+ goto out;
|
+ goto out;
|
||||||
+ }
|
+ }
|
||||||
+ }
|
+ }
|
||||||
+ }
|
+ }
|
||||||
+ if (2 == strlen(priv_mode))
|
+ if (2 == strlen(priv_mode))
|
||||||
+ {
|
+ {
|
||||||
+ if (('c' == priv_mode[1]) || ('n' == priv_mode[1]))
|
+ if (('c' == priv_mode[1]) || ('n' == priv_mode[1]))
|
||||||
+ priv_mode[1] = '\0';
|
+ priv_mode[1] = '\0';
|
||||||
+ else
|
+ else
|
||||||
+ {
|
+ {
|
||||||
+ if (0 == strcmp(priv_mode, "a+"))
|
+ if (0 == strcmp(priv_mode, "a+"))
|
||||||
+ flags = _O_RDWR | _O_CREAT | _O_APPEND;
|
+ flags = _O_RDWR | _O_CREAT | _O_APPEND;
|
||||||
+ else if (0 == strcmp(priv_mode, "ab"))
|
+ else if (0 == strcmp(priv_mode, "ab"))
|
||||||
@ -308,7 +522,7 @@ index 6d763e1..c1d072f 100644
|
|||||||
+ errno = EINVAL;
|
+ errno = EINVAL;
|
||||||
+ goto out;
|
+ goto out;
|
||||||
+ }
|
+ }
|
||||||
+ }
|
+ }
|
||||||
+ }
|
+ }
|
||||||
+ if (1 == strlen(priv_mode))
|
+ if (1 == strlen(priv_mode))
|
||||||
+ {
|
+ {
|
||||||
@ -337,6 +551,3 @@ index 6d763e1..c1d072f 100644
|
|||||||
return retval;
|
return retval;
|
||||||
#else
|
#else
|
||||||
return fopen (filename, mode);
|
return fopen (filename, mode);
|
||||||
--
|
|
||||||
1.7.11.4
|
|
||||||
|
|
||||||
@ -0,0 +1,45 @@
|
|||||||
|
From 25833cefda24c60af913d6f2d532b5afd608b821 Mon Sep 17 00:00:00 2001
|
||||||
|
From: Michael Catanzaro <mcatanzaro@redhat.com>
|
||||||
|
Date: Thu, 19 Sep 2024 18:35:53 +0100
|
||||||
|
Subject: [PATCH] gsocks4aproxy: Fix a single byte buffer overflow in connect
|
||||||
|
messages
|
||||||
|
|
||||||
|
`SOCKS4_CONN_MSG_LEN` failed to account for the length of the final nul
|
||||||
|
byte in the connect message, which is an addition in SOCKSv4a vs
|
||||||
|
SOCKSv4.
|
||||||
|
|
||||||
|
This means that the buffer for building and transmitting the connect
|
||||||
|
message could be overflowed if the username and hostname are both
|
||||||
|
`SOCKS4_MAX_LEN` (255) bytes long.
|
||||||
|
|
||||||
|
Proxy configurations are normally statically configured, so the username
|
||||||
|
is very unlikely to be near its maximum length, and hence this overflow
|
||||||
|
is unlikely to be triggered in practice.
|
||||||
|
|
||||||
|
(Commit message by Philip Withnall, diagnosis and fix by Michael
|
||||||
|
Catanzaro.)
|
||||||
|
|
||||||
|
Fixes: #3461
|
||||||
|
---
|
||||||
|
gio/gsocks4aproxy.c | 4 ++--
|
||||||
|
1 file changed, 2 insertions(+), 2 deletions(-)
|
||||||
|
|
||||||
|
diff --git a/gio/gsocks4aproxy.c b/gio/gsocks4aproxy.c
|
||||||
|
index 3dad118eb7..b3146d08fd 100644
|
||||||
|
--- a/gio/gsocks4aproxy.c
|
||||||
|
+++ b/gio/gsocks4aproxy.c
|
||||||
|
@@ -79,9 +79,9 @@ g_socks4a_proxy_init (GSocks4aProxy *proxy)
|
||||||
|
* +----+----+----+----+----+----+----+----+----+----+....+----+------+....+------+
|
||||||
|
* | VN | CD | DSTPORT | DSTIP | USERID |NULL| HOST | | NULL |
|
||||||
|
* +----+----+----+----+----+----+----+----+----+----+....+----+------+....+------+
|
||||||
|
- * 1 1 2 4 variable 1 variable
|
||||||
|
+ * 1 1 2 4 variable 1 variable 1
|
||||||
|
*/
|
||||||
|
-#define SOCKS4_CONN_MSG_LEN (9 + SOCKS4_MAX_LEN * 2)
|
||||||
|
+#define SOCKS4_CONN_MSG_LEN (10 + SOCKS4_MAX_LEN * 2)
|
||||||
|
static gint
|
||||||
|
set_connect_msg (guint8 *msg,
|
||||||
|
const gchar *hostname,
|
||||||
|
--
|
||||||
|
GitLab
|
||||||
|
|
||||||
@ -0,0 +1,261 @@
|
|||||||
|
From 9bcd65ba5fa1b92ff0fb8380faea335ccef56253 Mon Sep 17 00:00:00 2001
|
||||||
|
From: Philip Withnall <pwithnall@gnome.org>
|
||||||
|
Date: Thu, 13 Nov 2025 18:27:22 +0000
|
||||||
|
Subject: [PATCH 1/2] gconvert: Error out if g_escape_uri_string() would
|
||||||
|
overflow
|
||||||
|
MIME-Version: 1.0
|
||||||
|
Content-Type: text/plain; charset=UTF-8
|
||||||
|
Content-Transfer-Encoding: 8bit
|
||||||
|
|
||||||
|
If the string to escape contains a very large number of unacceptable
|
||||||
|
characters (which would need escaping), the calculation of the length of
|
||||||
|
the escaped string could overflow, leading to a potential write off the
|
||||||
|
end of the newly allocated string.
|
||||||
|
|
||||||
|
In addition to that, the number of unacceptable characters was counted
|
||||||
|
in a signed integer, which would overflow to become negative, making it
|
||||||
|
easier for an attacker to craft an input string which would cause an
|
||||||
|
out-of-bounds write.
|
||||||
|
|
||||||
|
Fix that by validating the allocation length, and using an unsigned
|
||||||
|
integer to count the number of unacceptable characters.
|
||||||
|
|
||||||
|
Spotted by treeplus. Thanks to the Sovereign Tech Resilience programme
|
||||||
|
from the Sovereign Tech Agency. ID: #YWH-PGM9867-134
|
||||||
|
|
||||||
|
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
||||||
|
|
||||||
|
Fixes: #3827
|
||||||
|
|
||||||
|
Backport 2.86: Changed the translatable error message to re-use an
|
||||||
|
existing translatable string, to avoid adding new translatable strings
|
||||||
|
to a stable branch. The re-used string doesn’t perfectly match the
|
||||||
|
error, but it’s good enough given that no users will ever see it.
|
||||||
|
---
|
||||||
|
glib/gconvert.c | 36 +++++++++++++++++++++++++-----------
|
||||||
|
1 file changed, 25 insertions(+), 11 deletions(-)
|
||||||
|
|
||||||
|
diff --git a/glib/gconvert.c b/glib/gconvert.c
|
||||||
|
index 7ad8ca018f..367e9b4661 100644
|
||||||
|
--- a/glib/gconvert.c
|
||||||
|
+++ b/glib/gconvert.c
|
||||||
|
@@ -1336,8 +1336,9 @@ static const gchar hex[] = "0123456789ABCDEF";
|
||||||
|
/* Note: This escape function works on file: URIs, but if you want to
|
||||||
|
* escape something else, please read RFC-2396 */
|
||||||
|
static gchar *
|
||||||
|
-g_escape_uri_string (const gchar *string,
|
||||||
|
- UnsafeCharacterSet mask)
|
||||||
|
+g_escape_uri_string (const gchar *string,
|
||||||
|
+ UnsafeCharacterSet mask,
|
||||||
|
+ GError **error)
|
||||||
|
{
|
||||||
|
#define ACCEPTABLE(a) ((a)>=32 && (a)<128 && (acceptable[(a)-32] & use_mask))
|
||||||
|
|
||||||
|
@@ -1345,7 +1346,7 @@ g_escape_uri_string (const gchar *string,
|
||||||
|
gchar *q;
|
||||||
|
gchar *result;
|
||||||
|
int c;
|
||||||
|
- gint unacceptable;
|
||||||
|
+ size_t unacceptable;
|
||||||
|
UnsafeCharacterSet use_mask;
|
||||||
|
|
||||||
|
g_return_val_if_fail (mask == UNSAFE_ALL
|
||||||
|
@@ -1362,7 +1363,14 @@ g_escape_uri_string (const gchar *string,
|
||||||
|
if (!ACCEPTABLE (c))
|
||||||
|
unacceptable++;
|
||||||
|
}
|
||||||
|
-
|
||||||
|
+
|
||||||
|
+ if (unacceptable >= (G_MAXSIZE - (p - string)) / 2)
|
||||||
|
+ {
|
||||||
|
+ g_set_error_literal (error, G_CONVERT_ERROR, G_CONVERT_ERROR_BAD_URI,
|
||||||
|
+ _("Invalid hostname"));
|
||||||
|
+ return NULL;
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
result = g_malloc (p - string + unacceptable * 2 + 1);
|
||||||
|
|
||||||
|
use_mask = mask;
|
||||||
|
@@ -1387,12 +1395,13 @@ g_escape_uri_string (const gchar *string,
|
||||||
|
|
||||||
|
|
||||||
|
static gchar *
|
||||||
|
-g_escape_file_uri (const gchar *hostname,
|
||||||
|
- const gchar *pathname)
|
||||||
|
+g_escape_file_uri (const gchar *hostname,
|
||||||
|
+ const gchar *pathname,
|
||||||
|
+ GError **error)
|
||||||
|
{
|
||||||
|
char *escaped_hostname = NULL;
|
||||||
|
- char *escaped_path;
|
||||||
|
- char *res;
|
||||||
|
+ char *escaped_path = NULL;
|
||||||
|
+ char *res = NULL;
|
||||||
|
|
||||||
|
#ifdef G_OS_WIN32
|
||||||
|
char *p, *backslash;
|
||||||
|
@@ -1413,10 +1422,14 @@ g_escape_file_uri (const gchar *hostname,
|
||||||
|
|
||||||
|
if (hostname && *hostname != '\0')
|
||||||
|
{
|
||||||
|
- escaped_hostname = g_escape_uri_string (hostname, UNSAFE_HOST);
|
||||||
|
+ escaped_hostname = g_escape_uri_string (hostname, UNSAFE_HOST, error);
|
||||||
|
+ if (escaped_hostname == NULL)
|
||||||
|
+ goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
- escaped_path = g_escape_uri_string (pathname, UNSAFE_PATH);
|
||||||
|
+ escaped_path = g_escape_uri_string (pathname, UNSAFE_PATH, error);
|
||||||
|
+ if (escaped_path == NULL)
|
||||||
|
+ goto out;
|
||||||
|
|
||||||
|
res = g_strconcat ("file://",
|
||||||
|
(escaped_hostname) ? escaped_hostname : "",
|
||||||
|
@@ -1424,6 +1437,7 @@ g_escape_file_uri (const gchar *hostname,
|
||||||
|
escaped_path,
|
||||||
|
NULL);
|
||||||
|
|
||||||
|
+out:
|
||||||
|
#ifdef G_OS_WIN32
|
||||||
|
g_free ((char *) pathname);
|
||||||
|
#endif
|
||||||
|
@@ -1757,7 +1771,7 @@ g_filename_to_uri (const gchar *filename,
|
||||||
|
hostname = NULL;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
- escaped_uri = g_escape_file_uri (hostname, filename);
|
||||||
|
+ escaped_uri = g_escape_file_uri (hostname, filename, error);
|
||||||
|
|
||||||
|
return escaped_uri;
|
||||||
|
}
|
||||||
|
--
|
||||||
|
GitLab
|
||||||
|
|
||||||
|
|
||||||
|
From 7e5489cb921d0531ee4ebc9938da30a02084b2fa Mon Sep 17 00:00:00 2001
|
||||||
|
From: Philip Withnall <pwithnall@gnome.org>
|
||||||
|
Date: Thu, 13 Nov 2025 18:31:43 +0000
|
||||||
|
Subject: [PATCH 2/2] fuzzing: Add fuzz tests for g_filename_{to,from}_uri()
|
||||||
|
|
||||||
|
These functions could be called on untrusted input data, and since they
|
||||||
|
do URI escaping/unescaping, they have non-trivial string handling code.
|
||||||
|
|
||||||
|
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
||||||
|
|
||||||
|
See: #3827
|
||||||
|
---
|
||||||
|
fuzzing/fuzz_filename_from_uri.c | 40 ++++++++++++++++++++++++++++++++
|
||||||
|
fuzzing/fuzz_filename_to_uri.c | 40 ++++++++++++++++++++++++++++++++
|
||||||
|
fuzzing/meson.build | 2 ++
|
||||||
|
3 files changed, 82 insertions(+)
|
||||||
|
create mode 100644 fuzzing/fuzz_filename_from_uri.c
|
||||||
|
create mode 100644 fuzzing/fuzz_filename_to_uri.c
|
||||||
|
|
||||||
|
diff --git a/fuzzing/fuzz_filename_from_uri.c b/fuzzing/fuzz_filename_from_uri.c
|
||||||
|
new file mode 100644
|
||||||
|
index 0000000000..9b7a715f07
|
||||||
|
--- /dev/null
|
||||||
|
+++ b/fuzzing/fuzz_filename_from_uri.c
|
||||||
|
@@ -0,0 +1,40 @@
|
||||||
|
+/*
|
||||||
|
+ * Copyright 2025 GNOME Foundation, Inc.
|
||||||
|
+ *
|
||||||
|
+ * SPDX-License-Identifier: LGPL-2.1-or-later
|
||||||
|
+ *
|
||||||
|
+ * This library is free software; you can redistribute it and/or
|
||||||
|
+ * modify it under the terms of the GNU Lesser General Public
|
||||||
|
+ * License as published by the Free Software Foundation; either
|
||||||
|
+ * version 2.1 of the License, or (at your option) any later version.
|
||||||
|
+ *
|
||||||
|
+ * This library is distributed in the hope that it will be useful,
|
||||||
|
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||||
|
+ * Lesser General Public License for more details.
|
||||||
|
+ *
|
||||||
|
+ * You should have received a copy of the GNU Lesser General Public
|
||||||
|
+ * License along with this library; if not, see <http://www.gnu.org/licenses/>.
|
||||||
|
+ */
|
||||||
|
+
|
||||||
|
+#include "fuzz.h"
|
||||||
|
+
|
||||||
|
+int
|
||||||
|
+LLVMFuzzerTestOneInput (const unsigned char *data, size_t size)
|
||||||
|
+{
|
||||||
|
+ unsigned char *nul_terminated_data = NULL;
|
||||||
|
+ char *filename = NULL;
|
||||||
|
+ GError *local_error = NULL;
|
||||||
|
+
|
||||||
|
+ fuzz_set_logging_func ();
|
||||||
|
+
|
||||||
|
+ /* ignore @size (g_filename_from_uri() doesn’t support it); ensure @data is nul-terminated */
|
||||||
|
+ nul_terminated_data = (unsigned char *) g_strndup ((const char *) data, size);
|
||||||
|
+ filename = g_filename_from_uri ((const char *) nul_terminated_data, NULL, &local_error);
|
||||||
|
+ g_free (nul_terminated_data);
|
||||||
|
+
|
||||||
|
+ g_free (filename);
|
||||||
|
+ g_clear_error (&local_error);
|
||||||
|
+
|
||||||
|
+ return 0;
|
||||||
|
+}
|
||||||
|
diff --git a/fuzzing/fuzz_filename_to_uri.c b/fuzzing/fuzz_filename_to_uri.c
|
||||||
|
new file mode 100644
|
||||||
|
index 0000000000..acb3192035
|
||||||
|
--- /dev/null
|
||||||
|
+++ b/fuzzing/fuzz_filename_to_uri.c
|
||||||
|
@@ -0,0 +1,40 @@
|
||||||
|
+/*
|
||||||
|
+ * Copyright 2025 GNOME Foundation, Inc.
|
||||||
|
+ *
|
||||||
|
+ * SPDX-License-Identifier: LGPL-2.1-or-later
|
||||||
|
+ *
|
||||||
|
+ * This library is free software; you can redistribute it and/or
|
||||||
|
+ * modify it under the terms of the GNU Lesser General Public
|
||||||
|
+ * License as published by the Free Software Foundation; either
|
||||||
|
+ * version 2.1 of the License, or (at your option) any later version.
|
||||||
|
+ *
|
||||||
|
+ * This library is distributed in the hope that it will be useful,
|
||||||
|
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||||
|
+ * Lesser General Public License for more details.
|
||||||
|
+ *
|
||||||
|
+ * You should have received a copy of the GNU Lesser General Public
|
||||||
|
+ * License along with this library; if not, see <http://www.gnu.org/licenses/>.
|
||||||
|
+ */
|
||||||
|
+
|
||||||
|
+#include "fuzz.h"
|
||||||
|
+
|
||||||
|
+int
|
||||||
|
+LLVMFuzzerTestOneInput (const unsigned char *data, size_t size)
|
||||||
|
+{
|
||||||
|
+ unsigned char *nul_terminated_data = NULL;
|
||||||
|
+ char *uri = NULL;
|
||||||
|
+ GError *local_error = NULL;
|
||||||
|
+
|
||||||
|
+ fuzz_set_logging_func ();
|
||||||
|
+
|
||||||
|
+ /* ignore @size (g_filename_to_uri() doesn’t support it); ensure @data is nul-terminated */
|
||||||
|
+ nul_terminated_data = (unsigned char *) g_strndup ((const char *) data, size);
|
||||||
|
+ uri = g_filename_to_uri ((const char *) nul_terminated_data, NULL, &local_error);
|
||||||
|
+ g_free (nul_terminated_data);
|
||||||
|
+
|
||||||
|
+ g_free (uri);
|
||||||
|
+ g_clear_error (&local_error);
|
||||||
|
+
|
||||||
|
+ return 0;
|
||||||
|
+}
|
||||||
|
diff --git a/fuzzing/meson.build b/fuzzing/meson.build
|
||||||
|
index addbe90717..05f936eeb2 100644
|
||||||
|
--- a/fuzzing/meson.build
|
||||||
|
+++ b/fuzzing/meson.build
|
||||||
|
@@ -25,6 +25,8 @@ fuzz_targets = [
|
||||||
|
'fuzz_date_parse',
|
||||||
|
'fuzz_date_time_new_from_iso8601',
|
||||||
|
'fuzz_dbus_message',
|
||||||
|
+ 'fuzz_filename_from_uri',
|
||||||
|
+ 'fuzz_filename_to_uri',
|
||||||
|
'fuzz_inet_address_mask_new_from_string',
|
||||||
|
'fuzz_inet_address_new_from_string',
|
||||||
|
'fuzz_inet_socket_address_new_from_string',
|
||||||
|
--
|
||||||
|
GitLab
|
||||||
|
|
||||||
@ -1,43 +1,39 @@
|
|||||||
%?mingw_package_header
|
%{?mingw_package_header}
|
||||||
|
|
||||||
# See https://fedoraproject.org/wiki/Packaging:Python_Appendix#Manual_byte_compilation
|
|
||||||
%global __python %{__python3}
|
|
||||||
|
|
||||||
Name: mingw-glib2
|
Name: mingw-glib2
|
||||||
Version: 2.70.1
|
Version: 2.78.6
|
||||||
Release: 9%{?dist}
|
Release: 3%{?dist}
|
||||||
Summary: MinGW Windows GLib2 library
|
Summary: MinGW Windows GLib2 library
|
||||||
|
|
||||||
License: LGPLv2+
|
License: LGPL-2.0-or-later
|
||||||
URL: http://www.gtk.org
|
URL: http://www.gtk.org
|
||||||
# first two digits of version
|
# first two digits of version
|
||||||
%global release_version %(echo %{version} | awk -F. '{print $1"."$2}')
|
%global release_version %(echo %{version} | awk -F. '{print $1"."$2}')
|
||||||
Source0: http://download.gnome.org/sources/glib/%{release_version}/glib-%{version}.tar.xz
|
Source0: http://download.gnome.org/sources/glib/%{release_version}/glib-%{version}.tar.xz
|
||||||
|
|
||||||
BuildArch: noarch
|
BuildArch: noarch
|
||||||
ExclusiveArch: %{ix86} x86_64
|
|
||||||
|
|
||||||
BuildRequires: meson
|
BuildRequires: meson
|
||||||
BuildRequires: gcc
|
BuildRequires: gcc
|
||||||
BuildRequires: gcc-c++
|
BuildRequires: gcc-c++
|
||||||
|
|
||||||
BuildRequires: mingw32-filesystem >= 104
|
BuildRequires: mingw32-filesystem >= 107
|
||||||
BuildRequires: mingw32-gcc
|
BuildRequires: mingw32-gcc
|
||||||
BuildRequires: mingw32-binutils
|
BuildRequires: mingw32-binutils
|
||||||
BuildRequires: mingw32-win-iconv
|
BuildRequires: mingw32-win-iconv
|
||||||
BuildRequires: mingw32-gettext
|
BuildRequires: mingw32-gettext
|
||||||
BuildRequires: mingw32-libffi
|
BuildRequires: mingw32-libffi
|
||||||
BuildRequires: mingw32-pcre
|
BuildRequires: mingw32-pcre2
|
||||||
BuildRequires: mingw32-zlib
|
BuildRequires: mingw32-zlib >= 1.2.13
|
||||||
|
|
||||||
BuildRequires: mingw64-filesystem >= 104
|
BuildRequires: mingw64-filesystem >= 107
|
||||||
BuildRequires: mingw64-gcc
|
BuildRequires: mingw64-gcc
|
||||||
BuildRequires: mingw64-binutils
|
BuildRequires: mingw64-binutils
|
||||||
BuildRequires: mingw64-win-iconv
|
BuildRequires: mingw64-win-iconv
|
||||||
BuildRequires: mingw64-gettext
|
BuildRequires: mingw64-gettext
|
||||||
BuildRequires: mingw64-libffi
|
BuildRequires: mingw64-libffi
|
||||||
BuildRequires: mingw64-pcre
|
BuildRequires: mingw64-pcre2
|
||||||
BuildRequires: mingw64-zlib
|
BuildRequires: mingw64-zlib >= 1.2.13
|
||||||
|
|
||||||
# Native version required for msgfmt use in build
|
# Native version required for msgfmt use in build
|
||||||
BuildRequires: gettext
|
BuildRequires: gettext
|
||||||
@ -48,37 +44,22 @@ BuildRequires: python3-devel
|
|||||||
# https://bugzilla.gnome.org/show_bug.cgi?id=674214
|
# https://bugzilla.gnome.org/show_bug.cgi?id=674214
|
||||||
Patch1: 0001-Use-CreateFile-on-Win32-to-make-sure-g_unlink-always.patch
|
Patch1: 0001-Use-CreateFile-on-Win32-to-make-sure-g_unlink-always.patch
|
||||||
|
|
||||||
|
# https://issues.redhat.com/browse/RHEL-67089
|
||||||
|
# https://gitlab.gnome.org/GNOME/glib/-/issues/3461
|
||||||
|
Patch2: CVE-2024-52533-buffer-overflow-in-set_connect_msg.patch
|
||||||
|
|
||||||
|
# https://issues.redhat.com/browse/RHEL-131012
|
||||||
|
# https://gitlab.gnome.org/GNOME/glib/-/issues/3827
|
||||||
|
# https://gitlab.gnome.org/GNOME/glib/-/merge_requests/4914
|
||||||
|
# https://gitlab.gnome.org/GNOME/glib/-/merge_requests/4915
|
||||||
|
Patch3: CVE-2025-13601-gconvert-Error-out-if-g_escape_uri_string-would-overflow.patch
|
||||||
|
|
||||||
# Prefer the use of GCC constructors over DllMain
|
# Prefer the use of GCC constructors over DllMain
|
||||||
# This prevents having to depend on DllMain in static libraries
|
# This prevents having to depend on DllMain in static libraries
|
||||||
# http://lists.fedoraproject.org/pipermail/mingw/2013-March/006429.html
|
# http://lists.fedoraproject.org/pipermail/mingw/2013-March/006429.html
|
||||||
# http://lists.fedoraproject.org/pipermail/mingw/2013-March/006469.html
|
# http://lists.fedoraproject.org/pipermail/mingw/2013-March/006469.html
|
||||||
# https://bugzilla.gnome.org/show_bug.cgi?id=698118
|
# https://bugzilla.gnome.org/show_bug.cgi?id=698118
|
||||||
Patch2: glib-prefer-constructors-over-DllMain.patch
|
#Patch5: glib-prefer-constructors-over-DllMain.patch
|
||||||
|
|
||||||
# https://gitlab.gnome.org/GNOME/glib/-/merge_requests/5172
|
|
||||||
Patch3: mingw-glib2-2.70.1-CVE-2026-58015.patch
|
|
||||||
|
|
||||||
# CVE-2026-58014: one-byte heap under-read with g_key_file_get_locale_string_list()
|
|
||||||
# https://gitlab.gnome.org/GNOME/glib/-/merge_requests/5171
|
|
||||||
Patch4: mingw-glib2-2.70.1-CVE-2026-58014.patch
|
|
||||||
|
|
||||||
# https://github.com/GNOME/glib/commit/c9da977c178f
|
|
||||||
Patch5: mingw-glib2-2.70.1-CVE-2026-58016.patch
|
|
||||||
|
|
||||||
# https://github.com/GNOME/glib/commit/31f82e22e21bae520b7228f7f57d357fb20df8a4
|
|
||||||
Patch6: mingw-glib2-2.70.1-CVE-2025-14087.patch
|
|
||||||
|
|
||||||
# https://gitlab.gnome.org/GNOME/glib/-/issues/3918
|
|
||||||
Patch7: mingw-glib2-2.70.1-CVE-2026-58012.patch
|
|
||||||
|
|
||||||
# https://gitlab.gnome.org/GNOME/glib/-/work_items/3925
|
|
||||||
Patch8: mingw-glib2-2.70.1-CVE-2026-58013.patch
|
|
||||||
|
|
||||||
# https://gitlab.gnome.org/GNOME/glib/-/issues/3917
|
|
||||||
Patch9: mingw-glib2-2.70.1-CVE-2026-58011.patch
|
|
||||||
|
|
||||||
# https://gitlab.gnome.org/GNOME/glib/-/issues/3915
|
|
||||||
Patch10: mingw-glib2-2.70.1-CVE-2026-58010.patch
|
|
||||||
|
|
||||||
%description
|
%description
|
||||||
MinGW Windows Glib2 library.
|
MinGW Windows Glib2 library.
|
||||||
@ -87,8 +68,7 @@ MinGW Windows Glib2 library.
|
|||||||
%package -n mingw32-glib2
|
%package -n mingw32-glib2
|
||||||
Summary: MinGW Windows Glib2 library for the win32 target
|
Summary: MinGW Windows Glib2 library for the win32 target
|
||||||
# glib-genmarshal and glib-mkenums are written in Python
|
# glib-genmarshal and glib-mkenums are written in Python
|
||||||
# plataform-python due: https://bugzilla.redhat.com/show_bug.cgi?id=1633614
|
Requires: python3
|
||||||
Requires: platform-python
|
|
||||||
|
|
||||||
%description -n mingw32-glib2
|
%description -n mingw32-glib2
|
||||||
MinGW Windows Glib2 library.
|
MinGW Windows Glib2 library.
|
||||||
@ -105,8 +85,7 @@ Static version of the MinGW Windows GLib2 library.
|
|||||||
%package -n mingw64-glib2
|
%package -n mingw64-glib2
|
||||||
Summary: MinGW Windows Glib2 library for the win64 target
|
Summary: MinGW Windows Glib2 library for the win64 target
|
||||||
# glib-genmarshal and glib-mkenums are written in Python
|
# glib-genmarshal and glib-mkenums are written in Python
|
||||||
# plataform-python due: https://bugzilla.redhat.com/show_bug.cgi?id=1633614
|
Requires: python3
|
||||||
Requires: platform-python
|
|
||||||
|
|
||||||
%description -n mingw64-glib2
|
%description -n mingw64-glib2
|
||||||
MinGW Windows Glib2 library.
|
MinGW Windows Glib2 library.
|
||||||
@ -120,30 +99,25 @@ Requires: mingw64-gettext-static
|
|||||||
Static version of the MinGW Windows GLib2 library.
|
Static version of the MinGW Windows GLib2 library.
|
||||||
|
|
||||||
|
|
||||||
%?mingw_debug_package
|
%{?mingw_debug_package}
|
||||||
|
|
||||||
|
|
||||||
%prep
|
%prep
|
||||||
%setup -q -n glib-%{version}
|
%autosetup -p1 -n glib-%{version}
|
||||||
%patch1 -p1
|
|
||||||
%patch2 -p1
|
|
||||||
%patch3 -p1
|
|
||||||
%patch4 -p1
|
|
||||||
%patch5 -p1
|
|
||||||
%patch6 -p1
|
|
||||||
%patch7 -p1
|
|
||||||
%patch8 -p1
|
|
||||||
%patch9 -p1
|
|
||||||
%patch10 -p1
|
|
||||||
|
|
||||||
%build
|
%build
|
||||||
%mingw_meson --default-library=both \
|
export MINGW_BUILDDIR_SUFFIX=static
|
||||||
--buildtype=release
|
%mingw_meson --default-library=static
|
||||||
|
%mingw_ninja
|
||||||
|
export MINGW_BUILDDIR_SUFFIX=shared
|
||||||
|
%mingw_meson --default-library=shared
|
||||||
%mingw_ninja
|
%mingw_ninja
|
||||||
|
|
||||||
%install
|
%install
|
||||||
export DESTDIR=$RPM_BUILD_ROOT
|
export MINGW_BUILDDIR_SUFFIX=static
|
||||||
%mingw_ninja install
|
%mingw_ninja_install
|
||||||
|
export MINGW_BUILDDIR_SUFFIX=shared
|
||||||
|
%mingw_ninja_install
|
||||||
|
|
||||||
# There's a small difference in the file glibconfig.h between the
|
# There's a small difference in the file glibconfig.h between the
|
||||||
# shared and the static build:
|
# shared and the static build:
|
||||||
@ -167,37 +141,39 @@ export DESTDIR=$RPM_BUILD_ROOT
|
|||||||
# and -DGOBJECT_STATIC_COMPILATION to their CFLAGS to avoid compile failures
|
# and -DGOBJECT_STATIC_COMPILATION to their CFLAGS to avoid compile failures
|
||||||
|
|
||||||
# Drop the folder which was temporary used for installing the static bits
|
# Drop the folder which was temporary used for installing the static bits
|
||||||
rm -f $RPM_BUILD_ROOT/%{mingw32_libdir}/charset.alias
|
rm -f %{buildroot}/%{mingw32_libdir}/charset.alias
|
||||||
rm -f $RPM_BUILD_ROOT/%{mingw64_libdir}/charset.alias
|
rm -f %{buildroot}/%{mingw64_libdir}/charset.alias
|
||||||
|
|
||||||
# Drop the GDB helper files as we can't use the native Fedora GDB to debug Win32 programs
|
# Drop the GDB helper files as we can't use the native Fedora GDB to debug Win32 programs
|
||||||
rm -rf $RPM_BUILD_ROOT%{mingw32_datadir}/gdb
|
rm -rf %{buildroot}%{mingw32_datadir}/gdb
|
||||||
rm -rf $RPM_BUILD_ROOT%{mingw64_datadir}/gdb
|
rm -rf %{buildroot}%{mingw64_datadir}/gdb
|
||||||
|
|
||||||
# Remove the gtk-doc documentation and manpages which duplicate Fedora native
|
# Remove the gtk-doc documentation and manpages which duplicate Fedora native
|
||||||
rm -rf $RPM_BUILD_ROOT%{mingw32_mandir}
|
rm -rf %{buildroot}%{mingw32_mandir}
|
||||||
rm -rf $RPM_BUILD_ROOT%{mingw32_datadir}/gtk-doc
|
rm -rf %{buildroot}%{mingw32_datadir}/gtk-doc
|
||||||
|
|
||||||
rm -rf $RPM_BUILD_ROOT%{mingw64_mandir}
|
rm -rf %{buildroot}%{mingw64_mandir}
|
||||||
rm -rf $RPM_BUILD_ROOT%{mingw64_datadir}/gtk-doc
|
rm -rf %{buildroot}%{mingw64_datadir}/gtk-doc
|
||||||
|
|
||||||
# Bash-completion files aren't interesting for mingw
|
# Bash-completion files aren't interesting for mingw
|
||||||
rm -rf $RPM_BUILD_ROOT%{mingw32_datadir}/bash-completion
|
rm -rf %{buildroot}%{mingw32_datadir}/bash-completion
|
||||||
rm -rf $RPM_BUILD_ROOT%{mingw64_datadir}/bash-completion
|
rm -rf %{buildroot}%{mingw64_datadir}/bash-completion
|
||||||
|
|
||||||
# The .def files are also of no use to other binaries
|
# The .def files are also of no use to other binaries
|
||||||
rm -f $RPM_BUILD_ROOT%{mingw32_libdir}/*.def
|
rm -f %{buildroot}%{mingw32_libdir}/*.def
|
||||||
rm -f $RPM_BUILD_ROOT%{mingw64_libdir}/*.def
|
rm -f %{buildroot}%{mingw64_libdir}/*.def
|
||||||
|
|
||||||
# The gdbus-codegen pieces are already in the native glib2 package
|
# The gdbus-codegen pieces are already in the native glib2 package
|
||||||
rm -f $RPM_BUILD_ROOT%{mingw32_bindir}/gdbus-codegen
|
rm -f %{buildroot}%{mingw32_bindir}/gdbus-codegen
|
||||||
rm -rf $RPM_BUILD_ROOT%{mingw32_libdir}/gdbus-2.0
|
rm -rf %{buildroot}%{mingw32_libdir}/gdbus-2.0
|
||||||
|
sed -i 's|gdbus_codegen=.*|gdbus_codegen=%{_bindir}/gdbus-codegen|g' %{buildroot}%{mingw32_libdir}/pkgconfig/gio-2.0.pc
|
||||||
|
|
||||||
rm -f $RPM_BUILD_ROOT%{mingw64_bindir}/gdbus-codegen
|
rm -f %{buildroot}%{mingw64_bindir}/gdbus-codegen
|
||||||
rm -rf $RPM_BUILD_ROOT%{mingw64_libdir}/gdbus-2.0
|
rm -rf %{buildroot}%{mingw64_libdir}/gdbus-2.0
|
||||||
|
sed -i 's|gdbus_codegen=.*|gdbus_codegen=%{_bindir}/gdbus-codegen|g' %{buildroot}%{mingw64_libdir}/pkgconfig/gio-2.0.pc
|
||||||
|
|
||||||
# Drop all .la files
|
# Drop all .la files
|
||||||
find $RPM_BUILD_ROOT -name "*.la" -delete
|
find %{buildroot} -name "*.la" -delete
|
||||||
|
|
||||||
%mingw_find_lang glib20
|
%mingw_find_lang glib20
|
||||||
|
|
||||||
@ -208,6 +184,7 @@ find $RPM_BUILD_ROOT -name "*.la" -delete
|
|||||||
%py_byte_compile %{__python3} %{buildroot}%{mingw64_datadir}/glib-2.0/gdb
|
%py_byte_compile %{__python3} %{buildroot}%{mingw64_datadir}/glib-2.0/gdb
|
||||||
%py_byte_compile %{__python3} %{buildroot}%{mingw64_datadir}/glib-2.0/codegen
|
%py_byte_compile %{__python3} %{buildroot}%{mingw64_datadir}/glib-2.0/codegen
|
||||||
|
|
||||||
|
|
||||||
# Win32
|
# Win32
|
||||||
%files -n mingw32-glib2 -f mingw32-glib20.lang
|
%files -n mingw32-glib2 -f mingw32-glib20.lang
|
||||||
%license COPYING
|
%license COPYING
|
||||||
@ -312,65 +289,148 @@ find $RPM_BUILD_ROOT -name "*.la" -delete
|
|||||||
|
|
||||||
|
|
||||||
%changelog
|
%changelog
|
||||||
* Wed Jul 22 2026 RHEL Packaging Agent <redhat-ymir-agent@redhat.com> - 2.70.1-9
|
* Mon Dec 8 2025 Konstantin Kostiuk <kkostiuk@redhat.com> - 2.78.6-3
|
||||||
- Fix CVE-2026-58010: off-by-one error in gvs_tuple_is_normal()
|
- Resolves: RHEL-131012 - CVE-2025-13601 mingw-glib2: Integer overflow in in g_escape_uri_string()
|
||||||
Resolves: RHEL-212164
|
|
||||||
|
|
||||||
* Wed Jul 22 2026 RHEL Packaging Agent <redhat-ymir-agent@redhat.com> - 2.70.1-8
|
* Tue Nov 26 2024 Konstantin Kostiuk <kkostiuk@redhat.com> - 2.78.6-2
|
||||||
- Fix CVE-2026-58011: g_date_time_add_full() range validation
|
- Resolves: RHEL-67088 - CVE-2024-52533 mingw-glib2: buffer overflow in set_connect_msg()
|
||||||
Resolves: RHEL-212184
|
|
||||||
|
|
||||||
* Wed Jul 22 2026 RHEL Packaging Agent <redhat-ymir-agent@redhat.com> - 2.70.1-7
|
* Tue May 21 2024 Konstantin Kostiuk <kkostiuk@redhat.com> - 2.78.6-1
|
||||||
- Fix CVE-2026-58013: memcmp buffer over-read in giochannel
|
- Bump glib2 version 2.78.6
|
||||||
Resolves: RHEL-212234
|
- Fix CVEs: CVE-2024-34397
|
||||||
|
- Resolves: RHEL-35776
|
||||||
|
|
||||||
* Wed Jul 22 2026 RHEL Packaging Agent <redhat-ymir-agent@redhat.com> - 2.70.1-6
|
* Thu Oct 26 2023 Konstantin Kostiuk <kkostiuk@redhat.com> - 2.78.0-1
|
||||||
- Fix CVE-2026-58012: buffer overflow in gregex substitutions
|
- Bump glib2 version 2.78.0
|
||||||
Resolves: RHEL-212200
|
- Drop DesktopQE gating
|
||||||
|
- Fix CVEs: CVE-2023-32636, CVE-2023-29499, CVE-2023-32611, CVE-2023-32665, DoS
|
||||||
|
- Resolves: RHEL-5019
|
||||||
|
- Resolves: RHEL-5020
|
||||||
|
- Resolves: RHEL-5092
|
||||||
|
- Resolves: RHEL-5093
|
||||||
|
- Resolves: RHEL-5094
|
||||||
|
|
||||||
* Wed Jul 22 2026 RHEL Packaging Agent <redhat-ymir-agent@redhat.com> - 2.70.1-5
|
* Mon Aug 7 2023 Konstantin Kostiuk <kkostiuk@redhat.com> - 2.70.1-4
|
||||||
- Fix CVE-2025-14087: integer overflow in GVariant parser
|
- Fix Glib2 build
|
||||||
Resolves: RHEL-154707
|
- Resolves: RHEL-1056
|
||||||
|
|
||||||
* Wed Jul 22 2026 RHEL Packaging Agent <redhat-ymir-agent@redhat.com> - 2.70.1-4
|
* Mon Aug 7 2023 Konstantin Kostiuk <kkostiuk@redhat.com> - 2.70.1-3
|
||||||
- Fix CVE-2026-58016: D-Bus introspection XML node nesting check
|
- Update license to SPDX format
|
||||||
Resolves: RHEL-190617
|
- Resolves: RHEL-1056
|
||||||
|
|
||||||
* Wed Jul 22 2026 RHEL Packaging Agent <redhat-ymir-agent@redhat.com> - 2.70.1-3
|
* Mon Aug 08 2022 Konstantin Kostiuk <kkostiuk@redhat.com> - 2.70.1-2
|
||||||
- Fix CVE-2026-58014: one-byte heap under-read in mingw-glib2
|
- Rebuild for mingw-zlib update
|
||||||
Resolves: RHEL-190609
|
resolves: rhbz#2116278
|
||||||
|
|
||||||
* Mon Jul 20 2026 RHEL Packaging Agent <redhat-ymir-agent@redhat.com> - 2.70.1-2
|
* Mon Oct 04 2021 Richard W.M. Jones <rjones@redhat.com> - 2.66.7-4
|
||||||
- Fix CVE-2026-58015: D-Bus cookie context path traversal
|
- Rebuild for changed mingw-libffi soname
|
||||||
Resolves: RHEL-212246
|
resolves: rhbz#2009943
|
||||||
|
|
||||||
* Thu Dec 23 2021 Yan Vugenfirer <yvugenfi@redhat.com> 2.70.1-1
|
* Mon Aug 09 2021 Mohan Boddu <mboddu@redhat.com> - 2.66.7-3
|
||||||
- Update to 2.70.1
|
- Rebuilt for IMA sigs, glibc 2.34, aarch64 flags
|
||||||
- Resolves: rhbz#2034959
|
Related: rhbz#1991688
|
||||||
|
|
||||||
* Thu Aug 05 2021 Uri Lublin <uril@redhat.com> - 2.66.7-2
|
* Fri Apr 16 2021 Mohan Boddu <mboddu@redhat.com> - 2.66.7-2
|
||||||
- Rebuilt
|
- Rebuilt for RHEL 9 BETA on Apr 15th 2021. Related: rhbz#1947937
|
||||||
Resolves: rhbz#1939111 (CVE-2021-27219)
|
|
||||||
Resolves: rhbz#1935248
|
|
||||||
|
|
||||||
* Sun Feb 21 2021 Basil Salman <bsalman@redhat.com> - 2.66.7-1
|
* Fri Mar 05 2021 Sandro Mani <manisandro@gmail.com> - 2.66.7-1
|
||||||
- Update to 2.66.7
|
- Update to 2.66.7
|
||||||
- Rebuild from newer version that fixes CVE-2021-27219
|
|
||||||
- Resolves: rhbz#1928649
|
|
||||||
|
|
||||||
* Tue Feb 16 2021 Basil Salman <bsalman@redhat.com> - 2.66.4-1
|
* Tue Jan 26 2021 Fedora Release Engineering <releng@fedoraproject.org> - 2.66.2-2
|
||||||
- Update to 2.66.4
|
- Rebuilt for https://fedoraproject.org/wiki/Fedora_34_Mass_Rebuild
|
||||||
- Dropped upstreamed patches
|
|
||||||
- Switched to meson
|
|
||||||
Resolves: rhbz#1928649
|
|
||||||
|
|
||||||
* Thu Sep 27 2018 Victor Toso <victortoso@redhat.com> - 2.56.1-3
|
* Mon Oct 19 2020 Sandro Mani <manisandro@gmail.com> - 2.66.2-1
|
||||||
- Use platform-python in Require
|
- Update to 2.66.2
|
||||||
Related: rhbz#1633614
|
|
||||||
|
|
||||||
* Thu Aug 16 2018 Snir Sheriber <ssheribe@redhat.com> - 2.56.1-2
|
* Mon Oct 05 2020 Sandro Mani <manisandro@gmail.com> - 2.66.1-1
|
||||||
- ExclusiveArch: i686, x86_64
|
- Update to 2.66.1
|
||||||
Related: rhbz#1615874
|
|
||||||
|
* Tue Sep 15 2020 Sandro Mani <manisandro@gmail.com> - 2.66.0-1
|
||||||
|
- Update to 2.66.0
|
||||||
|
|
||||||
|
* Wed Aug 12 13:36:55 GMT 2020 Sandro Mani <manisandro@gmail.com> - 2.64.3-3
|
||||||
|
- Rebuild (mingw-gettext)
|
||||||
|
|
||||||
|
* Tue Jul 28 2020 Fedora Release Engineering <releng@fedoraproject.org> - 2.64.3-2
|
||||||
|
- Rebuilt for https://fedoraproject.org/wiki/Fedora_33_Mass_Rebuild
|
||||||
|
|
||||||
|
* Fri May 22 2020 Sandro Mani <manisandro@gmail.com> - 2.64.3-1
|
||||||
|
- Update to 2.64.3
|
||||||
|
|
||||||
|
* Mon Apr 20 2020 Sandro Mani <manisandro@gmail.com> - 2.64.2-2
|
||||||
|
- Rebuild (gettext)
|
||||||
|
|
||||||
|
* Sat Apr 11 2020 Sandro Mani <manisandro@gmail.com> - 2.64.2-1
|
||||||
|
- Update to 2.64.2
|
||||||
|
|
||||||
|
* Thu Mar 12 2020 Sandro Mani <manisandro@gmail.com> - 2.64.1-1
|
||||||
|
- Update to 2.64.1
|
||||||
|
|
||||||
|
* Fri Mar 06 2020 Sandro Mani <manisandro@gmail.com> - 2.64.0-1
|
||||||
|
- Update to 2.64.0
|
||||||
|
|
||||||
|
* Tue Feb 25 2020 Sandro Mani <manisandro@gmail.com> - 2.63.6-1
|
||||||
|
- Update to 2.63.6
|
||||||
|
|
||||||
|
* Tue Feb 11 2020 Sandro Mani <manisandro@gmail.com> - 2.63.5-2
|
||||||
|
- Backport proposed patch for CVE-2020-6750
|
||||||
|
|
||||||
|
* Mon Feb 03 2020 Sandro Mani <manisandro@gmail.com> - 2.63.5-1
|
||||||
|
- Update to 2.63.5
|
||||||
|
|
||||||
|
* Wed Jan 29 2020 Fedora Release Engineering <releng@fedoraproject.org> - 2.63.4-2
|
||||||
|
- Rebuilt for https://fedoraproject.org/wiki/Fedora_32_Mass_Rebuild
|
||||||
|
|
||||||
|
* Fri Jan 24 2020 Sandro Mani <manisandro@gmail.com> - 2.63.4-1
|
||||||
|
- Update to 2.63.4
|
||||||
|
|
||||||
|
* Mon Dec 16 2019 Sandro Mani <manisandro@gmail.com> - 2.63.3-1
|
||||||
|
- Update to 2.63.3
|
||||||
|
|
||||||
|
* Tue Dec 03 2019 Sandro Mani <manisandro@gmail.com> - 2.63.2-1
|
||||||
|
- Update to 2.63.2
|
||||||
|
|
||||||
|
* Tue Oct 08 2019 Sandro Mani <manisandro@gmail.com> - 2.63.0-2
|
||||||
|
- Rebuild (Changes/Mingw32GccDwarf2)
|
||||||
|
|
||||||
|
* Fri Oct 04 2019 Sandro Mani <manisandro@gmail.com> - 2.63.0-1
|
||||||
|
- Update to 2.63.0
|
||||||
|
|
||||||
|
* Mon Sep 16 2019 Sandro Mani <manisandro@gmail.com> - 2.62.0-1
|
||||||
|
- Update to 2.62.0
|
||||||
|
|
||||||
|
* Wed Sep 04 2019 Sandro Mani <manisandro@gmail.com> - 2.61.3-1
|
||||||
|
- Update to 2.61.3
|
||||||
|
|
||||||
|
* Thu Aug 15 2019 Fabiano Fidêncio <fidencio@redhat.com> - 2.61.2-1
|
||||||
|
- Update to 2.61.2
|
||||||
|
|
||||||
|
* Thu Jul 25 2019 Fedora Release Engineering <releng@fedoraproject.org> - 2.58.3-3
|
||||||
|
- Rebuilt for https://fedoraproject.org/wiki/Fedora_31_Mass_Rebuild
|
||||||
|
|
||||||
|
* Fri Feb 01 2019 Fedora Release Engineering <releng@fedoraproject.org> - 2.58.3-2
|
||||||
|
- Rebuilt for https://fedoraproject.org/wiki/Fedora_30_Mass_Rebuild
|
||||||
|
|
||||||
|
* Tue Jan 22 2019 Kalev Lember <klember@redhat.com> - 2.58.3-1
|
||||||
|
- Update to 2.58.3
|
||||||
|
|
||||||
|
* Tue Jan 08 2019 Kalev Lember <klember@redhat.com> - 2.58.2-1
|
||||||
|
- Update to 2.58.2
|
||||||
|
|
||||||
|
* Fri Sep 21 2018 Kalev Lember <klember@redhat.com> - 2.58.1-1
|
||||||
|
- Update to 2.58.1
|
||||||
|
|
||||||
|
* Thu Aug 02 2018 Thomas Sailer <t.sailer@alumni.ethz.ch> - 2.57.2-1
|
||||||
|
- Update to 2.57.2
|
||||||
|
|
||||||
|
* Thu Aug 02 2018 Thomas Sailer <t.sailer@alumni.ethz.ch> - 2.57.1-1
|
||||||
|
- Update to 2.57.1
|
||||||
|
|
||||||
|
* Fri Jul 13 2018 Fedora Release Engineering <releng@fedoraproject.org> - 2.56.1-3
|
||||||
|
- Rebuilt for https://fedoraproject.org/wiki/Fedora_29_Mass_Rebuild
|
||||||
|
|
||||||
|
* Tue Jun 19 2018 Miro Hrončok <mhroncok@redhat.com> - 2.56.1-2
|
||||||
|
- Rebuilt for Python 3.7
|
||||||
|
|
||||||
* Mon May 28 2018 Thomas Sailer <t.sailer@alumni.ethz.ch> - 2.56.1-1
|
* Mon May 28 2018 Thomas Sailer <t.sailer@alumni.ethz.ch> - 2.56.1-1
|
||||||
- Update to 2.56.1
|
- Update to 2.56.1
|
||||||
@ -1,6 +0,0 @@
|
|||||||
--- !Policy
|
|
||||||
product_versions:
|
|
||||||
- rhel-8
|
|
||||||
decision_context: osci_compose_gate
|
|
||||||
rules:
|
|
||||||
- !PassingTestCaseRule {test_case_name: desktop-qe.desktop-ci.tier1-gating.functional}
|
|
||||||
@ -1,80 +0,0 @@
|
|||||||
From bc90511c1eb333e26e0bc0eaee62375d0e788db6 Mon Sep 17 00:00:00 2001
|
|
||||||
From: Erik van Pienbroek <epienbro@fedoraproject.org>
|
|
||||||
Date: Tue, 16 Apr 2013 11:42:11 +0200
|
|
||||||
Subject: [PATCH] win32: Prefer the use of constructors over DllMain
|
|
||||||
|
|
||||||
This prevents having to depend on DllMain in static libraries
|
|
||||||
|
|
||||||
Constructors are available in both the GCC build (GCC 2.7 and later)
|
|
||||||
and the MSVC build (MSVC 2008 and later using _Pragma, earlier
|
|
||||||
versions using #pragma)
|
|
||||||
---
|
|
||||||
glib/glib-init.c | 22 ++++++++++++++--------
|
|
||||||
1 file changed, 14 insertions(+), 8 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/glib/glib-init.c b/glib/glib-init.c
|
|
||||||
index 0032ee8..dd6ccbf 100644
|
|
||||||
--- a/glib/glib-init.c
|
|
||||||
+++ b/glib/glib-init.c
|
|
||||||
@@ -223,12 +223,14 @@ glib_init (void)
|
|
||||||
|
|
||||||
#if defined (G_OS_WIN32)
|
|
||||||
|
|
||||||
+HMODULE glib_dll = NULL;
|
|
||||||
+
|
|
||||||
+#if defined (DLL_EXPORT)
|
|
||||||
+
|
|
||||||
BOOL WINAPI DllMain (HINSTANCE hinstDLL,
|
|
||||||
DWORD fdwReason,
|
|
||||||
LPVOID lpvReserved);
|
|
||||||
|
|
||||||
-HMODULE glib_dll;
|
|
||||||
-
|
|
||||||
BOOL WINAPI
|
|
||||||
DllMain (HINSTANCE hinstDLL,
|
|
||||||
DWORD fdwReason,
|
|
||||||
@@ -238,14 +240,6 @@ DllMain (HINSTANCE hinstDLL,
|
|
||||||
{
|
|
||||||
case DLL_PROCESS_ATTACH:
|
|
||||||
glib_dll = hinstDLL;
|
|
||||||
- g_crash_handler_win32_init ();
|
|
||||||
- g_clock_win32_init ();
|
|
||||||
-#ifdef THREADS_WIN32
|
|
||||||
- g_thread_win32_init ();
|
|
||||||
-#endif
|
|
||||||
- glib_init ();
|
|
||||||
- /* must go after glib_init */
|
|
||||||
- g_console_win32_init ();
|
|
||||||
break;
|
|
||||||
|
|
||||||
case DLL_THREAD_DETACH:
|
|
||||||
@@ -259,7 +256,10 @@ DllMain (HINSTANCE hinstDLL,
|
|
||||||
return TRUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
-#elif defined (G_HAS_CONSTRUCTORS)
|
|
||||||
+#endif /* defined (DLL_EXPORT) */
|
|
||||||
+#endif /* defined (G_OS_WIN32) */
|
|
||||||
+
|
|
||||||
+#if defined (G_HAS_CONSTRUCTORS)
|
|
||||||
|
|
||||||
#ifdef G_DEFINE_CONSTRUCTOR_NEEDS_PRAGMA
|
|
||||||
#pragma G_DEFINE_CONSTRUCTOR_PRAGMA_ARGS(glib_init_ctor)
|
|
||||||
@@ -269,7 +266,15 @@ G_DEFINE_CONSTRUCTOR(glib_init_ctor)
|
|
||||||
static void
|
|
||||||
glib_init_ctor (void)
|
|
||||||
{
|
|
||||||
+#if defined (G_OS_WIN32)
|
|
||||||
+ g_clock_win32_init ();
|
|
||||||
+#ifdef THREADS_WIN32
|
|
||||||
+ g_thread_win32_init ();
|
|
||||||
+#endif /* defined (THREADS_WIN32) */
|
|
||||||
+#endif /* defined (G_OS_WIN32) */
|
|
||||||
glib_init ();
|
|
||||||
+ /* must go after glib_init */
|
|
||||||
+ g_console_win32_init ();
|
|
||||||
}
|
|
||||||
|
|
||||||
#else
|
|
||||||
--
|
|
||||||
1.8.2
|
|
||||||
@ -1,65 +0,0 @@
|
|||||||
From 074d82962028125c7886e5edcff1a58a508e0e61 Mon Sep 17 00:00:00 2001
|
|
||||||
From: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Date: Tue, 25 Nov 2025 19:02:56 +0000
|
|
||||||
Subject: [PATCH] gvariant-parser: Fix potential integer overflow parsing
|
|
||||||
(byte)strings
|
|
||||||
|
|
||||||
The termination condition for parsing string and bytestring literals in
|
|
||||||
GVariant text format input was subject to an integer overflow for input
|
|
||||||
string (or bytestring) literals longer than `INT_MAX`.
|
|
||||||
|
|
||||||
Fix that by counting as a `size_t` rather than as an `int`. The counter
|
|
||||||
can never correctly be negative.
|
|
||||||
|
|
||||||
Spotted by treeplus. Thanks to the Sovereign Tech Resilience programme
|
|
||||||
from the Sovereign Tech Agency. ID: #YWH-PGM9867-145
|
|
||||||
|
|
||||||
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Fixes: #3834
|
|
||||||
---
|
|
||||||
glib/gvariant-parser.c | 10 +++++-----
|
|
||||||
1 file changed, 5 insertions(+), 5 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/glib/gvariant-parser.c b/glib/gvariant-parser.c
|
|
||||||
index bb5238bea..af6527d40 100644
|
|
||||||
--- a/glib/gvariant-parser.c
|
|
||||||
+++ b/glib/gvariant-parser.c
|
|
||||||
@@ -594,7 +594,7 @@ ast_resolve (AST *ast,
|
|
||||||
{
|
|
||||||
GVariant *value;
|
|
||||||
gchar *pattern;
|
|
||||||
- gint i, j = 0;
|
|
||||||
+ size_t i, j = 0;
|
|
||||||
|
|
||||||
pattern = ast_get_pattern (ast, error);
|
|
||||||
|
|
||||||
@@ -1555,9 +1555,9 @@ string_free (AST *ast)
|
|
||||||
* No leading/trailing space allowed. */
|
|
||||||
static gboolean
|
|
||||||
unicode_unescape (const gchar *src,
|
|
||||||
- gint *src_ofs,
|
|
||||||
+ size_t *src_ofs,
|
|
||||||
gchar *dest,
|
|
||||||
- gint *dest_ofs,
|
|
||||||
+ size_t *dest_ofs,
|
|
||||||
gsize length,
|
|
||||||
SourceRef *ref,
|
|
||||||
GError **error)
|
|
||||||
@@ -1618,7 +1618,7 @@ string_parse (TokenStream *stream,
|
|
||||||
gsize length;
|
|
||||||
gchar quote;
|
|
||||||
gchar *str;
|
|
||||||
- gint i, j;
|
|
||||||
+ size_t i, j;
|
|
||||||
|
|
||||||
token_stream_start_ref (stream, &ref);
|
|
||||||
token = token_stream_get (stream);
|
|
||||||
@@ -1748,7 +1748,7 @@ bytestring_parse (TokenStream *stream,
|
|
||||||
gsize length;
|
|
||||||
gchar quote;
|
|
||||||
gchar *str;
|
|
||||||
- gint i, j;
|
|
||||||
+ size_t i, j;
|
|
||||||
|
|
||||||
token_stream_start_ref (stream, &ref);
|
|
||||||
token = token_stream_get (stream);
|
|
||||||
@ -1,106 +0,0 @@
|
|||||||
From eb63e89e237d35fb1d3cb757ea97b4c8806269a0 Mon Sep 17 00:00:00 2001
|
|
||||||
From: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Date: Sun, 29 Mar 2026 19:10:41 +0100
|
|
||||||
Subject: [PATCH] gvariant: Fix an off-by-one error in an offset comparison
|
|
||||||
MIME-Version: 1.0
|
|
||||||
Content-Type: text/plain; charset=UTF-8
|
|
||||||
Content-Transfer-Encoding: 8bit
|
|
||||||
|
|
||||||
This allows a single byte out-of-bounds read off the end of the
|
|
||||||
(potentially untrusted) byte array backing a `GVariant` when it’s
|
|
||||||
being checked for normal form.
|
|
||||||
|
|
||||||
I can’t see how this could practically be exploited, but it’s certainly
|
|
||||||
a security bug as the `GVariant` normal form checking code is supposed
|
|
||||||
to be robust to malicious inputs.
|
|
||||||
|
|
||||||
Spotted by linhlhq as #YWH-PGM9867-190, and fix and reproducer provided
|
|
||||||
by them too, thanks. Confirmed and turned into a unit test by me.
|
|
||||||
|
|
||||||
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
|
|
||||||
Fixes: #3915
|
|
||||||
---
|
|
||||||
glib/gvariant-serialiser.c | 2 +-
|
|
||||||
glib/tests/gvariant.c | 48 ++++++++++++++++++++++++++++++++++++++
|
|
||||||
2 files changed, 49 insertions(+), 1 deletion(-)
|
|
||||||
|
|
||||||
diff --git a/glib/gvariant-serialiser.c b/glib/gvariant-serialiser.c
|
|
||||||
index 832a8fdc2..1bf3e4688 100644
|
|
||||||
--- a/glib/gvariant-serialiser.c
|
|
||||||
+++ b/glib/gvariant-serialiser.c
|
|
||||||
@@ -1079,7 +1079,7 @@ gvs_tuple_is_normal (GVariantSerialised value)
|
|
||||||
|
|
||||||
while (offset & alignment)
|
|
||||||
{
|
|
||||||
- if (offset > value.size || value.data[offset] != '\0')
|
|
||||||
+ if (offset >= value.size || value.data[offset] != '\0')
|
|
||||||
return FALSE;
|
|
||||||
offset++;
|
|
||||||
}
|
|
||||||
diff --git a/glib/tests/gvariant.c b/glib/tests/gvariant.c
|
|
||||||
index 0110f2664..dd3af6941 100644
|
|
||||||
--- a/glib/tests/gvariant.c
|
|
||||||
+++ b/glib/tests/gvariant.c
|
|
||||||
@@ -5047,6 +5047,52 @@ test_normal_checking_tuple_offsets (void)
|
|
||||||
g_variant_unref (variant);
|
|
||||||
}
|
|
||||||
|
|
||||||
+/* This is a regression test that looping over the padding bytes in a short
|
|
||||||
+ * (non-normal) tuple doesn’t overflow the input data.
|
|
||||||
+ *
|
|
||||||
+ * See https://gitlab.gnome.org/GNOME/glib/-/issues/3915 */
|
|
||||||
+static void
|
|
||||||
+test_normal_checking_tuple_offsets6 (void)
|
|
||||||
+{
|
|
||||||
+ /*
|
|
||||||
+ * Type: (ynqiuxthdsog) — 12 members, first member 'y' (byte) has
|
|
||||||
+ * alignment 0, second 'n' (int16) has alignment 1.
|
|
||||||
+ * With 1 byte of data (0x28), after reading the first byte member,
|
|
||||||
+ * offset=1, alignment check for 'n' requires offset to be even,
|
|
||||||
+ * so the while loop checks value.data[1] — but size is only 1.
|
|
||||||
+ *
|
|
||||||
+ * Use heap allocation via GBytes so ASan reports heap-buffer-overflow.
|
|
||||||
+ */
|
|
||||||
+ uint8_t *heap_data = NULL;
|
|
||||||
+ GBytes *bytes = NULL;
|
|
||||||
+ const GVariantType *data_type = G_VARIANT_TYPE ("(ynqiuxthdsog)");
|
|
||||||
+ GVariant *variant = NULL;
|
|
||||||
+ GVariant *normal_variant = NULL;
|
|
||||||
+ GVariant *expected = NULL;
|
|
||||||
+
|
|
||||||
+ g_test_bug ("https://gitlab.gnome.org/GNOME/glib/-/issues/3915");
|
|
||||||
+
|
|
||||||
+ heap_data = g_malloc (1);
|
|
||||||
+ heap_data[0] = 0x28;
|
|
||||||
+ bytes = g_bytes_new_take (heap_data, 1);
|
|
||||||
+
|
|
||||||
+ variant = g_variant_new_from_bytes (data_type, bytes, FALSE);
|
|
||||||
+ g_assert_nonnull (variant);
|
|
||||||
+
|
|
||||||
+ g_assert_false (g_variant_is_normal_form (variant));
|
|
||||||
+
|
|
||||||
+ normal_variant = g_variant_get_normal_form (variant);
|
|
||||||
+ g_assert_nonnull (normal_variant);
|
|
||||||
+
|
|
||||||
+ expected = g_variant_new_parsed ("(byte 0x28, int16 0, uint16 0, 0, uint32 0, int64 0, uint64 0, handle 0, 0.0, '', objectpath '/', signature '')");
|
|
||||||
+ g_assert_cmpvariant (expected, variant);
|
|
||||||
+ g_assert_cmpvariant (expected, normal_variant);
|
|
||||||
+
|
|
||||||
+ g_variant_unref (expected);
|
|
||||||
+ g_variant_unref (normal_variant);
|
|
||||||
+ g_variant_unref (variant);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
/* Test that an empty object path is normalised successfully to the base object
|
|
||||||
* path, ‘/’. */
|
|
||||||
static void
|
|
||||||
@@ -5191,6 +5237,8 @@ main (int argc, char **argv)
|
|
||||||
test_normal_checking_array_offsets);
|
|
||||||
g_test_add_func ("/gvariant/normal-checking/tuple-offsets",
|
|
||||||
test_normal_checking_tuple_offsets);
|
|
||||||
+ g_test_add_func ("/gvariant/normal-checking/tuple-offsets6",
|
|
||||||
+ test_normal_checking_tuple_offsets6);
|
|
||||||
g_test_add_func ("/gvariant/normal-checking/empty-object-path",
|
|
||||||
test_normal_checking_empty_object_path);
|
|
||||||
|
|
||||||
@ -1,122 +0,0 @@
|
|||||||
From fbef21c7da7757239d6df411a24c7dbb345ab966 Mon Sep 17 00:00:00 2001
|
|
||||||
From: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Date: Sun, 29 Mar 2026 23:19:47 +0100
|
|
||||||
Subject: [PATCH 1/2] gdatetime: Factor out a couple of magic constants
|
|
||||||
|
|
||||||
This introduces no functional changes, it just makes the code a little
|
|
||||||
clearer.
|
|
||||||
|
|
||||||
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
---
|
|
||||||
glib/gdatetime.c | 9 ++++++---
|
|
||||||
1 file changed, 6 insertions(+), 3 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/glib/gdatetime.c b/glib/gdatetime.c
|
|
||||||
index a31afe713..029636c08 100644
|
|
||||||
--- a/glib/gdatetime.c
|
|
||||||
+++ b/glib/gdatetime.c
|
|
||||||
@@ -130,7 +130,7 @@ struct _GDateTime
|
|
||||||
gint interval;
|
|
||||||
|
|
||||||
/* 1 is 0001-01-01 in Proleptic Gregorian */
|
|
||||||
- gint32 days;
|
|
||||||
+ gint32 days; /* in range [MIN_DAYS, MAX_DAYS] */
|
|
||||||
|
|
||||||
gint ref_count; /* (atomic) */
|
|
||||||
};
|
|
||||||
@@ -172,6 +172,9 @@ struct _GDateTime
|
|
||||||
#define JULIAN_YEAR(d) ((d)->julian / 365.25)
|
|
||||||
#define DAYS_PER_PERIOD (G_GINT64_CONSTANT (2914695))
|
|
||||||
|
|
||||||
+#define MIN_DAYS 1 /* the days count for 0001-01-01 in Proleptic Gregorian */
|
|
||||||
+#define MAX_DAYS 3652059 /* the days count for 9999-12-31 in Proleptic Gregorian */
|
|
||||||
+
|
|
||||||
static const guint16 days_in_months[2][13] =
|
|
||||||
{
|
|
||||||
{ 0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 },
|
|
||||||
@@ -781,7 +784,7 @@ g_date_time_from_instant (GTimeZone *tz,
|
|
||||||
datetime->days = instant / USEC_PER_DAY;
|
|
||||||
datetime->usec = instant % USEC_PER_DAY;
|
|
||||||
|
|
||||||
- if (datetime->days < 1 || 3652059 < datetime->days)
|
|
||||||
+ if (datetime->days < MIN_DAYS || datetime->days > MAX_DAYS)
|
|
||||||
{
|
|
||||||
g_date_time_unref (datetime);
|
|
||||||
datetime = NULL;
|
|
||||||
@@ -817,7 +820,7 @@ g_date_time_deal_with_date_change (GDateTime *datetime)
|
|
||||||
gint64 full_time;
|
|
||||||
gint64 usec;
|
|
||||||
|
|
||||||
- if (datetime->days < 1 || datetime->days > 3652059)
|
|
||||||
+ if (datetime->days < MIN_DAYS || datetime->days > MAX_DAYS)
|
|
||||||
return FALSE;
|
|
||||||
|
|
||||||
was_dst = g_time_zone_is_dst (datetime->tz, datetime->interval);
|
|
||||||
|
|
||||||
From 5f0c67435364fe682fe9dcc1d23645134a445a17 Mon Sep 17 00:00:00 2001
|
|
||||||
From: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Date: Sun, 29 Mar 2026 23:46:17 +0100
|
|
||||||
Subject: [PATCH 2/2] gdatetime: Add missing range validation to
|
|
||||||
g_date_time_add_full()
|
|
||||||
MIME-Version: 1.0
|
|
||||||
Content-Type: text/plain; charset=UTF-8
|
|
||||||
Content-Transfer-Encoding: 8bit
|
|
||||||
|
|
||||||
Otherwise it’s possible to create a non-`NULL` but invalid `GDateTime`,
|
|
||||||
which breaks all kinds of internal assumptions.
|
|
||||||
|
|
||||||
Spotted by linhlhq as #YWH-PGM9867-191. Thanks to them for providing a
|
|
||||||
suggested fix and a test case, which I have adapted and validated.
|
|
||||||
|
|
||||||
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
|
|
||||||
Fixes: #3917
|
|
||||||
---
|
|
||||||
glib/gdatetime.c | 4 +++-
|
|
||||||
glib/tests/gdatetime.c | 18 ++++++++++++++++++
|
|
||||||
2 files changed, 21 insertions(+), 1 deletion(-)
|
|
||||||
|
|
||||||
diff --git a/glib/gdatetime.c b/glib/gdatetime.c
|
|
||||||
index 029636c08..883322891 100644
|
|
||||||
--- a/glib/gdatetime.c
|
|
||||||
+++ b/glib/gdatetime.c
|
|
||||||
@@ -2022,7 +2022,9 @@ g_date_time_add_full (GDateTime *datetime,
|
|
||||||
new->days = full_time / USEC_PER_DAY;
|
|
||||||
new->usec = full_time % USEC_PER_DAY;
|
|
||||||
|
|
||||||
- /* XXX validate */
|
|
||||||
+ /* Validate it’s still in the range 0001-01-01 to 9999-12-31 */
|
|
||||||
+ if (new->days < MIN_DAYS || new->days > MAX_DAYS)
|
|
||||||
+ g_clear_pointer (&new, g_date_time_unref);
|
|
||||||
|
|
||||||
return new;
|
|
||||||
}
|
|
||||||
diff --git a/glib/tests/gdatetime.c b/glib/tests/gdatetime.c
|
|
||||||
index 12f332b44..88041a684 100644
|
|
||||||
--- a/glib/tests/gdatetime.c
|
|
||||||
+++ b/glib/tests/gdatetime.c
|
|
||||||
@@ -1098,6 +1098,24 @@ test_GDateTime_add_full (void)
|
|
||||||
TEST_ADD_FULL (2010, 8, 25, 22, 45, 0,
|
|
||||||
0, 1, 6, 1, 25, 0,
|
|
||||||
2010, 10, 2, 0, 10, 0);
|
|
||||||
+
|
|
||||||
+#define TEST_ADD_FULL_ERROR(y,m,d,h,mi,s,ay,am,ad,ah,ami,as) G_STMT_START { \
|
|
||||||
+ GDateTime *dt; \
|
|
||||||
+ dt = g_date_time_new_utc (y, m, d, h, mi, s); \
|
|
||||||
+ g_assert_null (g_date_time_add_full (dt, ay, am, ad, ah, ami, as)); \
|
|
||||||
+ g_date_time_unref (dt); \
|
|
||||||
+} G_STMT_END
|
|
||||||
+
|
|
||||||
+ TEST_ADD_FULL_ERROR ( 1, 12, 1, 0, 0, 0,
|
|
||||||
+ -1, 0, 0, 0, 0, 0);
|
|
||||||
+ TEST_ADD_FULL_ERROR ( 1, 12, 1, 0, 0, 0,
|
|
||||||
+ 10000, 0, 0, 0, 0, 0);
|
|
||||||
+ TEST_ADD_FULL_ERROR ( 9999, 12, 1, 0, 0, 0,
|
|
||||||
+ -10000, 0, 0, 0, 0, 0);
|
|
||||||
+ TEST_ADD_FULL_ERROR ( 1, 12, 1, 0, 0, 0,
|
|
||||||
+ 0, 0, 3660001, 0, 0, 0);
|
|
||||||
+ TEST_ADD_FULL_ERROR ( 9999, 12, 1, 0, 0, 0,
|
|
||||||
+ 0, 0, -3660001, 0, 0, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
@ -1,221 +0,0 @@
|
|||||||
From a9a4c378a05723eb164f193d585b6611e4646b65 Mon Sep 17 00:00:00 2001
|
|
||||||
From: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Date: Tue, 31 Mar 2026 16:13:57 +0100
|
|
||||||
Subject: [PATCH] gregex: Fix case changing substitutions with G_REGEX_RAW
|
|
||||||
|
|
||||||
In `G_REGEX_RAW` mode, the input string is treated as a byte array
|
|
||||||
(basically ASCII) rather than a unichar array. Accordingly, the case
|
|
||||||
changing code for substitutions needs to operate on bytes with
|
|
||||||
`G_REGEX_RAW`, rather than operating on unichars.
|
|
||||||
|
|
||||||
This fixes a potential buffer overflow when trying to do a case change
|
|
||||||
on a match of a set of bytes which are a truncated multi-byte UTF-8
|
|
||||||
encoding at the end of the input buffer.
|
|
||||||
|
|
||||||
Spotted by linhlhq as #YWH-PGM9867-193. I adapted their reproducer as
|
|
||||||
the unit test, but implemented the fix in `gregex.c` independently.
|
|
||||||
|
|
||||||
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
|
|
||||||
Fixes: #3918
|
|
||||||
---
|
|
||||||
glib/gregex.c | 59 ++++++++++++++++++++++++++++++++++------------
|
|
||||||
glib/tests/regex.c | 53 +++++++++++++++++++++++++++++++++++++++++
|
|
||||||
2 files changed, 97 insertions(+), 15 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/glib/gregex.c b/glib/gregex.c
|
|
||||||
index a8a35a424..948df3f95 100644
|
|
||||||
--- a/glib/gregex.c
|
|
||||||
+++ b/glib/gregex.c
|
|
||||||
@@ -2655,19 +2655,25 @@ split_replacement (const gchar *replacement,
|
|
||||||
return g_list_reverse (list);
|
|
||||||
}
|
|
||||||
|
|
||||||
-/* Change the case of c based on change_case. */
|
|
||||||
-#define CHANGE_CASE(c, change_case) \
|
|
||||||
+/* Change the case of c based on change_case.
|
|
||||||
+ * g_ascii_to*() will happily pass through non-ASCII bytes unchanged. */
|
|
||||||
+#define UTF8_CHANGE_CASE(c, change_case) \
|
|
||||||
(((change_case) & CHANGE_CASE_LOWER_MASK) ? \
|
|
||||||
g_unichar_tolower (c) : \
|
|
||||||
g_unichar_toupper (c))
|
|
||||||
+#define RAW_CHANGE_CASE(c, change_case) \
|
|
||||||
+ (((change_case) & CHANGE_CASE_LOWER_MASK) ? \
|
|
||||||
+ g_ascii_tolower (c) : \
|
|
||||||
+ g_ascii_toupper (c))
|
|
||||||
|
|
||||||
+/* If @text_is_raw is set, @text might not be valid UTF-8 (but will be
|
|
||||||
+ * nul-terminated). */
|
|
||||||
static void
|
|
||||||
string_append (GString *string,
|
|
||||||
const gchar *text,
|
|
||||||
+ gboolean text_is_raw,
|
|
||||||
ChangeCase *change_case)
|
|
||||||
{
|
|
||||||
- gunichar c;
|
|
||||||
-
|
|
||||||
if (text[0] == '\0')
|
|
||||||
return;
|
|
||||||
|
|
||||||
@@ -2677,22 +2683,44 @@ string_append (GString *string,
|
|
||||||
}
|
|
||||||
else if (*change_case & CHANGE_CASE_SINGLE_MASK)
|
|
||||||
{
|
|
||||||
- c = g_utf8_get_char (text);
|
|
||||||
- g_string_append_unichar (string, CHANGE_CASE (c, *change_case));
|
|
||||||
- g_string_append (string, g_utf8_next_char (text));
|
|
||||||
+ if (!text_is_raw)
|
|
||||||
+ {
|
|
||||||
+ gunichar c = g_utf8_get_char (text);
|
|
||||||
+ g_string_append_unichar (string, UTF8_CHANGE_CASE (c, *change_case));
|
|
||||||
+ g_string_append (string, g_utf8_next_char (text));
|
|
||||||
+ }
|
|
||||||
+ else
|
|
||||||
+ {
|
|
||||||
+ g_string_append_c (string, RAW_CHANGE_CASE (text[0], *change_case));
|
|
||||||
+ g_string_append (string, text + 1);
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
*change_case = CHANGE_CASE_NONE;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
- while (*text != '\0')
|
|
||||||
+ if (!text_is_raw)
|
|
||||||
{
|
|
||||||
- c = g_utf8_get_char (text);
|
|
||||||
- g_string_append_unichar (string, CHANGE_CASE (c, *change_case));
|
|
||||||
- text = g_utf8_next_char (text);
|
|
||||||
+ while (*text != '\0')
|
|
||||||
+ {
|
|
||||||
+ gunichar c = g_utf8_get_char (text);
|
|
||||||
+ g_string_append_unichar (string, UTF8_CHANGE_CASE (c, *change_case));
|
|
||||||
+ text = g_utf8_next_char (text);
|
|
||||||
+ }
|
|
||||||
+ }
|
|
||||||
+ else
|
|
||||||
+ {
|
|
||||||
+ while (*text != '\0')
|
|
||||||
+ {
|
|
||||||
+ char c = *text;
|
|
||||||
+ g_string_append_c (string, RAW_CHANGE_CASE (c, *change_case));
|
|
||||||
+ text++;
|
|
||||||
+ }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
+/* @match_info is (nullable) */
|
|
||||||
static gboolean
|
|
||||||
interpolate_replacement (const GMatchInfo *match_info,
|
|
||||||
GString *result,
|
|
||||||
@@ -2702,6 +2730,7 @@ interpolate_replacement (const GMatchInfo *match_info,
|
|
||||||
InterpolationData *idata;
|
|
||||||
gchar *match;
|
|
||||||
ChangeCase change_case = CHANGE_CASE_NONE;
|
|
||||||
+ gboolean is_raw = (match_info != NULL && (match_info->regex->compile_opts & G_REGEX_RAW));
|
|
||||||
|
|
||||||
for (list = data; list; list = list->next)
|
|
||||||
{
|
|
||||||
@@ -2709,10 +2738,10 @@ interpolate_replacement (const GMatchInfo *match_info,
|
|
||||||
switch (idata->type)
|
|
||||||
{
|
|
||||||
case REPL_TYPE_STRING:
|
|
||||||
- string_append (result, idata->text, &change_case);
|
|
||||||
+ string_append (result, idata->text, is_raw, &change_case);
|
|
||||||
break;
|
|
||||||
case REPL_TYPE_CHARACTER:
|
|
||||||
- g_string_append_c (result, CHANGE_CASE (idata->c, change_case));
|
|
||||||
+ g_string_append_c (result, UTF8_CHANGE_CASE (idata->c, change_case));
|
|
||||||
if (change_case & CHANGE_CASE_SINGLE_MASK)
|
|
||||||
change_case = CHANGE_CASE_NONE;
|
|
||||||
break;
|
|
||||||
@@ -2720,7 +2749,7 @@ interpolate_replacement (const GMatchInfo *match_info,
|
|
||||||
match = g_match_info_fetch (match_info, idata->num);
|
|
||||||
if (match)
|
|
||||||
{
|
|
||||||
- string_append (result, match, &change_case);
|
|
||||||
+ string_append (result, match, is_raw, &change_case);
|
|
||||||
g_free (match);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
@@ -2728,7 +2757,7 @@ interpolate_replacement (const GMatchInfo *match_info,
|
|
||||||
match = g_match_info_fetch_named (match_info, idata->text);
|
|
||||||
if (match)
|
|
||||||
{
|
|
||||||
- string_append (result, match, &change_case);
|
|
||||||
+ string_append (result, match, is_raw, &change_case);
|
|
||||||
g_free (match);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
diff --git a/glib/tests/regex.c b/glib/tests/regex.c
|
|
||||||
index 88d12edf6..818d6d0a0 100644
|
|
||||||
--- a/glib/tests/regex.c
|
|
||||||
+++ b/glib/tests/regex.c
|
|
||||||
@@ -2183,6 +2183,58 @@ pcre_ge (guint64 major, guint64 minor)
|
|
||||||
return (pcre_major > major) || (pcre_major == major && pcre_minor >= minor);
|
|
||||||
}
|
|
||||||
|
|
||||||
+static void
|
|
||||||
+test_replace_raw_change_case (void)
|
|
||||||
+{
|
|
||||||
+ GError *local_error = NULL;
|
|
||||||
+ GRegex *regex = NULL;
|
|
||||||
+
|
|
||||||
+ g_test_bug ("https://gitlab.gnome.org/GNOME/glib/-/issues/3918");
|
|
||||||
+ g_test_summary ("Test that case changes as part of a replacement are handled correctly in G_REGEX_RAW mode");
|
|
||||||
+
|
|
||||||
+ /*
|
|
||||||
+ * Match a multi-byte sequence in RAW mode. The pattern matches
|
|
||||||
+ * exactly 2 bytes. The subject contains a 4-byte UTF-8 lead (0xF4)
|
|
||||||
+ * followed by only one continuation byte, then NUL.
|
|
||||||
+ *
|
|
||||||
+ * The matched substring will be "\xf4\x80" (2 bytes, heap-allocated
|
|
||||||
+ * as 3-byte buffer with NUL). If the code regresses and tries to handle
|
|
||||||
+ * the replacement as UTF-8 then g_utf8_get_char() would see 0xF4 and try
|
|
||||||
+ * to read 4 bytes, going 1 byte past the NUL into OOB territory.
|
|
||||||
+ */
|
|
||||||
+ regex = g_regex_new ("..", G_REGEX_RAW, 0, &local_error);
|
|
||||||
+ g_assert_no_error (local_error);
|
|
||||||
+
|
|
||||||
+ /*
|
|
||||||
+ * Build a subject string with truncated UTF-8.
|
|
||||||
+ * \xF4 = 4-byte UTF-8 lead byte
|
|
||||||
+ * \x80 = continuation byte
|
|
||||||
+ * No 3rd/4th continuation bytes — the match is only 2 bytes.
|
|
||||||
+ *
|
|
||||||
+ * \U\0 = uppercase the entire match → triggers string_append()
|
|
||||||
+ * with case change on the 2-byte non-UTF-8 match.
|
|
||||||
+ */
|
|
||||||
+ char subject[] = "\xf4\x80";
|
|
||||||
+ char *result = g_regex_replace (regex, subject, -1, 0, "\\U\\0", 0, &local_error);
|
|
||||||
+ g_assert_no_error (local_error);
|
|
||||||
+
|
|
||||||
+ g_clear_pointer (&result, g_free);
|
|
||||||
+ g_clear_pointer (®ex, g_regex_unref);
|
|
||||||
+
|
|
||||||
+ /*
|
|
||||||
+ * Second variant: single-char case change \u with \0 backreference.
|
|
||||||
+ */
|
|
||||||
+ regex = g_regex_new (".", G_REGEX_RAW, 0, &local_error);
|
|
||||||
+ g_assert_no_error (local_error);
|
|
||||||
+
|
|
||||||
+ char subject2[] = "\xe6\xb0"; /* 3-byte UTF-8 lead, only 2 bytes */
|
|
||||||
+ result = g_regex_replace (regex, subject2, -1, 0, "\\u\\0", 0, &local_error);
|
|
||||||
+ g_assert_no_error (local_error);
|
|
||||||
+
|
|
||||||
+ g_clear_pointer (&result, g_free);
|
|
||||||
+ g_clear_pointer (®ex, g_regex_unref);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
int
|
|
||||||
main (int argc, char *argv[])
|
|
||||||
{
|
|
||||||
@@ -2200,6 +2252,7 @@ main (int argc, char *argv[])
|
|
||||||
g_test_add_func ("/regex/multiline", test_multiline);
|
|
||||||
g_test_add_func ("/regex/explicit-crlf", test_explicit_crlf);
|
|
||||||
g_test_add_func ("/regex/max-lookbehind", test_max_lookbehind);
|
|
||||||
+ g_test_add_func ("/regex/replace-raw-change-case", test_replace_raw_change_case);
|
|
||||||
|
|
||||||
/* TEST_NEW(pattern, compile_opts, match_opts) */
|
|
||||||
TEST_NEW("[A-Z]+", G_REGEX_CASELESS | G_REGEX_EXTENDED | G_REGEX_OPTIMIZE, G_REGEX_MATCH_NOTBOL | G_REGEX_MATCH_PARTIAL);
|
|
||||||
@ -1,120 +0,0 @@
|
|||||||
From 5e8a44975bddd21a762e58c6717f841e90594f03 Mon Sep 17 00:00:00 2001
|
|
||||||
From: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Date: Tue, 28 Apr 2026 16:45:14 +0100
|
|
||||||
Subject: [PATCH] giochannel: Fix memcmp() off the end of the buffer with long
|
|
||||||
terminators
|
|
||||||
MIME-Version: 1.0
|
|
||||||
Content-Type: text/plain; charset=UTF-8
|
|
||||||
Content-Transfer-Encoding: 8bit
|
|
||||||
|
|
||||||
If the line terminator is longer than a single byte, and the current
|
|
||||||
line extends to the end of the buffer, and the buffer (which is a
|
|
||||||
`GString`) is near a power of two in length (as that’s how `GString`s
|
|
||||||
are allocated) it’s possible for the `memcmp()` which checks the
|
|
||||||
terminator to read off the end of the string buffer.
|
|
||||||
|
|
||||||
Fix that by checking the terminator length against the last character
|
|
||||||
before calling `memcmp()`. Add a unit test.
|
|
||||||
|
|
||||||
Spotted by linhlhq as #YWH-PGM9867-199. The fix is theirs (validated by
|
|
||||||
me), and the unit test is adapted from their proof of concept.
|
|
||||||
|
|
||||||
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Fixes: #3925
|
|
||||||
---
|
|
||||||
glib/giochannel.c | 3 ++-
|
|
||||||
glib/tests/io-channel.c | 60 +++++++++++++++++++++++++++++++++++++++++
|
|
||||||
2 files changed, 62 insertions(+), 1 deletion(-)
|
|
||||||
|
|
||||||
diff --git a/glib/giochannel.c b/glib/giochannel.c
|
|
||||||
index e93c4b458..66b68e645 100644
|
|
||||||
--- a/glib/giochannel.c
|
|
||||||
+++ b/glib/giochannel.c
|
|
||||||
@@ -1830,7 +1830,8 @@ read_again:
|
|
||||||
{
|
|
||||||
if (channel->line_term)
|
|
||||||
{
|
|
||||||
- if (memcmp (channel->line_term, nextchar, line_term_len) == 0)
|
|
||||||
+ if ((size_t) (lastchar - nextchar) >= line_term_len &&
|
|
||||||
+ memcmp (channel->line_term, nextchar, line_term_len) == 0)
|
|
||||||
{
|
|
||||||
line_length = nextchar - use_buf->str;
|
|
||||||
got_term_len = line_term_len;
|
|
||||||
diff --git a/glib/tests/io-channel.c b/glib/tests/io-channel.c
|
|
||||||
index 4a1b10876..c619fb00f 100644
|
|
||||||
--- a/glib/tests/io-channel.c
|
|
||||||
+++ b/glib/tests/io-channel.c
|
|
||||||
@@ -69,6 +69,65 @@ test_read_line_embedded_nuls (void)
|
|
||||||
g_free (filename);
|
|
||||||
}
|
|
||||||
|
|
||||||
+static void
|
|
||||||
+test_read_line_long_terminator (void)
|
|
||||||
+{
|
|
||||||
+ uint8_t *test_data = NULL;
|
|
||||||
+ size_t test_data_len = 0;
|
|
||||||
+ int fd;
|
|
||||||
+ char *filename = NULL;
|
|
||||||
+ GIOChannel *channel = NULL;
|
|
||||||
+ GError *local_error = NULL;
|
|
||||||
+ char *line = NULL;
|
|
||||||
+ size_t line_length, terminator_pos;
|
|
||||||
+ const char *line_term;
|
|
||||||
+ int line_term_length;
|
|
||||||
+ GIOStatus status;
|
|
||||||
+
|
|
||||||
+ g_test_summary ("Test that reading a line when using a long terminator doesn’t over-read the buffer.");
|
|
||||||
+ g_test_bug ("https://gitlab.gnome.org/GNOME/glib/-/work_items/3925");
|
|
||||||
+
|
|
||||||
+ /* Write out a temporary file containing 2047 bytes. This is enough to make it
|
|
||||||
+ * near the length of the GString buffer when read back in. */
|
|
||||||
+ fd = g_file_open_tmp ("glib-test-io-channel-XXXXXX", &filename, &local_error);
|
|
||||||
+ g_assert_no_error (local_error);
|
|
||||||
+ g_close (g_steal_fd (&fd), NULL);
|
|
||||||
+
|
|
||||||
+ test_data_len = 2047;
|
|
||||||
+ test_data = g_malloc (test_data_len);
|
|
||||||
+ memset (test_data, 'M', test_data_len);
|
|
||||||
+ g_file_set_contents (filename, (const gchar *) test_data, test_data_len, &local_error);
|
|
||||||
+ g_assert_no_error (local_error);
|
|
||||||
+
|
|
||||||
+ /* Create the channel. */
|
|
||||||
+ channel = g_io_channel_new_file (filename, "r", &local_error);
|
|
||||||
+ g_assert_no_error (local_error);
|
|
||||||
+
|
|
||||||
+ /* Use a long line terminator so it could potentially over-read the end of the buffer. */
|
|
||||||
+ g_io_channel_set_line_term (channel, "DEADBEEF", 8);
|
|
||||||
+
|
|
||||||
+ line_term = g_io_channel_get_line_term (channel, &line_term_length);
|
|
||||||
+ g_assert_cmpstr (line_term, ==, "DEADBEEF");
|
|
||||||
+ g_assert_cmpint (line_term_length, ==, 8);
|
|
||||||
+
|
|
||||||
+ g_io_channel_set_encoding (channel, "UTF-8", &local_error);
|
|
||||||
+ g_assert_no_error (local_error);
|
|
||||||
+
|
|
||||||
+ status = g_io_channel_read_line (channel, &line, &line_length,
|
|
||||||
+ &terminator_pos, &local_error);
|
|
||||||
+ g_assert_no_error (local_error);
|
|
||||||
+ g_assert_cmpint (status, ==, G_IO_STATUS_NORMAL);
|
|
||||||
+ g_assert_cmpuint (line_length, ==, 2047);
|
|
||||||
+ g_assert_cmpuint (terminator_pos, ==, 2047);
|
|
||||||
+ g_assert_cmpmem (line, line_length, test_data, test_data_len);
|
|
||||||
+
|
|
||||||
+ g_free (line);
|
|
||||||
+ g_io_channel_unref (channel);
|
|
||||||
+ g_free (test_data);
|
|
||||||
+ g_unlink (filename);
|
|
||||||
+ g_free (filename);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
int
|
|
||||||
main (int argc,
|
|
||||||
char *argv[])
|
|
||||||
@@ -76,6 +135,7 @@ main (int argc,
|
|
||||||
g_test_init (&argc, &argv, NULL);
|
|
||||||
|
|
||||||
g_test_add_func ("/io-channel/read-line/embedded-nuls", test_read_line_embedded_nuls);
|
|
||||||
+ g_test_add_func ("/io-channel/read-line/long-terminator", test_read_line_long_terminator);
|
|
||||||
|
|
||||||
return g_test_run ();
|
|
||||||
}
|
|
||||||
@ -1,101 +0,0 @@
|
|||||||
From 8e49ae633b6eaceff9881ea15c8bb48cf11c8a53 Mon Sep 17 00:00:00 2001
|
|
||||||
From: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Date: Sat, 11 Apr 2026 14:42:57 +0100
|
|
||||||
Subject: [PATCH] gkeyfile: Fix a one-byte heap under-read with
|
|
||||||
g_key_file_get_locale_string_list()
|
|
||||||
|
|
||||||
If this method was called on a key file key which has an empty value,
|
|
||||||
`len == 0` and this leads to a one-byte under-read off the start of the
|
|
||||||
key file buffer.
|
|
||||||
|
|
||||||
Spotted by linhlhq as #YWH-PGM9867-200. The suggested fix is theirs, and
|
|
||||||
the unit test is adapted from their report. I added the fuzzing test.
|
|
||||||
|
|
||||||
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
|
|
||||||
Fixes: #3930
|
|
||||||
---
|
|
||||||
fuzzing/fuzz_key.c | 9 +++++++++
|
|
||||||
glib/gkeyfile.c | 2 +-
|
|
||||||
glib/tests/keyfile.c | 23 +++++++++++++++++++++++
|
|
||||||
3 files changed, 33 insertions(+), 1 deletion(-)
|
|
||||||
|
|
||||||
diff --git a/fuzzing/fuzz_key.c b/fuzzing/fuzz_key.c
|
|
||||||
index 9f1f9187e..285bad26f 100644
|
|
||||||
--- a/fuzzing/fuzz_key.c
|
|
||||||
+++ b/fuzzing/fuzz_key.c
|
|
||||||
@@ -6,11 +6,20 @@ test_parse (const gchar *data,
|
|
||||||
GKeyFileFlags flags)
|
|
||||||
{
|
|
||||||
GKeyFile *key = NULL;
|
|
||||||
+ char *comment = NULL;
|
|
||||||
+ char **list = NULL;
|
|
||||||
|
|
||||||
key = g_key_file_new ();
|
|
||||||
g_key_file_load_from_data (key, (const gchar*) data, size, G_KEY_FILE_NONE,
|
|
||||||
NULL);
|
|
||||||
|
|
||||||
+ /* Also try some additional parsing and see if it crashes */
|
|
||||||
+ comment = g_key_file_get_comment (key, "group", "key", NULL);
|
|
||||||
+ g_free (comment);
|
|
||||||
+
|
|
||||||
+ list = g_key_file_get_locale_string_list (key, "group", "key", "de", NULL, NULL);
|
|
||||||
+ g_strfreev (list);
|
|
||||||
+
|
|
||||||
g_key_file_free (key);
|
|
||||||
}
|
|
||||||
|
|
||||||
diff --git a/glib/gkeyfile.c b/glib/gkeyfile.c
|
|
||||||
index 17cf85660..76459daab 100644
|
|
||||||
--- a/glib/gkeyfile.c
|
|
||||||
+++ b/glib/gkeyfile.c
|
|
||||||
@@ -2407,7 +2407,7 @@ g_key_file_get_locale_string_list (GKeyFile *key_file,
|
|
||||||
}
|
|
||||||
|
|
||||||
len = strlen (value);
|
|
||||||
- if (value[len - 1] == key_file->list_separator)
|
|
||||||
+ if (len > 0 && value[len - 1] == key_file->list_separator)
|
|
||||||
value[len - 1] = '\0';
|
|
||||||
|
|
||||||
list_separator[0] = key_file->list_separator;
|
|
||||||
diff --git a/glib/tests/keyfile.c b/glib/tests/keyfile.c
|
|
||||||
index 1f5be8b38..17724bc15 100644
|
|
||||||
--- a/glib/tests/keyfile.c
|
|
||||||
+++ b/glib/tests/keyfile.c
|
|
||||||
@@ -800,6 +800,28 @@ test_locale_string_multiple_loads (void)
|
|
||||||
g_free (old_locale);
|
|
||||||
}
|
|
||||||
|
|
||||||
+static void
|
|
||||||
+test_locale_string_empty (void)
|
|
||||||
+{
|
|
||||||
+ GKeyFile *keyfile = NULL;
|
|
||||||
+ GError *local_error = NULL;
|
|
||||||
+ const char *data =
|
|
||||||
+ "[valid]\n"
|
|
||||||
+ "key1=\n";
|
|
||||||
+
|
|
||||||
+ g_test_summary ("Check that loading an empty translatable string works");
|
|
||||||
+ g_test_bug ("https://gitlab.gnome.org/GNOME/glib/-/issues/3930");
|
|
||||||
+
|
|
||||||
+ keyfile = g_key_file_new ();
|
|
||||||
+
|
|
||||||
+ g_key_file_load_from_data (keyfile, data, -1, G_KEY_FILE_NONE, &local_error);
|
|
||||||
+ g_assert_no_error (local_error);
|
|
||||||
+
|
|
||||||
+ check_locale_string_list_value (keyfile, "valid", "key1", NULL, NULL);
|
|
||||||
+
|
|
||||||
+ g_key_file_free (keyfile);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
static void
|
|
||||||
test_lists (void)
|
|
||||||
{
|
|
||||||
@@ -1832,6 +1854,7 @@ main (int argc, char *argv[])
|
|
||||||
g_test_add_func ("/keyfile/number", test_number);
|
|
||||||
g_test_add_func ("/keyfile/locale-string", test_locale_string);
|
|
||||||
g_test_add_func ("/keyfile/locale-string/multiple-loads", test_locale_string_multiple_loads);
|
|
||||||
+ g_test_add_func ("/keyfile/locale-string/empty", test_locale_string_empty);
|
|
||||||
g_test_add_func ("/keyfile/lists", test_lists);
|
|
||||||
g_test_add_func ("/keyfile/lists-set-get", test_lists_set_get);
|
|
||||||
g_test_add_func ("/keyfile/group-remove", test_group_remove);
|
|
||||||
@ -1,578 +0,0 @@
|
|||||||
From a37a31d4088cf9563756dbbf0c3a7d78e43cb9ee Mon Sep 17 00:00:00 2001
|
|
||||||
From: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Date: Tue, 28 Apr 2026 15:47:30 +0100
|
|
||||||
Subject: [PATCH 1/5] gdbusauthmechanismsha1: Validate cookie context
|
|
||||||
MIME-Version: 1.0
|
|
||||||
Content-Type: text/plain; charset=UTF-8
|
|
||||||
Content-Transfer-Encoding: 8bit
|
|
||||||
|
|
||||||
Without validation, the server could send a malicious context which
|
|
||||||
contains path traversal characters, allowing it to exfiltrate a SHA-1
|
|
||||||
hashed copy of arbitrary data from the client’s file system.
|
|
||||||
|
|
||||||
To exploit this successfully would require the client to choose to
|
|
||||||
connect peer-to-peer to a malicious D-Bus server and to choose the SHA-1
|
|
||||||
authentication mechanism in preference to all the other mechanisms. This
|
|
||||||
is vanishingly unlikely.
|
|
||||||
|
|
||||||
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
|
|
||||||
Fixes: #3931
|
|
||||||
---
|
|
||||||
gio/gdbusauthmechanismsha1.c | 36 ++++++++++++++++++++++++++++++++++++
|
|
||||||
1 file changed, 36 insertions(+)
|
|
||||||
|
|
||||||
diff --git a/gio/gdbusauthmechanismsha1.c b/gio/gdbusauthmechanismsha1.c
|
|
||||||
index 94fe0bce8..d2a045f4c 100644
|
|
||||||
--- a/gio/gdbusauthmechanismsha1.c
|
|
||||||
+++ b/gio/gdbusauthmechanismsha1.c
|
|
||||||
@@ -1160,6 +1160,34 @@ mechanism_client_initiate (GDBusAuthMechanism *mechanism,
|
|
||||||
return initial_response;
|
|
||||||
}
|
|
||||||
|
|
||||||
+/* Context names must be valid ASCII, nonzero length, and may not contain the
|
|
||||||
+ * characters slash ("/"), backslash ("\"), space (" "), newline ("\n"),
|
|
||||||
+ * carriage return ("\r"), tab ("\t"), or period (".").
|
|
||||||
+ *
|
|
||||||
+ * See https://dbus.freedesktop.org/doc/dbus-specification.html#auth-mechanisms-sha */
|
|
||||||
+static gboolean
|
|
||||||
+validate_cookie_context (const char *cookie_context)
|
|
||||||
+{
|
|
||||||
+ size_t i = 0;
|
|
||||||
+
|
|
||||||
+ g_return_val_if_fail (cookie_context != NULL, FALSE);
|
|
||||||
+
|
|
||||||
+ for (i = 0; cookie_context[i] != '\0'; i++)
|
|
||||||
+ {
|
|
||||||
+ if ((uint8_t) cookie_context[i] >= 128 ||
|
|
||||||
+ cookie_context[i] == '/' ||
|
|
||||||
+ cookie_context[i] == '\\' ||
|
|
||||||
+ cookie_context[i] == ' ' ||
|
|
||||||
+ cookie_context[i] == '\n' ||
|
|
||||||
+ cookie_context[i] == '\r' ||
|
|
||||||
+ cookie_context[i] == '\t' ||
|
|
||||||
+ cookie_context[i] == '.')
|
|
||||||
+ return FALSE;
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ return (i > 0);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
static void
|
|
||||||
mechanism_client_data_receive (GDBusAuthMechanism *mechanism,
|
|
||||||
const gchar *data,
|
|
||||||
@@ -1194,6 +1222,14 @@ mechanism_client_data_receive (GDBusAuthMechanism *mechanism,
|
|
||||||
}
|
|
||||||
|
|
||||||
cookie_context = tokens[0];
|
|
||||||
+ if (!validate_cookie_context (tokens[0]))
|
|
||||||
+ {
|
|
||||||
+ g_free (m->priv->reject_reason);
|
|
||||||
+ m->priv->reject_reason = g_strdup_printf ("Malformed cookie_context '%s'", tokens[0]);
|
|
||||||
+ m->priv->state = G_DBUS_AUTH_MECHANISM_STATE_REJECTED;
|
|
||||||
+ goto out;
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
cookie_id = g_ascii_strtoll (tokens[1], &endp, 10);
|
|
||||||
if (*endp != '\0')
|
|
||||||
{
|
|
||||||
|
|
||||||
From 5bf53b50de87f0ad037508e4bd0099c4d0519b4b Mon Sep 17 00:00:00 2001
|
|
||||||
From: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Date: Tue, 28 Apr 2026 15:49:54 +0100
|
|
||||||
Subject: [PATCH 2/5] gdbusauthmechanismsha1: Improve validation of cookie ID
|
|
||||||
MIME-Version: 1.0
|
|
||||||
Content-Type: text/plain; charset=UTF-8
|
|
||||||
Content-Transfer-Encoding: 8bit
|
|
||||||
|
|
||||||
The D-Bus specification says the cookie ID has to be non-negative, but
|
|
||||||
we weren’t checking that (or checking that it was non-empty).
|
|
||||||
|
|
||||||
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
---
|
|
||||||
gio/gdbusauthmechanismsha1.c | 6 +++---
|
|
||||||
1 file changed, 3 insertions(+), 3 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/gio/gdbusauthmechanismsha1.c b/gio/gdbusauthmechanismsha1.c
|
|
||||||
index d2a045f4c..9f2d3ded6 100644
|
|
||||||
--- a/gio/gdbusauthmechanismsha1.c
|
|
||||||
+++ b/gio/gdbusauthmechanismsha1.c
|
|
||||||
@@ -1196,7 +1196,7 @@ mechanism_client_data_receive (GDBusAuthMechanism *mechanism,
|
|
||||||
GDBusAuthMechanismSha1 *m = G_DBUS_AUTH_MECHANISM_SHA1 (mechanism);
|
|
||||||
gchar **tokens;
|
|
||||||
const gchar *cookie_context;
|
|
||||||
- guint cookie_id;
|
|
||||||
+ int64_t cookie_id;
|
|
||||||
const gchar *server_challenge;
|
|
||||||
gchar *client_challenge;
|
|
||||||
gchar *endp;
|
|
||||||
@@ -1231,7 +1231,7 @@ mechanism_client_data_receive (GDBusAuthMechanism *mechanism,
|
|
||||||
}
|
|
||||||
|
|
||||||
cookie_id = g_ascii_strtoll (tokens[1], &endp, 10);
|
|
||||||
- if (*endp != '\0')
|
|
||||||
+ if (*endp != '\0' || endp == tokens[1] || cookie_id < 0 || cookie_id > UINT32_MAX)
|
|
||||||
{
|
|
||||||
g_free (m->priv->reject_reason);
|
|
||||||
m->priv->reject_reason = g_strdup_printf ("Malformed cookie_id '%s'", tokens[1]);
|
|
||||||
@@ -1241,7 +1241,7 @@ mechanism_client_data_receive (GDBusAuthMechanism *mechanism,
|
|
||||||
server_challenge = tokens[2];
|
|
||||||
|
|
||||||
error = NULL;
|
|
||||||
- cookie = keyring_lookup_entry (cookie_context, cookie_id, &error);
|
|
||||||
+ cookie = keyring_lookup_entry (cookie_context, (unsigned int) cookie_id, &error);
|
|
||||||
if (cookie == NULL)
|
|
||||||
{
|
|
||||||
g_free (m->priv->reject_reason);
|
|
||||||
|
|
||||||
From 2b185a1b6ff0fca50e3bf0032e81a09a4dbfd550 Mon Sep 17 00:00:00 2001
|
|
||||||
From: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Date: Tue, 28 Apr 2026 15:51:00 +0100
|
|
||||||
Subject: [PATCH 3/5] gdbusauthmechanism: Expose client reject reason as a new
|
|
||||||
vfunc
|
|
||||||
|
|
||||||
We can do this because `gdbusauthmechanism.h` is a private header.
|
|
||||||
|
|
||||||
Hook it up to the existing `reject_reason` code in each
|
|
||||||
`GDBusAuthMechanism` implementation, as all three implementations
|
|
||||||
currently intermingle reject reasons from the server and client code, so
|
|
||||||
there would currently be no benefit to having a separate server and
|
|
||||||
client implementation of `*_get_reject_reason()`.
|
|
||||||
|
|
||||||
This new private API will be used in a new unit test in the following
|
|
||||||
commit.
|
|
||||||
|
|
||||||
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
---
|
|
||||||
gio/gdbusauthmechanism.c | 7 +++++++
|
|
||||||
gio/gdbusauthmechanism.h | 2 ++
|
|
||||||
gio/gdbusauthmechanismanon.c | 8 ++++----
|
|
||||||
gio/gdbusauthmechanismexternal.c | 8 ++++----
|
|
||||||
gio/gdbusauthmechanismsha1.c | 8 ++++----
|
|
||||||
5 files changed, 21 insertions(+), 12 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/gio/gdbusauthmechanism.c b/gio/gdbusauthmechanism.c
|
|
||||||
index 897d41496..6ed7fb546 100644
|
|
||||||
--- a/gio/gdbusauthmechanism.c
|
|
||||||
+++ b/gio/gdbusauthmechanism.c
|
|
||||||
@@ -324,6 +324,13 @@ _g_dbus_auth_mechanism_client_data_send (GDBusAuthMechanism *mechanism,
|
|
||||||
return G_DBUS_AUTH_MECHANISM_GET_CLASS (mechanism)->client_data_send (mechanism, out_data_len);
|
|
||||||
}
|
|
||||||
|
|
||||||
+gchar *
|
|
||||||
+_g_dbus_auth_mechanism_client_get_reject_reason (GDBusAuthMechanism *mechanism)
|
|
||||||
+{
|
|
||||||
+ g_return_val_if_fail (G_IS_DBUS_AUTH_MECHANISM (mechanism), NULL);
|
|
||||||
+ return G_DBUS_AUTH_MECHANISM_GET_CLASS (mechanism)->client_get_reject_reason (mechanism);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
void
|
|
||||||
_g_dbus_auth_mechanism_client_shutdown (GDBusAuthMechanism *mechanism)
|
|
||||||
{
|
|
||||||
diff --git a/gio/gdbusauthmechanism.h b/gio/gdbusauthmechanism.h
|
|
||||||
index cee87b0a2..5ab3e34c9 100644
|
|
||||||
--- a/gio/gdbusauthmechanism.h
|
|
||||||
+++ b/gio/gdbusauthmechanism.h
|
|
||||||
@@ -97,6 +97,7 @@ struct _GDBusAuthMechanismClass
|
|
||||||
gsize data_len);
|
|
||||||
gchar *(*client_data_send) (GDBusAuthMechanism *mechanism,
|
|
||||||
gsize *out_data_len);
|
|
||||||
+ gchar *(*client_get_reject_reason) (GDBusAuthMechanism *mechanism);
|
|
||||||
void (*client_shutdown) (GDBusAuthMechanism *mechanism);
|
|
||||||
};
|
|
||||||
|
|
||||||
@@ -144,6 +145,7 @@ void _g_dbus_auth_mechanism_client_data_receive (GDBus
|
|
||||||
gsize data_len);
|
|
||||||
gchar *_g_dbus_auth_mechanism_client_data_send (GDBusAuthMechanism *mechanism,
|
|
||||||
gsize *out_data_len);
|
|
||||||
+gchar *_g_dbus_auth_mechanism_client_get_reject_reason (GDBusAuthMechanism *mechanism);
|
|
||||||
void _g_dbus_auth_mechanism_client_shutdown (GDBusAuthMechanism *mechanism);
|
|
||||||
|
|
||||||
|
|
||||||
diff --git a/gio/gdbusauthmechanismanon.c b/gio/gdbusauthmechanismanon.c
|
|
||||||
index dd57826ff..ab947bba6 100644
|
|
||||||
--- a/gio/gdbusauthmechanismanon.c
|
|
||||||
+++ b/gio/gdbusauthmechanismanon.c
|
|
||||||
@@ -54,7 +54,7 @@ static void mechanism_server_data_receive (GDBusAuthMe
|
|
||||||
gsize data_len);
|
|
||||||
static gchar *mechanism_server_data_send (GDBusAuthMechanism *mechanism,
|
|
||||||
gsize *out_data_len);
|
|
||||||
-static gchar *mechanism_server_get_reject_reason (GDBusAuthMechanism *mechanism);
|
|
||||||
+static gchar *mechanism_server_or_client_get_reject_reason (GDBusAuthMechanism *mechanism);
|
|
||||||
static void mechanism_server_shutdown (GDBusAuthMechanism *mechanism);
|
|
||||||
static GDBusAuthMechanismState mechanism_client_get_state (GDBusAuthMechanism *mechanism);
|
|
||||||
static gchar *mechanism_client_initiate (GDBusAuthMechanism *mechanism,
|
|
||||||
@@ -100,12 +100,13 @@ _g_dbus_auth_mechanism_anon_class_init (GDBusAuthMechanismAnonClass *klass)
|
|
||||||
mechanism_class->server_initiate = mechanism_server_initiate;
|
|
||||||
mechanism_class->server_data_receive = mechanism_server_data_receive;
|
|
||||||
mechanism_class->server_data_send = mechanism_server_data_send;
|
|
||||||
- mechanism_class->server_get_reject_reason = mechanism_server_get_reject_reason;
|
|
||||||
+ mechanism_class->server_get_reject_reason = mechanism_server_or_client_get_reject_reason;
|
|
||||||
mechanism_class->server_shutdown = mechanism_server_shutdown;
|
|
||||||
mechanism_class->client_get_state = mechanism_client_get_state;
|
|
||||||
mechanism_class->client_initiate = mechanism_client_initiate;
|
|
||||||
mechanism_class->client_data_receive = mechanism_client_data_receive;
|
|
||||||
mechanism_class->client_data_send = mechanism_client_data_send;
|
|
||||||
+ mechanism_class->client_get_reject_reason = mechanism_server_or_client_get_reject_reason;
|
|
||||||
mechanism_class->client_shutdown = mechanism_client_shutdown;
|
|
||||||
}
|
|
||||||
|
|
||||||
@@ -219,12 +220,11 @@ mechanism_server_data_send (GDBusAuthMechanism *mechanism,
|
|
||||||
}
|
|
||||||
|
|
||||||
static gchar *
|
|
||||||
-mechanism_server_get_reject_reason (GDBusAuthMechanism *mechanism)
|
|
||||||
+mechanism_server_or_client_get_reject_reason (GDBusAuthMechanism *mechanism)
|
|
||||||
{
|
|
||||||
GDBusAuthMechanismAnon *m = G_DBUS_AUTH_MECHANISM_ANON (mechanism);
|
|
||||||
|
|
||||||
g_return_val_if_fail (G_IS_DBUS_AUTH_MECHANISM_ANON (mechanism), NULL);
|
|
||||||
- g_return_val_if_fail (m->priv->is_server && !m->priv->is_client, NULL);
|
|
||||||
g_return_val_if_fail (m->priv->state == G_DBUS_AUTH_MECHANISM_STATE_REJECTED, NULL);
|
|
||||||
|
|
||||||
/* can never end up here because we are never in the REJECTED state */
|
|
||||||
diff --git a/gio/gdbusauthmechanismexternal.c b/gio/gdbusauthmechanismexternal.c
|
|
||||||
index 182c57278..30adfc415 100644
|
|
||||||
--- a/gio/gdbusauthmechanismexternal.c
|
|
||||||
+++ b/gio/gdbusauthmechanismexternal.c
|
|
||||||
@@ -57,7 +57,7 @@ static void mechanism_server_data_receive (GDBusAuthMe
|
|
||||||
gsize data_len);
|
|
||||||
static gchar *mechanism_server_data_send (GDBusAuthMechanism *mechanism,
|
|
||||||
gsize *out_data_len);
|
|
||||||
-static gchar *mechanism_server_get_reject_reason (GDBusAuthMechanism *mechanism);
|
|
||||||
+static gchar *mechanism_server_or_client_get_reject_reason (GDBusAuthMechanism *mechanism);
|
|
||||||
static void mechanism_server_shutdown (GDBusAuthMechanism *mechanism);
|
|
||||||
static GDBusAuthMechanismState mechanism_client_get_state (GDBusAuthMechanism *mechanism);
|
|
||||||
static gchar *mechanism_client_initiate (GDBusAuthMechanism *mechanism,
|
|
||||||
@@ -103,12 +103,13 @@ _g_dbus_auth_mechanism_external_class_init (GDBusAuthMechanismExternalClass *kla
|
|
||||||
mechanism_class->server_initiate = mechanism_server_initiate;
|
|
||||||
mechanism_class->server_data_receive = mechanism_server_data_receive;
|
|
||||||
mechanism_class->server_data_send = mechanism_server_data_send;
|
|
||||||
- mechanism_class->server_get_reject_reason = mechanism_server_get_reject_reason;
|
|
||||||
+ mechanism_class->server_get_reject_reason = mechanism_server_or_client_get_reject_reason;
|
|
||||||
mechanism_class->server_shutdown = mechanism_server_shutdown;
|
|
||||||
mechanism_class->client_get_state = mechanism_client_get_state;
|
|
||||||
mechanism_class->client_initiate = mechanism_client_initiate;
|
|
||||||
mechanism_class->client_data_receive = mechanism_client_data_receive;
|
|
||||||
mechanism_class->client_data_send = mechanism_client_data_send;
|
|
||||||
+ mechanism_class->client_get_reject_reason = mechanism_server_or_client_get_reject_reason;
|
|
||||||
mechanism_class->client_shutdown = mechanism_client_shutdown;
|
|
||||||
}
|
|
||||||
|
|
||||||
@@ -285,12 +286,11 @@ mechanism_server_data_send (GDBusAuthMechanism *mechanism,
|
|
||||||
}
|
|
||||||
|
|
||||||
static gchar *
|
|
||||||
-mechanism_server_get_reject_reason (GDBusAuthMechanism *mechanism)
|
|
||||||
+mechanism_server_or_client_get_reject_reason (GDBusAuthMechanism *mechanism)
|
|
||||||
{
|
|
||||||
GDBusAuthMechanismExternal *m = G_DBUS_AUTH_MECHANISM_EXTERNAL (mechanism);
|
|
||||||
|
|
||||||
g_return_val_if_fail (G_IS_DBUS_AUTH_MECHANISM_EXTERNAL (mechanism), NULL);
|
|
||||||
- g_return_val_if_fail (m->priv->is_server && !m->priv->is_client, NULL);
|
|
||||||
g_return_val_if_fail (m->priv->state == G_DBUS_AUTH_MECHANISM_STATE_REJECTED, NULL);
|
|
||||||
|
|
||||||
/* can never end up here because we are never in the REJECTED state */
|
|
||||||
diff --git a/gio/gdbusauthmechanismsha1.c b/gio/gdbusauthmechanismsha1.c
|
|
||||||
index 9f2d3ded6..d74f70387 100644
|
|
||||||
--- a/gio/gdbusauthmechanismsha1.c
|
|
||||||
+++ b/gio/gdbusauthmechanismsha1.c
|
|
||||||
@@ -111,7 +111,7 @@ static void mechanism_server_data_receive (GDBusAuthMe
|
|
||||||
gsize data_len);
|
|
||||||
static gchar *mechanism_server_data_send (GDBusAuthMechanism *mechanism,
|
|
||||||
gsize *out_data_len);
|
|
||||||
-static gchar *mechanism_server_get_reject_reason (GDBusAuthMechanism *mechanism);
|
|
||||||
+static gchar *mechanism_server_or_client_get_reject_reason (GDBusAuthMechanism *mechanism);
|
|
||||||
static void mechanism_server_shutdown (GDBusAuthMechanism *mechanism);
|
|
||||||
static GDBusAuthMechanismState mechanism_client_get_state (GDBusAuthMechanism *mechanism);
|
|
||||||
static gchar *mechanism_client_initiate (GDBusAuthMechanism *mechanism,
|
|
||||||
@@ -163,12 +163,13 @@ _g_dbus_auth_mechanism_sha1_class_init (GDBusAuthMechanismSha1Class *klass)
|
|
||||||
mechanism_class->server_initiate = mechanism_server_initiate;
|
|
||||||
mechanism_class->server_data_receive = mechanism_server_data_receive;
|
|
||||||
mechanism_class->server_data_send = mechanism_server_data_send;
|
|
||||||
- mechanism_class->server_get_reject_reason = mechanism_server_get_reject_reason;
|
|
||||||
+ mechanism_class->server_get_reject_reason = mechanism_server_or_client_get_reject_reason;
|
|
||||||
mechanism_class->server_shutdown = mechanism_server_shutdown;
|
|
||||||
mechanism_class->client_get_state = mechanism_client_get_state;
|
|
||||||
mechanism_class->client_initiate = mechanism_client_initiate;
|
|
||||||
mechanism_class->client_data_receive = mechanism_client_data_receive;
|
|
||||||
mechanism_class->client_data_send = mechanism_client_data_send;
|
|
||||||
+ mechanism_class->client_get_reject_reason = mechanism_server_or_client_get_reject_reason;
|
|
||||||
mechanism_class->client_shutdown = mechanism_client_shutdown;
|
|
||||||
}
|
|
||||||
|
|
||||||
@@ -1096,12 +1097,11 @@ mechanism_server_data_send (GDBusAuthMechanism *mechanism,
|
|
||||||
}
|
|
||||||
|
|
||||||
static gchar *
|
|
||||||
-mechanism_server_get_reject_reason (GDBusAuthMechanism *mechanism)
|
|
||||||
+mechanism_server_or_client_get_reject_reason (GDBusAuthMechanism *mechanism)
|
|
||||||
{
|
|
||||||
GDBusAuthMechanismSha1 *m = G_DBUS_AUTH_MECHANISM_SHA1 (mechanism);
|
|
||||||
|
|
||||||
g_return_val_if_fail (G_IS_DBUS_AUTH_MECHANISM_SHA1 (mechanism), NULL);
|
|
||||||
- g_return_val_if_fail (m->priv->is_server && !m->priv->is_client, NULL);
|
|
||||||
g_return_val_if_fail (m->priv->state == G_DBUS_AUTH_MECHANISM_STATE_REJECTED, NULL);
|
|
||||||
|
|
||||||
return g_strdup (m->priv->reject_reason);
|
|
||||||
|
|
||||||
From 0c526648c0346fd7287941817641d235ddf4998a Mon Sep 17 00:00:00 2001
|
|
||||||
From: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Date: Tue, 28 Apr 2026 15:52:53 +0100
|
|
||||||
Subject: [PATCH 4/5] tests: Add a unit test for GDBusAuthMechanismSha1 cookie
|
|
||||||
context parsing
|
|
||||||
|
|
||||||
This checks for regressions in the fixes from the previous few commits.
|
|
||||||
|
|
||||||
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Helps: #3931
|
|
||||||
---
|
|
||||||
gio/gdbusauthmechanismsha1.c | 2 +-
|
|
||||||
gio/tests/gdbus-auth-mechanism-sha1.c | 177 ++++++++++++++++++++++++++
|
|
||||||
gio/tests/meson.build | 1 +
|
|
||||||
3 files changed, 179 insertions(+), 1 deletion(-)
|
|
||||||
create mode 100644 gio/tests/gdbus-auth-mechanism-sha1.c
|
|
||||||
|
|
||||||
diff --git a/gio/gdbusauthmechanismsha1.c b/gio/gdbusauthmechanismsha1.c
|
|
||||||
index d74f70387..cb1a4f828 100644
|
|
||||||
--- a/gio/gdbusauthmechanismsha1.c
|
|
||||||
+++ b/gio/gdbusauthmechanismsha1.c
|
|
||||||
@@ -1174,7 +1174,7 @@ validate_cookie_context (const char *cookie_context)
|
|
||||||
|
|
||||||
for (i = 0; cookie_context[i] != '\0'; i++)
|
|
||||||
{
|
|
||||||
- if ((uint8_t) cookie_context[i] >= 128 ||
|
|
||||||
+ if ((guint8) cookie_context[i] >= 128 ||
|
|
||||||
cookie_context[i] == '/' ||
|
|
||||||
cookie_context[i] == '\\' ||
|
|
||||||
cookie_context[i] == ' ' ||
|
|
||||||
diff --git a/gio/tests/gdbus-auth-mechanism-sha1.c b/gio/tests/gdbus-auth-mechanism-sha1.c
|
|
||||||
new file mode 100644
|
|
||||||
index 000000000..abcdb4e3e
|
|
||||||
--- /dev/null
|
|
||||||
+++ b/gio/tests/gdbus-auth-mechanism-sha1.c
|
|
||||||
@@ -0,0 +1,177 @@
|
|
||||||
+/* GLib testing framework examples and tests
|
|
||||||
+ *
|
|
||||||
+ * Copyright (C) 2026 Philip Withnall
|
|
||||||
+ *
|
|
||||||
+ * SPDX-License-Identifier: LGPL-2.1-or-later
|
|
||||||
+ *
|
|
||||||
+ * This library is free software; you can redistribute it and/or
|
|
||||||
+ * modify it under the terms of the GNU Lesser General Public
|
|
||||||
+ * License as published by the Free Software Foundation; either
|
|
||||||
+ * version 2.1 of the License, or (at your option) any later version.
|
|
||||||
+ *
|
|
||||||
+ * This library is distributed in the hope that it will be useful,
|
|
||||||
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
+ * Lesser General Public License for more details.
|
|
||||||
+ *
|
|
||||||
+ * You should have received a copy of the GNU Lesser General
|
|
||||||
+ * Public License along with this library; if not, see <http://www.gnu.org/licenses/>.
|
|
||||||
+ *
|
|
||||||
+ * Author: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
+ */
|
|
||||||
+
|
|
||||||
+#include <locale.h>
|
|
||||||
+#include <gio/gio.h>
|
|
||||||
+
|
|
||||||
+#include <string.h>
|
|
||||||
+#include <unistd.h>
|
|
||||||
+
|
|
||||||
+#include "gdbus-tests.h"
|
|
||||||
+
|
|
||||||
+#ifdef G_OS_UNIX
|
|
||||||
+#include <gio/gunixconnection.h>
|
|
||||||
+#include <gio/gnetworkingprivate.h>
|
|
||||||
+#include <gio/gunixsocketaddress.h>
|
|
||||||
+#include <gio/gunixfdlist.h>
|
|
||||||
+#endif
|
|
||||||
+
|
|
||||||
+#define GIO_COMPILATION 1
|
|
||||||
+#include "gdbusauthmechanism.h"
|
|
||||||
+#include "gdbusauthmechanismsha1.h"
|
|
||||||
+
|
|
||||||
+/* Vfunc wrappers copied from gdbusauthmechanism.c as they are not public. */
|
|
||||||
+static gboolean
|
|
||||||
+dbus_auth_mechanism_is_supported (GDBusAuthMechanism *mechanism)
|
|
||||||
+{
|
|
||||||
+ return G_DBUS_AUTH_MECHANISM_GET_CLASS (mechanism)->is_supported (mechanism);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
+static GDBusAuthMechanismState
|
|
||||||
+dbus_auth_mechanism_client_get_state (GDBusAuthMechanism *mechanism)
|
|
||||||
+{
|
|
||||||
+ return G_DBUS_AUTH_MECHANISM_GET_CLASS (mechanism)->client_get_state (mechanism);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
+static gchar *
|
|
||||||
+dbus_auth_mechanism_client_initiate (GDBusAuthMechanism *mechanism,
|
|
||||||
+ GDBusConnectionFlags conn_flags,
|
|
||||||
+ size_t *out_initial_response_len)
|
|
||||||
+{
|
|
||||||
+ return G_DBUS_AUTH_MECHANISM_GET_CLASS (mechanism)->client_initiate (mechanism,
|
|
||||||
+ conn_flags,
|
|
||||||
+ out_initial_response_len);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
+static void
|
|
||||||
+dbus_auth_mechanism_client_data_receive (GDBusAuthMechanism *mechanism,
|
|
||||||
+ const char *data,
|
|
||||||
+ size_t data_len)
|
|
||||||
+{
|
|
||||||
+ G_DBUS_AUTH_MECHANISM_GET_CLASS (mechanism)->client_data_receive (mechanism, data, data_len);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
+static char *
|
|
||||||
+dbus_auth_mechanism_client_get_reject_reason (GDBusAuthMechanism *mechanism)
|
|
||||||
+{
|
|
||||||
+ return G_DBUS_AUTH_MECHANISM_GET_CLASS (mechanism)->client_get_reject_reason (mechanism);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
+static void
|
|
||||||
+dbus_auth_mechanism_client_shutdown (GDBusAuthMechanism *mechanism)
|
|
||||||
+{
|
|
||||||
+ G_DBUS_AUTH_MECHANISM_GET_CLASS (mechanism)->client_shutdown (mechanism);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
+static void
|
|
||||||
+test_server_challenge_validation (void)
|
|
||||||
+{
|
|
||||||
+ const struct
|
|
||||||
+ {
|
|
||||||
+ const char *server_challenge;
|
|
||||||
+ const char *expected_reject_reason_prefix;
|
|
||||||
+ }
|
|
||||||
+ vectors[] = {
|
|
||||||
+ { "valid_context 123 456", "Problems looking up entry in keyring" },
|
|
||||||
+ { "invalid/context 123 456", "Malformed cookie_context" },
|
|
||||||
+ { "invalid.context 123 456", "Malformed cookie_context" },
|
|
||||||
+ { " 123 456", "Malformed cookie_context" },
|
|
||||||
+ { "😀 123 456", "Malformed cookie_context" },
|
|
||||||
+ { "invalid\ncontext 123 456", "Malformed cookie_context" },
|
|
||||||
+ { "invalid\rcontext 123 456", "Malformed cookie_context" },
|
|
||||||
+ { "invalid\tcontext 123 456", "Malformed cookie_context" },
|
|
||||||
+ { "invalid\\context 123 456", "Malformed cookie_context" },
|
|
||||||
+ { "valid_context 456", "Malformed cookie_id" },
|
|
||||||
+ { "valid_context 123notanumber 456", "Malformed cookie_id" },
|
|
||||||
+ { "valid_context -1 456", "Malformed cookie_id" },
|
|
||||||
+ { "valid_context 4294967296 456", "Malformed cookie_id" },
|
|
||||||
+ { "valid_context 123 ", "Malformed data" },
|
|
||||||
+ { "valid_context ", "Malformed data" },
|
|
||||||
+ };
|
|
||||||
+ GType mechanism_type;
|
|
||||||
+ GDBusConnection *connection = NULL;
|
|
||||||
+
|
|
||||||
+ g_test_summary ("Test that GDBusAuthMechanismSha1 rejects various malformed server data lines");
|
|
||||||
+
|
|
||||||
+ /* Briefly connect to the actual bus to ensure the GDBusAuth mechanisms are
|
|
||||||
+ * all registered. */
|
|
||||||
+ session_bus_up ();
|
|
||||||
+
|
|
||||||
+ connection = g_bus_get_sync (G_BUS_TYPE_SESSION, NULL, NULL);
|
|
||||||
+ g_assert_nonnull (connection);
|
|
||||||
+ g_clear_object (&connection);
|
|
||||||
+
|
|
||||||
+ session_bus_down ();
|
|
||||||
+
|
|
||||||
+ /* Check that we now have the type ID for GDBusAuthMechanismSha1 */
|
|
||||||
+ mechanism_type = g_type_from_name ("GDBusAuthMechanismSha1");
|
|
||||||
+ g_assert_cmpint (mechanism_type, !=, 0);
|
|
||||||
+
|
|
||||||
+ for (size_t i = 0; i < G_N_ELEMENTS (vectors); i++)
|
|
||||||
+ {
|
|
||||||
+ GDBusAuthMechanism *mechanism = NULL;
|
|
||||||
+ char *data = NULL;
|
|
||||||
+ size_t data_len = 0;
|
|
||||||
+ char *reject_reason = NULL;
|
|
||||||
+
|
|
||||||
+ mechanism = g_object_new (mechanism_type, NULL);
|
|
||||||
+
|
|
||||||
+ if (!dbus_auth_mechanism_is_supported (mechanism))
|
|
||||||
+ {
|
|
||||||
+ g_test_skip ("Mechanism not supported");
|
|
||||||
+ g_clear_object (&mechanism);
|
|
||||||
+ return;
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ data = dbus_auth_mechanism_client_initiate (mechanism,
|
|
||||||
+ G_DBUS_CONNECTION_FLAGS_AUTHENTICATION_CLIENT,
|
|
||||||
+ &data_len);
|
|
||||||
+ g_free (data);
|
|
||||||
+
|
|
||||||
+ dbus_auth_mechanism_client_data_receive (mechanism, vectors[i].server_challenge, strlen (vectors[i].server_challenge));
|
|
||||||
+
|
|
||||||
+ g_assert_cmpint (dbus_auth_mechanism_client_get_state (mechanism), ==, G_DBUS_AUTH_MECHANISM_STATE_REJECTED);
|
|
||||||
+
|
|
||||||
+ reject_reason = dbus_auth_mechanism_client_get_reject_reason (mechanism);
|
|
||||||
+ g_assert_true (g_str_has_prefix (reject_reason, vectors[i].expected_reject_reason_prefix));
|
|
||||||
+ g_free (reject_reason);
|
|
||||||
+
|
|
||||||
+ dbus_auth_mechanism_client_shutdown (mechanism);
|
|
||||||
+
|
|
||||||
+ g_clear_object (&mechanism);
|
|
||||||
+ }
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
+int
|
|
||||||
+main (int argc,
|
|
||||||
+ char *argv[])
|
|
||||||
+{
|
|
||||||
+ setlocale (LC_ALL, "C");
|
|
||||||
+
|
|
||||||
+ g_test_init (&argc, &argv, G_TEST_OPTION_ISOLATE_DIRS, NULL);
|
|
||||||
+
|
|
||||||
+ g_test_dbus_unset ();
|
|
||||||
+
|
|
||||||
+ g_test_add_func ("/gdbus/auth-mechanism-sha1/server-challenge-validation", test_server_challenge_validation);
|
|
||||||
+
|
|
||||||
+ return g_test_run ();
|
|
||||||
+}
|
|
||||||
diff --git a/gio/tests/meson.build b/gio/tests/meson.build
|
|
||||||
index 5dbfb8e60..c5380c16a 100644
|
|
||||||
--- a/gio/tests/meson.build
|
|
||||||
+++ b/gio/tests/meson.build
|
|
||||||
@@ -294,6 +294,7 @@ if host_machine.system() != 'windows'
|
|
||||||
'suite' : ['slow'],
|
|
||||||
},
|
|
||||||
'gdbus-auth' : {'extra_sources' : extra_sources},
|
|
||||||
+ 'gdbus-auth-mechanism-sha1': {'extra_sources' : extra_sources},
|
|
||||||
'gdbus-bz627724' : {'extra_sources' : extra_sources},
|
|
||||||
'gdbus-close-pending' : {'extra_sources' : extra_sources},
|
|
||||||
'gdbus-connection' : {'extra_sources' : extra_sources},
|
|
||||||
|
|
||||||
From 8c11c462af6ca9338e95ed3e4ce78d59df1c7474 Mon Sep 17 00:00:00 2001
|
|
||||||
From: RHEL Packaging Agent <redhat-ymir-agent@redhat.com>
|
|
||||||
Date: Mon, 20 Jul 2026 07:10:32 +0000
|
|
||||||
Subject: [PATCH 5/5] Fix: use GLib types instead of stdint.h types for
|
|
||||||
portability
|
|
||||||
|
|
||||||
Replace int64_t with gint64 and UINT32_MAX with G_MAXUINT32 to avoid
|
|
||||||
dependency on <stdint.h> which may not be included in older GLib builds.
|
|
||||||
---
|
|
||||||
gio/gdbusauthmechanismsha1.c | 4 ++--
|
|
||||||
1 file changed, 2 insertions(+), 2 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/gio/gdbusauthmechanismsha1.c b/gio/gdbusauthmechanismsha1.c
|
|
||||||
index cb1a4f828..007c6b901 100644
|
|
||||||
--- a/gio/gdbusauthmechanismsha1.c
|
|
||||||
+++ b/gio/gdbusauthmechanismsha1.c
|
|
||||||
@@ -1196,7 +1196,7 @@ mechanism_client_data_receive (GDBusAuthMechanism *mechanism,
|
|
||||||
GDBusAuthMechanismSha1 *m = G_DBUS_AUTH_MECHANISM_SHA1 (mechanism);
|
|
||||||
gchar **tokens;
|
|
||||||
const gchar *cookie_context;
|
|
||||||
- int64_t cookie_id;
|
|
||||||
+ gint64 cookie_id;
|
|
||||||
const gchar *server_challenge;
|
|
||||||
gchar *client_challenge;
|
|
||||||
gchar *endp;
|
|
||||||
@@ -1231,7 +1231,7 @@ mechanism_client_data_receive (GDBusAuthMechanism *mechanism,
|
|
||||||
}
|
|
||||||
|
|
||||||
cookie_id = g_ascii_strtoll (tokens[1], &endp, 10);
|
|
||||||
- if (*endp != '\0' || endp == tokens[1] || cookie_id < 0 || cookie_id > UINT32_MAX)
|
|
||||||
+ if (*endp != '\0' || endp == tokens[1] || cookie_id < 0 || cookie_id > G_MAXUINT32)
|
|
||||||
{
|
|
||||||
g_free (m->priv->reject_reason);
|
|
||||||
m->priv->reject_reason = g_strdup_printf ("Malformed cookie_id '%s'", tokens[1]);
|
|
||||||
@ -1,87 +0,0 @@
|
|||||||
From 0cf6b5ef06f44a4b259a014870cdc02780cc8ba4 Mon Sep 17 00:00:00 2001
|
|
||||||
From: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
Date: Thu, 16 Apr 2026 15:27:37 +0100
|
|
||||||
Subject: [PATCH] gdbusintrospection: Fix XML parser state handling for <node>
|
|
||||||
element nesting
|
|
||||||
|
|
||||||
The check for whether a `<node>` element in D-Bus introspection XML was
|
|
||||||
nested correctly was broken. `<node>` elements can only be at the top
|
|
||||||
level, or nested immediately within another `<node>` element.
|
|
||||||
|
|
||||||
Fix the check and add some unit tests for it.
|
|
||||||
|
|
||||||
Spotted by linhlhq as #YWH-PGM9867-204. The fix is mine, and the unit test
|
|
||||||
uses example XML strings adapted from their report.
|
|
||||||
|
|
||||||
Signed-off-by: Philip Withnall <pwithnall@gnome.org>
|
|
||||||
|
|
||||||
Fixes: #3932
|
|
||||||
---
|
|
||||||
gio/gdbusintrospection.c | 2 +-
|
|
||||||
gio/tests/gdbus-introspection.c | 33 +++++++++++++++++++++++++++++++++
|
|
||||||
2 files changed, 34 insertions(+), 1 deletion(-)
|
|
||||||
|
|
||||||
diff --git a/gio/gdbusintrospection.c b/gio/gdbusintrospection.c
|
|
||||||
index d6aa445d5..1e0cb81de 100644
|
|
||||||
--- a/gio/gdbusintrospection.c
|
|
||||||
+++ b/gio/gdbusintrospection.c
|
|
||||||
@@ -1270,7 +1270,7 @@ parser_start_element (GMarkupParseContext *context,
|
|
||||||
/* ---------------------------------------------------------------------------------------------------- */
|
|
||||||
if (strcmp (element_name, "node") == 0)
|
|
||||||
{
|
|
||||||
- if (!(g_slist_length (stack) >= 1 || strcmp (stack->next->data, "node") != 0))
|
|
||||||
+ if (stack->next != NULL && strcmp (stack->next->data, "node") != 0)
|
|
||||||
{
|
|
||||||
g_set_error_literal (error,
|
|
||||||
G_MARKUP_ERROR,
|
|
||||||
diff --git a/gio/tests/gdbus-introspection.c b/gio/tests/gdbus-introspection.c
|
|
||||||
index 50c0cc721..e2cdf0a25 100644
|
|
||||||
--- a/gio/tests/gdbus-introspection.c
|
|
||||||
+++ b/gio/tests/gdbus-introspection.c
|
|
||||||
@@ -297,6 +297,38 @@ test_extra_data (void)
|
|
||||||
g_dbus_node_info_unref (info);
|
|
||||||
}
|
|
||||||
|
|
||||||
+static void
|
|
||||||
+test_invalid (void)
|
|
||||||
+{
|
|
||||||
+ const struct
|
|
||||||
+ {
|
|
||||||
+ const char *xml;
|
|
||||||
+ GMarkupError expected_error_code;
|
|
||||||
+ }
|
|
||||||
+ vectors[] =
|
|
||||||
+ {
|
|
||||||
+ { "", G_MARKUP_ERROR_EMPTY },
|
|
||||||
+ { "<node><interface name=\"I\"><method name=\"M\"><node><interface name=\"I2\"></interface></node></method>", G_MARKUP_ERROR_INVALID_CONTENT },
|
|
||||||
+ { "<node><interface name=\"I\"><signal name=\"S\"><node><interface name=\"I2\"><signal name=\"S2\"></signal></interface></node></signal>", G_MARKUP_ERROR_INVALID_CONTENT },
|
|
||||||
+ { "<node><interface name=\"I\"><property name=\"P\" type=\"s\" access=\"read\"><node><interface name=\"I2\"></interface></node></property>", G_MARKUP_ERROR_INVALID_CONTENT },
|
|
||||||
+ { "<node><interface name=\"I\"><method name=\"M\"><arg type=\"\"><node><interface name=\"I2\"><method name=\"M2\"></method></interface></node></arg>", G_MARKUP_ERROR_INVALID_CONTENT },
|
|
||||||
+ };
|
|
||||||
+
|
|
||||||
+ for (size_t i = 0; i < G_N_ELEMENTS (vectors); i++)
|
|
||||||
+ {
|
|
||||||
+ GDBusNodeInfo *node;
|
|
||||||
+ GError *local_error = NULL;
|
|
||||||
+
|
|
||||||
+ g_test_message ("Testing parsing of %s gives an error", vectors[i].xml);
|
|
||||||
+
|
|
||||||
+ node = g_dbus_node_info_new_for_xml (vectors[i].xml, &local_error);
|
|
||||||
+ g_assert_error (local_error, G_MARKUP_ERROR, (int) vectors[i].expected_error_code);
|
|
||||||
+ g_assert_null (node);
|
|
||||||
+
|
|
||||||
+ g_clear_error (&local_error);
|
|
||||||
+ }
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
/* ---------------------------------------------------------------------------------------------------- */
|
|
||||||
|
|
||||||
int
|
|
||||||
@@ -314,6 +346,7 @@ main (int argc,
|
|
||||||
g_test_add_func ("/gdbus/introspection-generate", test_generate);
|
|
||||||
g_test_add_func ("/gdbus/introspection-default-direction", test_default_direction);
|
|
||||||
g_test_add_func ("/gdbus/introspection-extra-data", test_extra_data);
|
|
||||||
+ g_test_add_func ("/gdbus/introspection-invalid", test_invalid);
|
|
||||||
|
|
||||||
ret = session_bus_run ();
|
|
||||||
|
|
||||||
Loading…
Reference in New Issue
Block a user