freebsd-ports/net-im/telepathy-gabble/files/patch-lib_gibber_gibber-unix-transport.c
Koop Mast 3680f27ebf Presenting GNOME 2.32.1 for FreeBSD. The offical release notes for this
release can be found at http://library.gnome.org/misc/release-notes/2.32/

This will be the last release of the GNOME 2.x series, mainly a bugfix and
bridge release to the first release of the GNOME 3.x series.

This release features commits by avl, marcus, mezz and myself.

The FreeBSD GNOME Team would like to thank the following contributors and
testers for there help with this release:

Zane C.B. <vvelox@vvelox.net>
romain@
Olaf Seibert <O.Seibert@cs.ru.nl>
DomiX
Bapt <baptiste.daroussin@gmail.com>
jsa@
miwi@
Sergio de Almeida Lenzi <lenzi.sergio@gmail.com>
Maxim Samsonov <xors@mne.ru>
Kris Moore

And pav@ for 2 exp-runs

PR:		ports/152255
		ports/143260
		ports/141033
		ports/149629
		ports/150350
		ports/151523
With hat:	gnome@
2010-11-20 15:37:08 +00:00

181 lines
4.6 KiB
C

--- lib/gibber/gibber-unix-transport.c.orig 2010-06-09 16:09:58.000000000 +0000
+++ lib/gibber/gibber-unix-transport.c 2010-09-18 21:24:44.000000000 +0000
@@ -375,6 +375,167 @@ gibber_unix_transport_recv_credentials (
return TRUE;
}
+/* End Linux part */
+#elif defined(__FreeBSD__)
+
+gboolean
+gibber_unix_transport_send_credentials (GibberUnixTransport *transport,
+ const guint8 *data,
+ gsize size)
+{
+ int fd, ret;
+ struct msghdr msg;
+ struct iovec iov;
+ union {
+ struct cmsghdr hdr;
+ char cred[CMSG_SPACE (sizeof (struct cmsgcred))];
+ } cmsg;
+
+ DEBUG ("send credentials");
+ fd = GIBBER_FD_TRANSPORT (transport)->fd;
+
+ /* Set the message payload */
+ memset (&iov, 0, sizeof (iov));
+ iov.iov_base = (void *) data;
+ iov.iov_len = size;
+
+ memset (&msg, 0, sizeof (msg));
+ msg.msg_iov = &iov;
+ msg.msg_iovlen = 1;
+ msg.msg_control = (caddr_t) &cmsg;
+ msg.msg_controllen = CMSG_SPACE (sizeof (struct cmsgcred));
+ memset (&cmsg, 0, sizeof (cmsg));
+ cmsg.hdr.cmsg_len = CMSG_LEN (sizeof (struct cmsgcred));
+ cmsg.hdr.cmsg_level = SOL_SOCKET;
+ cmsg.hdr.cmsg_type = SCM_CREDS;
+
+ ret = sendmsg (fd, &msg, 0);
+ if (ret == -1)
+ {
+ DEBUG ("sendmsg failed: %s", g_strerror (errno));
+ return FALSE;
+ }
+
+ return TRUE;
+}
+
+gboolean
+gibber_unix_transport_recv_credentials (GibberUnixTransport *self,
+ GibberUnixTransportRecvCredentialsCb callback,
+ gpointer user_data)
+{
+ GibberUnixTransportPrivate *priv = GIBBER_UNIX_TRANSPORT_GET_PRIVATE (self);
+
+ if (priv->recv_creds_cb != NULL)
+ {
+ DEBUG ("already waiting for credentials");
+ return FALSE;
+ }
+
+ priv->recv_creds_cb = callback;
+ priv->recv_creds_data = user_data;
+ return TRUE;
+}
+
+gboolean
+gibber_unix_transport_supports_credentials (void)
+{
+ return TRUE;
+}
+
+#define BUFSIZE 1024
+
+static GibberFdIOResult
+gibber_unix_transport_read (GibberFdTransport *transport,
+ GIOChannel *channel,
+ GError **error)
+{
+ GibberUnixTransport *self = GIBBER_UNIX_TRANSPORT (transport);
+ GibberUnixTransportPrivate *priv = GIBBER_UNIX_TRANSPORT_GET_PRIVATE (self);
+ int fd;
+ guint8 buffer[BUFSIZE];
+ ssize_t bytes_read;
+ GibberBuffer buf;
+ struct iovec iov;
+ struct msghdr msg;
+ struct cmsgcred *cred;
+ union {
+ struct cmsghdr hdr;
+ char cred[CMSG_SPACE (sizeof *cred)];
+ } cmsg;
+ int opt;
+
+ if (priv->recv_creds_cb == NULL)
+ return gibber_fd_transport_read (transport, channel, error);
+
+ /* We are waiting for credentials */
+ fd = transport->fd;
+
+ memset (buffer, 0, sizeof (buffer));
+ memset (&iov, 0, sizeof (iov));
+ iov.iov_base = buffer;
+ iov.iov_len = sizeof (buffer);
+
+ memset (&msg, 0, sizeof (msg));
+ msg.msg_iov = &iov;
+ msg.msg_iovlen = 1;
+ msg.msg_control = (caddr_t) &cmsg;
+ msg.msg_controllen = CMSG_SPACE (sizeof *cred);
+
+ bytes_read = recvmsg (fd, &msg, 0);
+
+ if (bytes_read == -1)
+ {
+ GError *err = NULL;
+
+ g_set_error_literal (&err, G_IO_CHANNEL_ERROR,
+ g_io_channel_error_from_errno (errno), "recvmsg failed");
+
+ priv->recv_creds_cb (self, NULL, NULL, err, priv->recv_creds_data);
+ g_propagate_error (error, err);
+
+ priv->recv_creds_cb = NULL;
+ priv->recv_creds_data = NULL;
+ return GIBBER_FD_IO_RESULT_ERROR;
+ }
+
+ buf.data = buffer;
+ buf.length = bytes_read;
+
+ /* extract the credentials */
+ if (cmsg.hdr.cmsg_len < CMSG_LEN (sizeof *cred) ||
+ cmsg.hdr.cmsg_type != SCM_CREDS)
+ {
+ GError *err = NULL;
+
+ DEBUG ("Message doesn't contain credentials");
+
+ g_set_error_literal (&err, GIBBER_UNIX_TRANSPORT_ERROR,
+ GIBBER_UNIX_TRANSPORT_ERROR_NO_CREDENTIALS,
+ "no credentials received");
+
+ priv->recv_creds_cb (self, &buf, NULL, err, priv->recv_creds_data);
+ g_error_free (err);
+ }
+ else
+ {
+ GibberCredentials credentials;
+
+ cred = (struct cmsgcred *) CMSG_DATA (&cmsg.hdr);
+ credentials.pid = cred->cmcred_pid;
+ credentials.uid = cred->cmcred_uid;
+ credentials.gid = cred->cmcred_gid;
+
+ priv->recv_creds_cb (self, &buf, &credentials, NULL,
+ priv->recv_creds_data);
+ }
+
+ priv->recv_creds_cb = NULL;
+ priv->recv_creds_data = NULL;
+ return GIBBER_FD_IO_RESULT_SUCCESS;
+}
+
+/* End FreeBSD part */
#else /* OSs where we have no implementation */
gboolean
@@ -393,9 +554,7 @@ gibber_unix_transport_recv_credentials (
}
gboolean
-gibber_unix_transport_send_credentials (GibberUnixTransport *transport,
- const guint8 *data,
- gsize size)
+gibber_unix_transport_send_credentials (void)
{
DEBUG ("stub implementation, failing");
return FALSE;