[Top][All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: socket_send & socket_recv fail when sending non-socket ports

From: Manuel Menal
Subject: Re: socket_send & socket_recv fail when sending non-socket ports
Date: Sun, 19 Sep 2010 13:54:23 +0200
User-agent: Mozilla/5.0 (X11; U; Linux i686; en-US; rv: Gecko/20100918 Icedove/3.0.8

On 27/07/2010 17:39, Emilio Pozuelo Monfort wrote:
> Hi,


> While adding support for SCM_RIGHTS to glibc, I've created a testcase that 
> sends
> and receives some ports on the result of a socketpair() call. The ports sent
> were initially the two ports result of another socketpair() call, and it was
> working fine, but then I tried with the result of a couple of open() calls, 
> and
> socket_recv() was returning EMIGSERVERDIED.
> It's returning because of this:
>         if (OutP->Head.msgh_id != 26115) {
>                 if (OutP->Head.msgh_id == MACH_NOTIFY_SEND_ONCE)
>                 return MIG_SERVER_DIED;
> But I'm not sure how to interpret it, and why a non-socket port in the ports
> argument would cause this.
> Any ideas?

I think you've encountered a little bug in pflocal.

Here's the story: the file descriptor you're sending is, in Mach terms,
a send right. It gets stored by pflocal (libpipe actually) when you send
it through socket_send() (see <pflocal/socket.c:S_socket_send>). When
you call socket_recv(), pflocal retrieves your send right and tries to
send it to the caller. But it sends it with the MACH_MSG_TYPE_MAKE_SEND
flag (see <pflocal/socket.c:S_socket_recv>). This can't work, since
MAKE_SEND only works with receive rights. So mach_msg() fails and you
get the error code you've mentioned.

Here is a very simple fix for this bug:

diff -Nurp hurd-20100829/pflocal/socket.c
--- hurd-20100829/pflocal/socket.c      2010-09-19 12:49:09.000000000 +0200
+++ hurd-20100829.patched//pflocal/socket.c     2010-09-19
12:47:23.000000000 +0200
@@ -397,7 +397,7 @@ S_socket_recv (struct sock_user *user,
     /* Setup mach ports for return.  */
       *addr_type = MACH_MSG_TYPE_MAKE_SEND;
-      *ports_type = MACH_MSG_TYPE_MAKE_SEND;
+      *ports_type = MACH_MSG_TYPE_COPY_SEND;
       if (source_addr)
          *addr = ports_get_right (source_addr);

I've tried several test cases (including yours) using your libc patch
for sendmsg()/recvmsg() and this fix for pflocal. They all work fine.

As a sidenote, this also makes us able to use sshd with
UsePrivilegeSeparation set to yes (which used to fail because it sends
the tty fd through sendmsg() with SCM_RIGHTS, which fails silently
without your patch).


Manuel Menal

reply via email to

[Prev in Thread] Current Thread [Next in Thread]