Exemplo n.º 1
0
static int unix_server_start(server_generic_t *server)
{
        int ret;
        struct sockaddr_un *sa = (struct sockaddr_un *) server->sa;

        server->sock = socket(AF_UNIX, SOCK_STREAM, 0);
        if ( server->sock < 0 )
                return prelude_error_verbose(PRELUDE_ERROR_GENERIC, "error creating UNIX socket: %s", strerror(errno));

        ret = is_unix_socket_already_used(server->sock, sa, server->slen);
        if ( ret < 0 ) {
                close(server->sock);
                return ret;
        }

        ret = generic_server(server->sock, server->sa, server->slen);
        if ( ret < 0 ) {
                close(server->sock);
                return ret;
        }

        /*
         * Everyone should be able to access the filesystem object
         * representing our socket.
         */
        ret = chmod(sa->sun_path, S_IRWXU|S_IRWXG|S_IRWXO);
        if ( ret < 0 )
                return prelude_error_verbose(PRELUDE_ERROR_GENERIC, "could not set permission on UNIX socket: %s", strerror(errno));

        return 0;
}
Exemplo n.º 2
0
static int inet_server_start(server_generic_t *server, struct sockaddr *addr, socklen_t addrlen)
{
        int ret, on = 1;

        server->sock = socket(server->sa->sa_family, SOCK_STREAM, IPPROTO_TCP);
        if ( server->sock < 0 )
                return prelude_error_verbose(PRELUDE_ERROR_GENERIC, "error creating socket: %s", strerror(errno));


#ifdef IPV6_V6ONLY
        /*
         * There is a problem on Linux system where getaddrinfo() return address in
         * the wrong sort order (IPv4 first, IPv6 next).
         *
         * As a result we first bind IPv4 addresses, but then we get an error for
         * dual-stacked addresses, when the IPv6 addresses come second. When an
         * address is dual-stacked, we thus end-up listening only to the IPv4
         * instance.
         *
         * The error happen on dual-stack Linux system, because mapping the IPv6
         * address will actually attempt to bind both the IPv4 and IPv6 address.
         *
         * In order to prevent this problem, we set the IPV6_V6ONLY option so that
         * only the IPv6 address is bound.
         */
        if ( server->sa->sa_family == AF_INET6 ) {
                ret = setsockopt(server->sock, IPPROTO_IPV6, IPV6_V6ONLY, (void *) &on, sizeof(int));
                if ( ret < 0 ) {
                        ret = prelude_error_verbose(PRELUDE_ERROR_GENERIC, "could not set IPV6_V6ONLY: %s.\n", strerror(errno));
                        goto err;
                }
        }
#endif

        ret = setsockopt(server->sock, SOL_SOCKET, SO_REUSEADDR, &on, sizeof(int));
        if ( ret < 0 ) {
                ret = prelude_error_verbose(PRELUDE_ERROR_GENERIC, "error setting SO_REUSEADDR: %s", strerror(errno));
                goto err;
        }

        ret = generic_server(server->sock, addr, addrlen);
        if ( ret < 0 )
                goto err;

        return 0;

 err:
        close(server->sock);
        return ret;
}
Exemplo n.º 3
0
static int inet_server_start(server_generic_t *server, struct sockaddr *addr, socklen_t addrlen)
{
        int ret, on = 1;

        server->sock = socket(server->sa->sa_family, SOCK_STREAM, IPPROTO_TCP);
        if ( server->sock < 0 )
                return prelude_error_verbose(PRELUDE_ERROR_GENERIC, "error creating socket: %s", strerror(errno));

        ret = setsockopt(server->sock, SOL_SOCKET, SO_REUSEADDR, &on, sizeof(int));
        if ( ret < 0 ) {
                ret = prelude_error_verbose(PRELUDE_ERROR_GENERIC, "error setting SO_REUSEADDR: %s", strerror(errno));
                goto err;
        }

        ret = generic_server(server->sock, addr, addrlen);
        if ( ret < 0 )
                goto err;

        return 0;

 err:
        close(server->sock);
        return ret;
}