openbmc/build/tmp/deploy/sdk/witherspoon-2019-08-08/sysroots/armv6-openbmc-linux-gnueabi/usr/src/debug/libnl/1_3.4.0-r0/libnl-3.4.0/lib/socket.c
int nl_socket_set_fd(struct nl_sock* sk, int protocol, int fd)
{
    int err = 0;
    socklen_t addrlen;
    struct sockaddr_nl local = {0};
    int so_type = -1, so_protocol = -1;

    if (sk->s_fd != -1)
        return -NLE_BAD_SOCK;
    if (fd < 0)
        return -NLE_INVAL;

    addrlen = sizeof(local);
    err = getsockname(fd, (struct sockaddr*)&local, &addrlen);
    if (err < 0)
    {
        NL_DBG(4,
               "nl_socket_set_fd(%p,%d): getsockname() failed with %d (%s)\n",
               sk, fd, errno, nl_strerror_l(errno));
        return -nl_syserr2nlerr(errno);
    }
    if (addrlen != sizeof(local))
        return -NLE_INVAL;
    if (local.nl_family != AF_NETLINK)
    {
        NL_DBG(4,
               "nl_socket_set_fd(%p,%d): getsockname() returned family %d "
               "instead of %d (AF_NETLINK)\n",
               sk, fd, local.nl_family, AF_NETLINK);
        return -NLE_INVAL;
    }

    addrlen = sizeof(so_type);
    err = getsockopt(fd, SOL_SOCKET, SO_TYPE, &so_type, &addrlen);
    if (err < 0)
    {
        NL_DBG(4,
               "nl_socket_set_fd(%p,%d): getsockopt() for SO_TYPE failed with "
               "%d (%s)\n",
               sk, fd, errno, nl_strerror_l(errno));
        return -nl_syserr2nlerr(errno);
    }
    if (addrlen != sizeof(so_type))
        return -NLE_INVAL;
    if (so_type != SOCK_RAW)
    {
        NL_DBG(4,
               "nl_socket_set_fd(%p,%d): getsockopt() returned SO_TYPE %d "
               "instead of %d (SOCK_RAW)\n",
               sk, fd, so_type, SOCK_RAW);
        return -NLE_INVAL;
    }

#if SO_PROTOCOL
    addrlen = sizeof(so_protocol);
    err = getsockopt(fd, SOL_SOCKET, SO_PROTOCOL, &so_protocol, &addrlen);
    if (err < 0)
    {
        if (errno == ENOPROTOOPT)
            goto no_so_protocol;
        NL_DBG(4,
               "nl_socket_set_fd(%p,%d): getsockopt() for SO_PROTOCOL failed "
               "with %d (%s)\n",
               sk, fd, errno, nl_strerror_l(errno));
        return -nl_syserr2nlerr(errno);
    }
    if (addrlen != sizeof(so_protocol))
        return -NLE_INVAL;
    if (protocol >= 0 && protocol != so_protocol)
    {
        NL_DBG(4,
               "nl_socket_set_fd(%p,%d): getsockopt() for SO_PROTOCOL returned "
               "%d instead of %d\n",
               sk, fd, so_protocol, protocol);
        return -NLE_INVAL;
    }

    if (0)
#endif
    {
    no_so_protocol:
        if (protocol < 0)
        {
            NL_DBG(4,
                   "nl_socket_set_fd(%p,%d): unknown protocol and unable to "
                   "detect it via SO_PROTOCOL socket option\n",
                   sk, fd);
            return -NLE_INVAL;
        }
        so_protocol = protocol;
    }

    nl_socket_set_local_port(sk, local.nl_pid);
    sk->s_local = local;
    sk->s_fd = fd;
    sk->s_proto = so_protocol;

    return 0;
}
/**
 * Set the socket file descriptor externally which initializes the
 * socket similar to nl_connect().
 *
 * @arg sk         Netlink socket (required)
 * @arg protocol   The socket protocol (optional). Linux 2.6.32 supports
 *                 the socket option SO_PROTOCOL. In this case, you can set
 *                 protocol to a negative value and let it autodetect.
 *                 If you set it to a non-negative value, the detected protocol
 *                 must match the one provided.
 *                 To support older kernels, you must specify the protocol.
 * @arg fd         Socket file descriptor to use (required)
 *
 * Set the socket file descriptor. @fd must be valid and bind'ed.
 *
 * This is an alternative to nl_connect(). nl_connect() creates, binds and
 * sets the socket. With this function you can set the socket to an externally
 * created file descriptor.
 *
 * @see nl_connect()
 *
 * @return 0 on success or a negative error code. On error, @fd is not closed
 * but possibly unusable.
 *
 * @retval -NLE_BAD_SOCK Netlink socket is already connected
 * @retval -NLE_INVAL Socket is of unexpected type
 */
Set the socket file descriptor externally which initializes the
socket similar to nl_connect().

@arg sk         Netlink socket (required)
@arg protocol   The socket protocol (optional). Linux 2.6.32 supports
the socket option SO_PROTOCOL. In this case, you can set
protocol to a negative value and let it autodetect.
If you set it to a non-negative value, the detected protocol
must match the one provided.
To support older kernels, you must specify the protocol.
@arg fd         Socket file descriptor to use (required)

Set the socket file descriptor. @fd must be valid and bind'ed.

This is an alternative to nl_connect(). nl_connect() creates, binds and
sets the socket. With this function you can set the socket to an externally
created file descriptor.



@return 0 on success or a negative error code. On error, @fd is not closed
but possibly unusable.

@retval -NLE_BAD_SOCK Netlink socket is already connected
@retval -NLE_INVAL Socket is of unexpected type
Set the socket file descriptor externally which initializes the socket similar to nl_connect () . @arg sk Netlink socket ( required ) @arg protocol The socket protocol ( optional ) . Linux 2 . 6 . 32 supports the socket option SO_PROTOCOL . In this case you can set protocol to a negative value and let it autodetect . If you set it to a non - negative value the detected protocol must match the one provided . To support older kernels you must specify the protocol . @arg fd Socket file descriptor to use ( required ) Set the socket file descriptor . @fd must be valid and bind ' ed . This is an alternative to nl_connect () . nl_connect () creates binds and sets the socket . With this function you can set the socket to an externally created file descriptor . @return 0 on success or a negative error code . On error @fd is not closed but possibly unusable . @retval - NLE_BAD_SOCK Netlink socket is already connected @retval - NLE_INVAL Socket is of unexpected type
int nl_socket_set_fd(struct nl_sock* sk, int protocol, int fd)
{
    int err = 0;
    socklen_t addrlen;
    struct sockaddr_nl local = {0};
    int so_type = -1, so_protocol = -1;
    if (sk->s_fd != -1)
        return -NLE_BAD_SOCK;
    if (fd < 0)
        return -NLE_INVAL;
    addrlen = sizeof(local);
    err = getsockname(fd, (struct sockaddr*)&local, &addrlen);
    if (err < 0)
    {
        NL_DBG(4,
               "nl_socket_set_fd(%p,%d): getsockname() failed with %d (%s)\n",
               sk, fd, errno, nl_strerror_l(errno));
        return -nl_syserr2nlerr(errno);
    }
    if (addrlen != sizeof(local))
        return -NLE_INVAL;
    if (local.nl_family != AF_NETLINK)
    {
        NL_DBG(4,
               "nl_socket_set_fd(%p,%d): getsockname() returned family %d "
               "instead of %d (AF_NETLINK)\n",
               sk, fd, local.nl_family, AF_NETLINK);
        return -NLE_INVAL;
    }
    addrlen = sizeof(so_type);
    err = getsockopt(fd, SOL_SOCKET, SO_TYPE, &so_type, &addrlen);
    if (err < 0)
    {
        NL_DBG(4,
               "nl_socket_set_fd(%p,%d): getsockopt() for SO_TYPE failed with "
               "%d (%s)\n",
               sk, fd, errno, nl_strerror_l(errno));
        return -nl_syserr2nlerr(errno);
    }
    if (addrlen != sizeof(so_type))
        return -NLE_INVAL;
    if (so_type != SOCK_RAW)
    {
        NL_DBG(4,
               "nl_socket_set_fd(%p,%d): getsockopt() returned SO_TYPE %d "
               "instead of %d (SOCK_RAW)\n",
               sk, fd, so_type, SOCK_RAW);
        return -NLE_INVAL;
    }
#if SO_PROTOCOL
    addrlen = sizeof(so_protocol);
    err = getsockopt(fd, SOL_SOCKET, SO_PROTOCOL, &so_protocol, &addrlen);
    if (err < 0)
    {
        if (errno == ENOPROTOOPT)
            goto no_so_protocol;
        NL_DBG(4,
               "nl_socket_set_fd(%p,%d): getsockopt() for SO_PROTOCOL failed "
               "with %d (%s)\n",
               sk, fd, errno, nl_strerror_l(errno));
        return -nl_syserr2nlerr(errno);
    }
    if (addrlen != sizeof(so_protocol))
        return -NLE_INVAL;
    if (protocol >= 0 && protocol != so_protocol)
    {
        NL_DBG(4,
               "nl_socket_set_fd(%p,%d): getsockopt() for SO_PROTOCOL returned "
               "%d instead of %d\n",
               sk, fd, so_protocol, protocol);
        return -NLE_INVAL;
    }
    if (0)
#endif
    {
    no_so_protocol:
        if (protocol < 0)
        {
            NL_DBG(4,
                   "nl_socket_set_fd(%p,%d): unknown protocol and unable to "
                   "detect it via SO_PROTOCOL socket option\n",
                   sk, fd);
            return -NLE_INVAL;
        }
        so_protocol = protocol;
    }
    nl_socket_set_local_port(sk, local.nl_pid);
    sk->s_local = local;
    sk->s_fd = fd;
    sk->s_proto = so_protocol;
    return 0;
}
int nl_socket_set_fd ( struct nl_sock * sk , int protocol , int fd ) { int err = 0 ; socklen_t addrlen ; struct sockaddr_nl local = { 0 } ; int so_type = -1 , so_protocol = -1 ; if ( sk -> s_fd != -1 ) return - NLE_BAD_SOCK ; if ( fd < 0 ) return - NLE_INVAL ; addrlen = sizeof ( local ) ; err = getsockname ( fd , ( struct sockaddr * ) & local , & addrlen ) ; if ( err < 0 ) { NL_DBG ( 4 , " \n " , sk , fd , errno , nl_strerror_l ( errno ) ) ; return - nl_syserr2nlerr ( errno ) ; } if ( addrlen != sizeof ( local ) ) return - NLE_INVAL ; if ( local . nl_family != AF_NETLINK ) { NL_DBG ( 4 , " " " \n " , sk , fd , local . nl_family , AF_NETLINK ) ; return - NLE_INVAL ; } addrlen = sizeof ( so_type ) ; err = getsockopt ( fd , SOL_SOCKET , SO_TYPE , & so_type , & addrlen ) ; if ( err < 0 ) { NL_DBG ( 4 , " " " \n " , sk , fd , errno , nl_strerror_l ( errno ) ) ; return - nl_syserr2nlerr ( errno ) ; } if ( addrlen != sizeof ( so_type ) ) return - NLE_INVAL ; if ( so_type != SOCK_RAW ) { NL_DBG ( 4 , " " " \n " , sk , fd , so_type , SOCK_RAW ) ; return - NLE_INVAL ; } #if SO_PROTOCOL addrlen = sizeof ( so_protocol ) ; err = getsockopt ( fd , SOL_SOCKET , SO_PROTOCOL , & so_protocol , & addrlen ) ; if ( err < 0 ) { if ( errno == ENOPROTOOPT ) goto no_so_protocol ; NL_DBG ( 4 , " " " \n " , sk , fd , errno , nl_strerror_l ( errno ) ) ; return - nl_syserr2nlerr ( errno ) ; } if ( addrlen != sizeof ( so_protocol ) ) return - NLE_INVAL ; if ( protocol >= 0 && protocol != so_protocol ) { NL_DBG ( 4 , " " " \n " , sk , fd , so_protocol , protocol ) ; return - NLE_INVAL ; } if ( 0 ) #endif { no_so_protocol : if ( protocol < 0 ) { NL_DBG ( 4 , " " " \n " , sk , fd ) ; return - NLE_INVAL ; } so_protocol = protocol ; } nl_socket_set_local_port ( sk , local . nl_pid ) ; sk -> s_local = local ; sk -> s_fd = fd ; sk -> s_proto = so_protocol ; return 0 ; }
Set the socket file descriptor externally which initializes the
 socket similar to nl_connect().
Set the socket file descriptor externally which initializes the socket similar to nl_connect () .