134 lines
3.9 KiB
Plaintext
134 lines
3.9 KiB
Plaintext
$OpenBSD: patch-gio_gunixconnection_c,v 1.2 2011/05/23 16:36:13 ajacoutot Exp $
|
|
|
|
XXX
|
|
Workaround the fact that we cannot pass SCM_CREDS over unix sockets:
|
|
implement the "intended" SCM_CREDS stack as if we had support for that
|
|
in the kernel (by-pass it almost completely).
|
|
send/recv a single null byte without creds, but on recv, just do a
|
|
getsockopt(SO_PEERCRED) and return that as if it coming from the cmsg.
|
|
This works as long as creds are not retreived from an fd which has
|
|
already been handed over to a different process via SCM_RIGHTS. It will
|
|
probably not be enough in the future but we'll see then.
|
|
|
|
--- gio/gunixconnection.c.orig Sat May 21 05:29:24 2011
|
|
+++ gio/gunixconnection.c Mon May 23 18:20:08 2011
|
|
@@ -42,7 +42,7 @@
|
|
#include <gio/gsocket.h>
|
|
#include <unistd.h>
|
|
|
|
-#ifdef __linux__
|
|
+#if defined(__linux__) || defined(__OpenBSD__)
|
|
/* for getsockopt() and setsockopt() */
|
|
#include <sys/types.h> /* See NOTES */
|
|
#include <sys/socket.h>
|
|
@@ -328,8 +328,10 @@ g_unix_connection_send_credentials (GUnixConnection
|
|
GCancellable *cancellable,
|
|
GError **error)
|
|
{
|
|
+#ifndef __OpenBSD__
|
|
GCredentials *credentials;
|
|
GSocketControlMessage *scm;
|
|
+#endif
|
|
GSocket *socket;
|
|
gboolean ret;
|
|
GOutputVector vector;
|
|
@@ -340,18 +342,28 @@ g_unix_connection_send_credentials (GUnixConnection
|
|
|
|
ret = FALSE;
|
|
|
|
+#ifndef __OpenBSD__
|
|
credentials = g_credentials_new ();
|
|
+ scm = g_unix_credentials_message_new_with_credentials (credentials);
|
|
+#endif
|
|
|
|
vector.buffer = &nul_byte;
|
|
vector.size = 1;
|
|
+#ifndef __OpenBSD__
|
|
scm = g_unix_credentials_message_new_with_credentials (credentials);
|
|
+#endif
|
|
g_object_get (connection, "socket", &socket, NULL);
|
|
if (g_socket_send_message (socket,
|
|
NULL, /* address */
|
|
&vector,
|
|
1,
|
|
+#ifndef __OpenBSD__
|
|
&scm,
|
|
1,
|
|
+#else
|
|
+ NULL,
|
|
+ 0,
|
|
+#endif
|
|
G_SOCKET_MSG_NONE,
|
|
cancellable,
|
|
error) != 1)
|
|
@@ -364,8 +376,10 @@ g_unix_connection_send_credentials (GUnixConnection
|
|
|
|
out:
|
|
g_object_unref (socket);
|
|
+#ifndef __OpenBSD__
|
|
g_object_unref (scm);
|
|
g_object_unref (credentials);
|
|
+#endif
|
|
return ret;
|
|
}
|
|
|
|
@@ -406,6 +420,10 @@ g_unix_connection_receive_credentials (GUnixConnection
|
|
#ifdef __linux__
|
|
gboolean turn_off_so_passcreds;
|
|
#endif
|
|
+#ifdef __OpenBSD__
|
|
+ struct sockpeercred cred;
|
|
+ socklen_t len;
|
|
+#endif
|
|
|
|
g_return_val_if_fail (G_IS_UNIX_CONNECTION (connection), NULL);
|
|
g_return_val_if_fail (error == NULL || *error == NULL, NULL);
|
|
@@ -497,16 +515,25 @@ g_unix_connection_receive_credentials (GUnixConnection
|
|
goto out;
|
|
}
|
|
|
|
+#ifndef __OpenBSD__
|
|
if (nscm != 1)
|
|
+#else
|
|
+ if (nscm != 0)
|
|
+#endif
|
|
{
|
|
g_set_error (error,
|
|
G_IO_ERROR,
|
|
G_IO_ERROR_FAILED,
|
|
+#ifndef __OpenBSD__
|
|
_("Expecting 1 control message, got %d"),
|
|
+#else
|
|
+ _("Expecting 0 control message, got %d"),
|
|
+#endif
|
|
nscm);
|
|
goto out;
|
|
}
|
|
|
|
+#ifndef __OpenBSD__
|
|
if (!G_IS_UNIX_CREDENTIALS_MESSAGE (scms[0]))
|
|
{
|
|
g_set_error_literal (error,
|
|
@@ -518,6 +545,21 @@ g_unix_connection_receive_credentials (GUnixConnection
|
|
|
|
ret = g_unix_credentials_message_get_credentials (G_UNIX_CREDENTIALS_MESSAGE (scms[0]));
|
|
g_object_ref (ret);
|
|
+#else
|
|
+ len = sizeof(cred);
|
|
+ if (getsockopt(g_socket_get_fd(socket),
|
|
+ SOL_SOCKET, SO_PEERCRED, &cred, &len) == -1) {
|
|
+ g_set_error (error,
|
|
+ G_IO_ERROR,
|
|
+ g_io_error_from_errno (errno),
|
|
+ _("Error : getsockopt(SO_PEERCRED): %s"),
|
|
+ strerror (errno));
|
|
+ goto out;
|
|
+ }
|
|
+
|
|
+ ret = g_credentials_new();
|
|
+ g_credentials_set_native(ret, G_CREDENTIALS_TYPE_OPENBSD_SOCKPEERCRED, &cred);
|
|
+#endif
|
|
|
|
out:
|
|
|