From 5efb84f24a83ba10f6e1ae0385fa0fbc68103ad1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Date: Thu, 7 Apr 2022 17:59:00 +0400 Subject: [PATCH 01/10] gio: add GUnixFDList on win32 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit FDs are not specific to Unix. win32 has APIs to map CRT fd to/from HANDLE. Signed-off-by: Marc-André Lureau --- gio/gio.h | 1 + gio/gunixfdlist.c | 25 +++++++++++++++++++------ gio/meson.build | 2 +- 3 files changed, 21 insertions(+), 7 deletions(-) diff --git a/gio/gio.h b/gio/gio.h index e37b6bb49..6f92f8a66 100644 --- a/gio/gio.h +++ b/gio/gio.h @@ -169,6 +169,7 @@ #include #include #include +#include #include #include #include diff --git a/gio/gunixfdlist.c b/gio/gunixfdlist.c index e8c4ac55e..6689a7216 100644 --- a/gio/gunixfdlist.c +++ b/gio/gunixfdlist.c @@ -26,9 +26,11 @@ * the %G_SOCKET_FAMILY_UNIX family by using g_socket_send_message() * and received using g_socket_receive_message(). * - * Note that `` belongs to the UNIX-specific GIO - * interfaces, thus you have to use the `gio-unix-2.0.pc` pkg-config - * file when using it. + * Before 2.74, `` belonged to the UNIX-specific GIO + * interfaces, thus you had to use the `gio-unix-2.0.pc` pkg-config file when + * using it. + * + * Since 2.74, the API is available for Windows. */ /** @@ -40,7 +42,6 @@ #include "config.h" -#include #include #include #include @@ -48,6 +49,12 @@ #include "gunixfdlist.h" #include "gnetworking.h" #include "gioerror.h" +#include "glib/glib-private.h" +#include "glib/gstdio.h" + +#ifdef G_OS_WIN32 +#include +#endif struct _GUnixFDListPrivate { @@ -70,7 +77,7 @@ g_unix_fd_list_finalize (GObject *object) gint i; for (i = 0; i < list->priv->nfd; i++) - close (list->priv->fds[i]); + g_close (list->priv->fds[i], NULL); g_free (list->priv->fds); G_OBJECT_CLASS (g_unix_fd_list_parent_class) @@ -90,7 +97,9 @@ dup_close_on_exec_fd (gint fd, GError **error) { gint new_fd; +#ifndef G_OS_WIN32 gint s; +#endif #ifdef F_DUPFD_CLOEXEC do @@ -118,6 +127,9 @@ dup_close_on_exec_fd (gint fd, return -1; } +#ifdef G_OS_WIN32 + new_fd = GLIB_PRIVATE_CALL (g_win32_reopen_noninherited) (new_fd, 0, error); +#else do { s = fcntl (new_fd, F_GETFD); @@ -134,10 +146,11 @@ dup_close_on_exec_fd (gint fd, g_set_error (error, G_IO_ERROR, g_io_error_from_errno (saved_errno), "fcntl: %s", g_strerror (saved_errno)); - close (new_fd); + g_close (new_fd, NULL); return -1; } +#endif return new_fd; } diff --git a/gio/meson.build b/gio/meson.build index e980ad9e4..2d20794e4 100644 --- a/gio/meson.build +++ b/gio/meson.build @@ -354,7 +354,6 @@ if host_system != 'windows' unix_sources = files( 'gfiledescriptorbased.c', 'giounix-private.c', - 'gunixfdlist.c', 'gunixfdmessage.c', 'gunixmount.c', 'gunixmounts.c', @@ -574,6 +573,7 @@ gio_sources = files( 'gdtlsserverconnection.c', 'gunionvolumemonitor.c', 'gunixconnection.c', + 'gunixfdlist.c', 'gunixcredentialsmessage.c', 'gunixsocketaddress.c', 'gvfs.c', From b8eb64b350449e65bcd75b79172eee231966ea9c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Date: Thu, 7 Apr 2022 19:00:32 +0400 Subject: [PATCH 02/10] gio/tests: add unix-fd test to win32 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The "/unix-fd/scm" test is quite Unix-specific, the next patch is going to add a portable test. Signed-off-by: Marc-André Lureau --- gio/tests/meson.build | 2 +- gio/tests/unix-fd.c | 9 ++++++++- 2 files changed, 9 insertions(+), 2 deletions(-) diff --git a/gio/tests/meson.build b/gio/tests/meson.build index 7b4613403..7867918f5 100644 --- a/gio/tests/meson.build +++ b/gio/tests/meson.build @@ -115,6 +115,7 @@ gio_tests = { 'tls-interaction' : {'extra_sources' : ['gtesttlsbackend.c']}, 'tls-database' : {'extra_sources' : ['gtesttlsbackend.c']}, 'tls-bindings' : {'extra_sources' : ['gtesttlsbackend.c']}, + 'unix-fd' : {}, 'gdbus-address-get-session' : { # FIXME: https://gitlab.gnome.org/GNOME/glib/-/issues/1392 'should_fail' : host_system == 'darwin', @@ -194,7 +195,6 @@ if host_machine.system() != 'windows' 'resolver-parsing' : {'dependencies' : [network_libs]}, 'socket-address' : {}, 'stream-rw_all' : {}, - 'unix-fd' : {}, 'unix-mounts' : {}, 'unix-streams' : {}, 'g-file-info-filesystem-readonly' : {}, diff --git a/gio/tests/unix-fd.c b/gio/tests/unix-fd.c index b29ddca1f..ca20e80ab 100644 --- a/gio/tests/unix-fd.c +++ b/gio/tests/unix-fd.c @@ -2,8 +2,11 @@ #include #include #include -#include +#ifdef G_OS_UNIX +#include #include +#endif +#include /* ensures that no FDs are left open at the end */ static void @@ -41,6 +44,7 @@ create_fd_list (gint *fd_list) static void test_scm (void) { +#ifndef G_OS_WIN32 GError *err = NULL; GUnixFDMessage *message; GUnixFDMessage **mv; @@ -228,6 +232,9 @@ G_GNUC_END_IGNORE_DEPRECATIONS g_object_unref (list); check_fd_list (fd_list); +#else + g_test_skip ("FD SCM support doesn’t exist on Windows"); +#endif } int From c9b5b1fb940890d1881e3f203bd05380dda93dff Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Date: Tue, 17 May 2022 14:16:40 +0200 Subject: [PATCH 03/10] gio/tests: switch to g_close() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit For the better behaviour and portability. Signed-off-by: Marc-André Lureau --- gio/tests/unix-fd.c | 65 +++++++++++++++++++++------------------------ 1 file changed, 30 insertions(+), 35 deletions(-) diff --git a/gio/tests/unix-fd.c b/gio/tests/unix-fd.c index ca20e80ab..c12d83461 100644 --- a/gio/tests/unix-fd.c +++ b/gio/tests/unix-fd.c @@ -6,6 +6,7 @@ #include #include #endif +#include #include /* ensures that no FDs are left open at the end */ @@ -23,7 +24,7 @@ check_fd_list (const gint *fd_list) } for (i = 0; i < 40; i++) - close (fd_list[i]); + g_close (fd_list[i], NULL); } static void @@ -38,7 +39,7 @@ create_fd_list (gint *fd_list) } for (i = 0; i < 40; i++) - close (fd_list[i]); + g_close (fd_list[i], NULL); } static void @@ -60,7 +61,7 @@ test_scm (void) gint sv[3]; gint flags; gint nm; - gint s; + gint s, i; gchar *path; GByteArray *array; gboolean abstract; @@ -94,31 +95,24 @@ test_scm (void) g_unix_fd_message_append_fd (message, sv[0], &err); g_assert_no_error (err); - s = close (sv[0]); - g_assert_cmpint (s, ==, 0); + g_close (sv[0], &err); + g_assert_no_error (err); g_unix_fd_message_append_fd (message, sv[1], &err); g_assert_no_error (err); - s = close (sv[1]); - g_assert_cmpint (s, ==, 0); + g_close (sv[1], &err); + g_assert_no_error (err); - s = close (g_unix_fd_list_get (list, 0, &err)); - g_assert_no_error (err); - g_assert_cmpint (s, ==, 0); - s = close (g_unix_fd_list_get (list, 1, &err)); - g_assert_no_error (err); - g_assert_cmpint (s, ==, 0); - s = close (g_unix_fd_list_get (list, 0, &err)); - g_assert_no_error (err); - g_assert_cmpint (s, ==, 0); - s = close (g_unix_fd_list_get (list, 1, &err)); - g_assert_no_error (err); - g_assert_cmpint (s, ==, 0); - s = close (g_unix_fd_list_get (list, 0, &err)); - g_assert_no_error (err); - g_assert_cmpint (s, ==, 0); - s = close (g_unix_fd_list_get (list, 1, &err)); - g_assert_no_error (err); - g_assert_cmpint (s, ==, 0); + for (i = 0; i < 3; i++) + { + s = g_unix_fd_list_get (list, 0, &err); + g_assert_no_error (err); + g_close (s, &err); + g_assert_no_error (err); + s = g_unix_fd_list_get (list, 1, &err); + g_assert_no_error (err); + g_close (s, &err); + g_assert_no_error (err); + } g_object_unref (message); g_object_unref (list); @@ -135,16 +129,18 @@ test_scm (void) g_assert_no_error (err); g_assert_cmpint (s, >=, 0); - s = close (sv[0]); - g_assert_cmpint (s, ==, 0); - s = close (sv[1]); - g_assert_cmpint (s, ==, 0); - s = close (g_unix_fd_list_get (list, 0, &err)); + g_close (sv[0], &err); g_assert_no_error (err); - g_assert_cmpint (s, ==, 0); - s = close (g_unix_fd_list_get (list, 1, &err)); + g_close (sv[1], &err); + g_assert_no_error (err); + s = g_unix_fd_list_get (list, 0, &err); + g_assert_no_error (err); + g_close (s, &err); + g_assert_no_error (err); + s = g_unix_fd_list_get (list, 1, &err); + g_assert_no_error (err); + g_close (s, &err); g_assert_no_error (err); - g_assert_cmpint (s, ==, 0); s = socketpair (PF_UNIX, SOCK_STREAM, 0, sv); g_assert_cmpint (s, ==, 0); @@ -221,7 +217,7 @@ G_GNUC_END_IGNORE_DEPRECATIONS s = write (sv[0], buffer, strlen (buffer) + 1); g_assert_cmpint (s, ==, strlen (buffer) + 1); - close (sv[0]); + g_close (sv[0], NULL); memset (buffer, 0xff, sizeof buffer); s = read (peek[0], buffer, sizeof buffer); @@ -245,5 +241,4 @@ main (int argc, char **argv) g_test_add_func ("/unix-fd/scm", test_scm); return g_test_run(); - } From b5c97b1016e5fac75c3309c97d34f7afed35b2cf Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Date: Tue, 17 May 2022 13:05:57 +0200 Subject: [PATCH 04/10] gio/tests: add basic fd-list unit test to unix-fd MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit To cover win32 support. Signed-off-by: Marc-André Lureau --- gio/tests/unix-fd.c | 60 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 60 insertions(+) diff --git a/gio/tests/unix-fd.c b/gio/tests/unix-fd.c index c12d83461..ecf1aea37 100644 --- a/gio/tests/unix-fd.c +++ b/gio/tests/unix-fd.c @@ -7,7 +7,11 @@ #include #endif #include +#include #include +#ifdef G_OS_WIN32 +#include +#endif /* ensures that no FDs are left open at the end */ static void @@ -42,6 +46,61 @@ create_fd_list (gint *fd_list) g_close (fd_list[i], NULL); } +static void +test_fd_list (void) +{ + GError *err = NULL; + GUnixFDList *list; + const gint *peek; + gint *stolen; + gint fd_list[40]; + gint sv[3]; + gint s; + + create_fd_list (fd_list); + sv[2] = -1; +#ifdef G_OS_WIN32 + s = _pipe (sv, 4096, _O_NOINHERIT | _O_BINARY); + g_assert_cmpint (s, ==, 0); +#else + g_unix_open_pipe (sv, FD_CLOEXEC, &err); + g_assert_no_error (err); +#endif + list = g_unix_fd_list_new_from_array (sv, -1); + peek = g_unix_fd_list_peek_fds (list, &s); + g_assert_cmpint (s, ==, 2); + g_assert_cmpint (peek[0], ==, sv[0]); + g_assert_cmpint (peek[1], ==, sv[1]); + + s = g_unix_fd_list_get (list, 0, &err); + g_assert_no_error (err); + g_close (s, &err); + g_assert_no_error (err); + s = g_unix_fd_list_get (list, 1, &err); + g_assert_no_error (err); + g_close (s, &err); + g_assert_no_error (err); + + s = g_unix_fd_list_append (list, sv[0], &err); + g_assert_no_error (err); + g_assert_cmpint (s, >=, 0); + stolen = g_unix_fd_list_steal_fds (list, &s); + g_assert_cmpint (s, ==, 3); + g_assert_cmpint (stolen[0], ==, sv[0]); + g_assert_cmpint (stolen[1], ==, sv[1]); + g_assert_cmpint (stolen[2], >=, 0); + g_close (stolen[0], &err); + g_assert_no_error (err); + g_close (stolen[1], &err); + g_assert_no_error (err); + g_close (stolen[2], &err); + g_assert_no_error (err); + g_free (stolen); + + g_object_unref (list); + check_fd_list (fd_list); +} + static void test_scm (void) { @@ -238,6 +297,7 @@ main (int argc, char **argv) { g_test_init (&argc, &argv, NULL); + g_test_add_func ("/unix-fd/fd-list", test_fd_list); g_test_add_func ("/unix-fd/scm", test_scm); return g_test_run(); From 18886d43d28981f01daa11198704968b70677fee Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Date: Thu, 7 Apr 2022 23:26:47 +0400 Subject: [PATCH 05/10] gio/gdbusauth: remove #ifdef G_OS_UNIX around credentials MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The AF_UNIX API is available under all platforms since 2.71.1, and credentials functions returns NOT_SUPPORTED error appropriately, we can thus remove the special-casing for !unix. Signed-off-by: Marc-André Lureau --- gio/gdbusauth.c | 13 +------------ 1 file changed, 1 insertion(+), 12 deletions(-) diff --git a/gio/gdbusauth.c b/gio/gdbusauth.c index 7a7900c1b..2e3c50db6 100644 --- a/gio/gdbusauth.c +++ b/gio/gdbusauth.c @@ -37,11 +37,9 @@ #include "gdatainputstream.h" #include "gdataoutputstream.h" -#ifdef G_OS_UNIX #include "gnetworking.h" #include "gunixconnection.h" #include "gunixcredentialsmessage.h" -#endif #include "glibintl.h" @@ -972,7 +970,6 @@ _g_dbus_auth_run_server (GDBusAuth *auth, g_data_input_stream_set_newline_type (dis, G_DATA_STREAM_NEWLINE_TYPE_CR_LF); /* read the NUL-byte, possibly with credentials attached */ -#ifdef G_OS_UNIX #ifndef G_CREDENTIALS_PREFER_MESSAGE_PASSING if (G_IS_SOCKET_CONNECTION (auth->priv->stream)) { @@ -1018,15 +1015,7 @@ _g_dbus_auth_run_server (GDBusAuth *auth, goto out; } } -#else - local_error = NULL; - (void)g_data_input_stream_read_byte (dis, cancellable, &local_error); - if (local_error != NULL) - { - g_propagate_error (error, local_error); - goto out; - } -#endif + if (credentials != NULL) { if (G_UNLIKELY (_g_dbus_debug_authentication ())) From e34795b43136824339361866db85737aac3b1893 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Date: Thu, 7 Apr 2022 23:54:24 +0400 Subject: [PATCH 06/10] gio/gdbusserver: add "unix:" address support on !unix MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This is another minor left-over after GNOME/glib!2445. Signed-off-by: Marc-André Lureau --- gio/gdbusserver.c | 7 ------- 1 file changed, 7 deletions(-) diff --git a/gio/gdbusserver.c b/gio/gdbusserver.c index 3034c8f86..a45bac843 100644 --- a/gio/gdbusserver.c +++ b/gio/gdbusserver.c @@ -51,9 +51,7 @@ #include #endif -#ifdef G_OS_UNIX #include "gunixsocketaddress.h" -#endif #include "glibintl.h" @@ -673,8 +671,6 @@ g_dbus_server_stop (GDBusServer *server) /* ---------------------------------------------------------------------------------------------------- */ -#ifdef G_OS_UNIX - static gint random_ascii (void) { @@ -823,7 +819,6 @@ try_unix (GDBusServer *server, } return ret; } -#endif /* ---------------------------------------------------------------------------------------------------- */ @@ -1142,10 +1137,8 @@ initable_init (GInitable *initable, if (FALSE) { } -#ifdef G_OS_UNIX else if (g_strcmp0 (transport_name, "unix") == 0) ret = try_unix (server, address_entry, key_value_pairs, &this_error); -#endif else if (g_strcmp0 (transport_name, "tcp") == 0) ret = try_tcp (server, address_entry, key_value_pairs, FALSE, &this_error); else if (g_strcmp0 (transport_name, "nonce-tcp") == 0) From 78862837507f5929cffb7680bb66b9c1a2954a70 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Date: Sun, 15 May 2022 16:54:25 +0200 Subject: [PATCH 07/10] gio/tests: unescape the nonce_file value MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The raw value is escaped according to D-Bus rules. This is probablematic for Windows backslashed paths. We can use URI unescaping, it seems that's what gdbusaddress.c is doing too. Signed-off-by: Marc-André Lureau --- gio/tests/gdbus-peer.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gio/tests/gdbus-peer.c b/gio/tests/gdbus-peer.c index 7ca8bb715..8df78af1d 100644 --- a/gio/tests/gdbus-peer.c +++ b/gio/tests/gdbus-peer.c @@ -1724,7 +1724,7 @@ test_nonce_tcp (void) s = strstr (address, "noncefile="); g_assert (s != NULL); s += sizeof "noncefile=" - 1; - nonce_file = g_strdup (s); + nonce_file = g_uri_unescape_string (s, NULL); /* URI-unescaping should be good enough */ /* First try invalid data in the nonce file - this will actually * make the client send this and the server will reject it. The way From 984103b0e74ef10797834b9a8b2bb367270fc0d0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Date: Thu, 7 Apr 2022 20:03:51 +0400 Subject: [PATCH 08/10] gio/tests: add gdbus-peer test to win32 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Because we can :) Signed-off-by: Marc-André Lureau --- gio/tests/gdbus-peer.c | 63 ++++++++++++++++++++++++++++++++++++------ gio/tests/meson.build | 12 ++++---- 2 files changed, 60 insertions(+), 15 deletions(-) diff --git a/gio/tests/gdbus-peer.c b/gio/tests/gdbus-peer.c index 8df78af1d..a2df028e1 100644 --- a/gio/tests/gdbus-peer.c +++ b/gio/tests/gdbus-peer.c @@ -21,7 +21,6 @@ #include "config.h" #include -#include #include /* for open(2) */ @@ -43,6 +42,10 @@ #include #endif +#ifdef G_OS_WIN32 +#include +#endif + #include "gdbus-tests.h" #include "gdbus-object-manager-example/objectmanager-gen.h" @@ -296,10 +299,27 @@ on_proxy_signal_received_with_name_set (GDBusProxy *proxy, /* ---------------------------------------------------------------------------------------------------- */ +static gboolean +af_unix_works (void) +{ + int fd; + + g_networking_init (); + fd = socket (AF_UNIX, SOCK_STREAM, 0); + +#ifdef G_OS_WIN32 + closesocket (fd); + return fd != (int) INVALID_SOCKET; +#else + g_close (fd, NULL); + return fd >= 0; +#endif +} + static void setup_test_address (void) { - if (is_unix) + if (is_unix || af_unix_works ()) { g_test_message ("Testing with unix:dir address"); tmpdir = g_dir_make_tmp ("gdbus-test-XXXXXX", NULL); @@ -388,6 +408,13 @@ on_new_connection (GDBusServer *server, credentials = g_dbus_connection_get_peer_credentials (connection); g_assert (credentials != NULL); +#ifdef G_OS_WIN32 + { + DWORD *pid; + pid = g_credentials_get_native (credentials, G_CREDENTIALS_TYPE_WIN32_PID); + g_assert_cmpuint (*pid, ==, GetCurrentProcessId ()); + } +#else g_assert_cmpuint (g_credentials_get_unix_user (credentials, NULL), ==, getuid ()); #if G_CREDENTIALS_HAS_PID @@ -398,9 +425,10 @@ on_new_connection (GDBusServer *server, g_assert_cmpint (g_credentials_get_unix_pid (credentials, &error), ==, -1); g_assert_error (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED); g_clear_error (&error); -#endif +#endif /* G_CREDENTIALS_HAS_PID */ +#endif /* G_OS_WIN32 */ } -#endif +#endif /* G_CREDENTIALS_SUPPORTED */ /* export object on the newly established connection */ reg_id = g_dbus_connection_register_object (connection, @@ -998,6 +1026,13 @@ do_test_peer (void) g_assert_no_error (error); g_assert (G_IS_CREDENTIALS (credentials)); +#ifdef G_OS_WIN32 + { + DWORD *pid; + pid = g_credentials_get_native (credentials, G_CREDENTIALS_TYPE_WIN32_PID); + g_assert_cmpuint (*pid, ==, GetCurrentProcessId ()); + } +#else g_assert_cmpuint (g_credentials_get_unix_user (credentials, NULL), ==, getuid ()); #if G_CREDENTIALS_HAS_PID @@ -1008,12 +1043,13 @@ do_test_peer (void) g_assert_cmpint (g_credentials_get_unix_pid (credentials, &error), ==, -1); g_assert_error (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED); g_clear_error (&error); -#endif +#endif /* G_CREDENTIALS_HAS_PID */ g_object_unref (credentials); +#endif /* G_OS_WIN32 */ #else g_assert_error (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED); g_assert (credentials == NULL); -#endif +#endif /* G_CREDENTIALS_SOCKET_GET_CREDENTIALS_SUPPORTED */ } @@ -1472,7 +1508,7 @@ dmp_on_new_connection (GDBusServer *server, * G_DBUS_CONNECTION_FLAGS_DELAY_MESSAGE_PROCESSING really works * (GDBusServer uses this feature). */ - usleep (100 * 1000); + g_usleep (100 * 1000); /* export an object */ error = NULL; @@ -1807,17 +1843,26 @@ test_credentials (void) GCredentials *c1, *c2; GError *error; gchar *desc; + gboolean same; c1 = g_credentials_new (); c2 = g_credentials_new (); error = NULL; +#ifdef G_OS_UNIX if (g_credentials_set_unix_user (c2, getuid (), &error)) g_assert_no_error (error); +#endif - g_clear_error (&error); - g_assert (g_credentials_is_same_user (c1, c2, &error)); + same = g_credentials_is_same_user (c1, c2, &error); +#ifdef G_OS_UNIX + g_assert (same); g_assert_no_error (error); +#else + g_assert (!same); + g_assert_error (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED); + g_clear_error (&error); +#endif desc = g_credentials_to_string (c1); g_assert (desc != NULL); diff --git a/gio/tests/meson.build b/gio/tests/meson.build index 7867918f5..b90c3e5c6 100644 --- a/gio/tests/meson.build +++ b/gio/tests/meson.build @@ -81,6 +81,12 @@ gio_tests = { 'g-icon' : {}, 'gdbus-addresses' : {}, 'gdbus-message' : {}, + 'gdbus-peer' : { + 'dependencies' : [libgdbus_example_objectmanager_dep], + 'install_rpath' : installed_tests_execdir, + # FIXME: https://gitlab.gnome.org/GNOME/glib/-/issues/1392 + 'should_fail' : host_system == 'darwin', + }, 'inet-address' : {}, 'io-stream' : {}, 'memory-input-stream' : {}, @@ -184,12 +190,6 @@ endif if host_machine.system() != 'windows' gio_tests += { 'file' : {}, - 'gdbus-peer' : { - 'dependencies' : [libgdbus_example_objectmanager_dep], - 'install_rpath' : installed_tests_execdir, - # FIXME: https://gitlab.gnome.org/GNOME/glib/-/issues/1392 - 'should_fail' : host_system == 'darwin', - }, 'gdbus-peer-object-manager' : {}, 'live-g-file' : {}, 'resolver-parsing' : {'dependencies' : [network_libs]}, From 15ce3c9b37c2767c82de249e60781439c9abaf78 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Date: Tue, 17 May 2022 15:01:04 +0200 Subject: [PATCH 09/10] glib/tests/spawn-path-search: fix stack-buffer-overflow MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ==24477==ERROR: AddressSanitizer: stack-buffer-overflow on address 0x7ffde020de20 at pc 0x7f2e6f6413f1 bp 0x7ffde020c9d0 sp 0x7ffde020c180 READ of size 4101 at 0x7ffde020de20 thread T0 #0 0x7f2e6f6413f0 in __interceptor_strlen.part.0 (/lib64/libasan.so.8+0x4c3f0) #1 0x7f2e6ef4abee in g_build_path_va ../glib/gfileutils.c:1908 #2 0x7f2e6f085956 in g_test_build_filename_va ../glib/gtestutils.c:4294 #3 0x7f2e6f086684 in g_test_build_filename ../glib/gtestutils.c:4365 #4 0x403a33 in test_search_path_heap_allocation ../glib/tests/spawn-path-search.c:422 #5 0x7f2e6f0839a5 in test_case_run ../glib/gtestutils.c:2930 #6 0x7f2e6f0839a5 in g_test_run_suite_internal ../glib/gtestutils.c:3018 #7 0x7f2e6f0834ed in g_test_run_suite_internal ../glib/gtestutils.c:3035 #8 0x7f2e6f084879 in g_test_run_suite ../glib/gtestutils.c:3112 #9 0x7f2e6f084995 in g_test_run ../glib/gtestutils.c:2231 #10 0x40145f in main ../glib/tests/spawn-path-search.c:488 #11 0x7f2e6e31258f in __libc_start_call_main (/lib64/libc.so.6+0x2d58f) #12 0x7f2e6e312648 in __libc_start_main_alias_1 (/lib64/libc.so.6+0x2d648) #13 0x401524 in _start (/home/elmarco/src/gnome/glib/build/glib/tests/spawn-path-search+0x401524) Address 0x7ffde020de20 is located in stack of thread T0 at offset 4256 in frame #0 0x40387f in test_search_path_heap_allocation ../glib/tests/spawn-path-search.c:401 Signed-off-by: Marc-André Lureau --- glib/tests/spawn-path-search.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/glib/tests/spawn-path-search.c b/glib/tests/spawn-path-search.c index 5008fc960..221849d5c 100644 --- a/glib/tests/spawn-path-search.c +++ b/glib/tests/spawn-path-search.c @@ -417,7 +417,8 @@ test_search_path_heap_allocation (void) if (skip_win32 ()) return; - memset (placeholder, '_', sizeof (placeholder)); + memset (placeholder, '_', sizeof (placeholder) - 1); + placeholder[sizeof (placeholder) - 1] = '\0'; /* Force search_path_buffer to be heap-allocated */ long_dir = g_test_build_filename (G_TEST_BUILT, "path-test-subdir", placeholder, NULL); long_path = g_strjoin (G_SEARCHPATH_SEPARATOR_S, subdir, long_dir, NULL); From bb890b57d210701d4cab70f625121f2d0741d12c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Date: Tue, 17 May 2022 15:21:53 +0200 Subject: [PATCH 10/10] gobject/gsignalgroup: fix memory leaks on error MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Spotted by ASAN during the tests: Direct leak of 72 byte(s) in 1 object(s) allocated from: #0 0x7ff0b4562077 in calloc (/lib64/libasan.so.8+0xba077) #1 0x7ff0b3e8b508 in g_malloc0 ../glib/gmem.c:155 #2 0x7ff0b375052f in g_closure_new_simple ../gobject/gclosure.c:220 #3 0x7ff0b375b422 in g_cclosure_new ../gobject/gclosure.c:976 #4 0x7ff0b37d159e in g_signal_group_connect_full ../gobject/gsignalgroup.c:790 #5 0x7ff0b37d159e in g_signal_group_connect ../gobject/gsignalgroup.c:886 #6 0x4045d8 in test_signal_group_invalid ../gobject/tests/signalgroup.c:331 #7 0x7ff0b3f369a5 in test_case_run ../glib/gtestutils.c:2930 #8 0x7ff0b3f369a5 in g_test_run_suite_internal ../glib/gtestutils.c:3018 #9 0x7ff0b3f364ed in g_test_run_suite_internal ../glib/gtestutils.c:3035 #10 0x7ff0b3f364ed in g_test_run_suite_internal ../glib/gtestutils.c:3035 #11 0x7ff0b3f37879 in g_test_run_suite ../glib/gtestutils.c:3112 #12 0x7ff0b3f37995 in g_test_run ../glib/gtestutils.c:2231 #13 0x40253c in main ../gobject/tests/signalgroup.c:664 #14 0x7ff0b2de758f in __libc_start_call_main (/lib64/libc.so.6+0x2d58f) Direct leak of 72 byte(s) in 1 object(s) allocated from: #0 0x7f012addf077 in calloc (/lib64/libasan.so.8+0xba077) #1 0x7f012a708508 in g_malloc0 ../glib/gmem.c:155 #2 0x7f0129fcd52f in g_closure_new_simple ../gobject/gclosure.c:220 #3 0x7f0129fd8422 in g_cclosure_new ../gobject/gclosure.c:976 #4 0x7f012a04e5ae in g_signal_group_connect_full ../gobject/gsignalgroup.c:791 #5 0x7f012a04e5ae in g_signal_group_connect ../gobject/gsignalgroup.c:887 #6 0x4043cc in test_signal_group_invalid ../gobject/tests/signalgroup.c:308 #7 0x7f012a7b39a5 in test_case_run ../glib/gtestutils.c:2930 #8 0x7f012a7b39a5 in g_test_run_suite_internal ../glib/gtestutils.c:3018 #9 0x7f012a7b34ed in g_test_run_suite_internal ../glib/gtestutils.c:3035 #10 0x7f012a7b34ed in g_test_run_suite_internal ../glib/gtestutils.c:3035 #11 0x7f012a7b4879 in g_test_run_suite ../glib/gtestutils.c:3112 #12 0x7f012a7b4995 in g_test_run ../glib/gtestutils.c:2231 #13 0x40253c in main ../gobject/tests/signalgroup.c:664 #14 0x7f012966458f in __libc_start_call_main (/lib64/libc.so.6+0x2d58f) Signed-off-by: Marc-André Lureau --- gobject/gsignalgroup.c | 69 ++++++++++++++++++++++++------------------ 1 file changed, 40 insertions(+), 29 deletions(-) diff --git a/gobject/gsignalgroup.c b/gobject/gsignalgroup.c index 01a0a12c8..e773fc040 100644 --- a/gobject/gsignalgroup.c +++ b/gobject/gsignalgroup.c @@ -705,36 +705,22 @@ g_signal_group_new (GType target_type) NULL); } -/** - * g_signal_group_connect_closure: - * @self: a #GSignalGroup - * @detailed_signal: a string of the form `signal-name` with optional `::signal-detail` - * @closure: (not nullable): the closure to connect. - * @after: whether the handler should be called before or after the - * default handler of the signal. - * - * Connects @closure to the signal @detailed_signal on #GSignalGroup:target. - * - * You cannot connect a signal handler after #GSignalGroup:target has been set. - * - * Since: 2.74 - */ -void -g_signal_group_connect_closure (GSignalGroup *self, - const gchar *detailed_signal, - GClosure *closure, - gboolean after) +static gboolean +g_signal_group_connect_closure_ (GSignalGroup *self, + const gchar *detailed_signal, + GClosure *closure, + gboolean after) { GObject *target; SignalHandler *handler; guint signal_id; GQuark signal_detail; - g_return_if_fail (G_IS_SIGNAL_GROUP (self)); - g_return_if_fail (detailed_signal != NULL); - g_return_if_fail (g_signal_parse_name (detailed_signal, self->target_type, - &signal_id, &signal_detail, TRUE) != 0); - g_return_if_fail (closure != NULL); + g_return_val_if_fail (G_IS_SIGNAL_GROUP (self), FALSE); + g_return_val_if_fail (detailed_signal != NULL, FALSE); + g_return_val_if_fail (g_signal_parse_name (detailed_signal, self->target_type, + &signal_id, &signal_detail, TRUE) != 0, FALSE); + g_return_val_if_fail (closure != NULL, FALSE); g_rec_mutex_lock (&self->mutex); @@ -742,7 +728,7 @@ g_signal_group_connect_closure (GSignalGroup *self, { g_critical ("Cannot add signals after setting target"); g_rec_mutex_unlock (&self->mutex); - return; + return FALSE; } handler = g_slice_new0 (SignalHandler); @@ -768,6 +754,30 @@ g_signal_group_connect_closure (GSignalGroup *self, g_signal_group_gc_handlers (self); g_rec_mutex_unlock (&self->mutex); + return TRUE; +} + +/** + * g_signal_group_connect_closure: + * @self: a #GSignalGroup + * @detailed_signal: a string of the form `signal-name` with optional `::signal-detail` + * @closure: (not nullable): the closure to connect. + * @after: whether the handler should be called before or after the + * default handler of the signal. + * + * Connects @closure to the signal @detailed_signal on #GSignalGroup:target. + * + * You cannot connect a signal handler after #GSignalGroup:target has been set. + * + * Since: 2.74 + */ +void +g_signal_group_connect_closure (GSignalGroup *self, + const gchar *detailed_signal, + GClosure *closure, + gboolean after) +{ + g_signal_group_connect_closure_ (self, detailed_signal, closure, after); } static void @@ -798,10 +808,11 @@ g_signal_group_connect_full (GSignalGroup *self, g_object_watch_closure (data, closure); } - g_signal_group_connect_closure (self, - detailed_signal, - closure, - (flags & G_CONNECT_AFTER) != 0); + if (!g_signal_group_connect_closure_ (self, + detailed_signal, + closure, + (flags & G_CONNECT_AFTER) != 0)) + g_closure_unref (closure); } /**