假设我有两个进程,进程A和进程B.如果我在ProcessA中执行int fd=open(somefile),那么我可以通过IPC将文件描述符fd的值传递给ProcessB并让它处理同一个文件吗?

推荐答案

您可以通过unix domain多个套接字将文件描述符传递给另一个进程.

ssize_t
write_fd(int fd, void *ptr, size_t nbytes, int sendfd)
{
    struct msghdr   msg;
    struct iovec    iov[1];

#ifdef  HAVE_MSGHDR_MSG_CONTROL
    union {
      struct cmsghdr    cm;
      char              control[CMSG_SPACE(sizeof(int))];
    } control_un;
    struct cmsghdr  *cmptr;

    msg.msg_control = control_un.control;
    msg.msg_controllen = sizeof(control_un.control);

    cmptr = CMSG_FIRSTHDR(&msg);
    cmptr->cmsg_len = CMSG_LEN(sizeof(int));
    cmptr->cmsg_level = SOL_SOCKET;
    cmptr->cmsg_type = SCM_RIGHTS;
    *((int *) CMSG_DATA(cmptr)) = sendfd;
#else
    msg.msg_accrights = (caddr_t) &sendfd;
    msg.msg_accrightslen = sizeof(int);
#endif

    msg.msg_name = NULL;
    msg.msg_namelen = 0;

    iov[0].iov_base = ptr;
    iov[0].iov_len = nbytes;
    msg.msg_iov = iov;
    msg.msg_iovlen = 1;

    return(sendmsg(fd, &msg, 0));
}
/* end write_fd */

下面是接收文件描述符的代码

ssize_t
read_fd(int fd, void *ptr, size_t nbytes, int *recvfd)
{
    struct msghdr   msg;
    struct iovec    iov[1];
    ssize_t         n;
    int             newfd;

#ifdef  HAVE_MSGHDR_MSG_CONTROL
    union {
      struct cmsghdr    cm;
      char              control[CMSG_SPACE(sizeof(int))];
    } control_un;
    struct cmsghdr  *cmptr;

    msg.msg_control = control_un.control;
    msg.msg_controllen = sizeof(control_un.control);
#else
    msg.msg_accrights = (caddr_t) &newfd;
    msg.msg_accrightslen = sizeof(int);
#endif

    msg.msg_name = NULL;
    msg.msg_namelen = 0;

    iov[0].iov_base = ptr;
    iov[0].iov_len = nbytes;
    msg.msg_iov = iov;
    msg.msg_iovlen = 1;

    if ( (n = recvmsg(fd, &msg, 0)) <= 0)
        return(n);

#ifdef  HAVE_MSGHDR_MSG_CONTROL
    if ( (cmptr = CMSG_FIRSTHDR(&msg)) != NULL &&
        cmptr->cmsg_len == CMSG_LEN(sizeof(int))) {
        if (cmptr->cmsg_level != SOL_SOCKET)
            err_quit("control level != SOL_SOCKET");
        if (cmptr->cmsg_type != SCM_RIGHTS)
            err_quit("control type != SCM_RIGHTS");
        *recvfd = *((int *) CMSG_DATA(cmptr));
    } else
        *recvfd = -1;       /* descriptor was not passed */
#else
/* *INDENT-OFF* */
    if (msg.msg_accrightslen == sizeof(int))
        *recvfd = newfd;
    else
        *recvfd = -1;       /* descriptor was not passed */
/* *INDENT-ON* */
#endif

    return(n);
}
/* end read_fd */

C++相关问答推荐

如何将一个integer与一个数组进行比较?

从STdin读写超过4096个字节

如何将FileFilter添加到FileDialog GTK 4

了解一些CLIPS原语数据类型

球体—立方体重叠:无、部分或全部?

将 typewriter LF打印到Windows终端,而不是隐含的CR+LF

C:scanf(%d&q;,...)输入只有一个减号

为什么在C中进行大量的位移位?

我应该如何解决我自己为iOS编译的xmlsec1库的问题?转换Ctx.first在xmlSecTransformCtxPrepare()之后为空

当execvp在C函数中失败时杀死子进程

如何知道我是否从非阻塞套接字读取所有内容

Clang警告称,`ffi_type`与`sizeof`不兼容

Square不与Raylib一起移动

For循环中的变量行为不符合预期.[C17]

在C中包装两个数组?

将 struct 数组写入二进制文件时发生Valgrind错误

如何读取程序中嵌入的数据S自己的ELF?

如何逐位读取二进制文件?

为什么会导致分段故障?(C语言中的一个程序,统计文件中某个单词的出现次数)

在Ubuntu上使用库部署C程序的最佳实践