/*
 * Copyright 2016-2022 The OpenSSL Project Authors. All Rights Reserved.
 *
 * Licensed under the Apache License 2.0 (the "License").  You may not use
 * this file except in compliance with the License.  You can obtain a copy
 * in the file LICENSE in the source distribution or at
 * https://www.openssl.org/source/license.html
 */

#ifndef _GNU_SOURCE
# define _GNU_SOURCE
#endif

/*
 * VC configurations may define UNICODE, to indicate to the C RTL that
 * WCHAR functions are preferred.
 * This affects functions like gai_strerror(), which is implemented as
 * an alias macro for gai_strerrorA() (which returns a const char *) or
 * gai_strerrorW() (which returns a const WCHAR *).  This source file
 * assumes POSIX declarations, so prefer the non-UNICODE definitions.
 */
#undef UNICODE

#include <assert.h>
#include <string.h>

#include "bio_local.h"
#include <openssl/crypto.h>

#ifndef OPENSSL_NO_SOCK
#include <openssl/err.h>
#include <openssl/buffer.h>
#include "internal/thread_once.h"

CRYPTO_RWLOCK *bio_lookup_lock;
static CRYPTO_ONCE bio_lookup_init = CRYPTO_ONCE_STATIC_INIT;

/*
 * Throughout this file and bio_local.h, the existence of the macro
 * AI_PASSIVE is used to detect the availability of struct addrinfo,
 * getnameinfo() and getaddrinfo().  If that macro doesn't exist,
 * we use our own implementation instead, using gethostbyname,
 * getservbyname and a few other.
 */

/**********************************************************************
 *
 * Address structure
 *
 */

BIO_ADDR *BIO_ADDR_new(void)
{
    BIO_ADDR *ret = OPENSSL_zalloc(sizeof(*ret));

    if (ret == NULL) {
        ERR_raise(ERR_LIB_BIO, ERR_R_MALLOC_FAILURE);
        return NULL;
    }

    ret->sa.sa_family = AF_UNSPEC;
    return ret;
}

void BIO_ADDR_free(BIO_ADDR *ap)
{
    OPENSSL_free(ap);
}

BIO_ADDR *BIO_ADDR_dup(const BIO_ADDR *ap)
{
    BIO_ADDR *ret = NULL;

    if (ap != NULL) {
        ret = BIO_ADDR_new();
        if (ret != NULL)
            memcpy(ret, ap, sizeof(BIO_ADDR));
    }
    return ret;
}

void BIO_ADDR_clear(BIO_ADDR *ap)
{
    memset(ap, 0, sizeof(*ap));
    ap->sa.sa_family = AF_UNSPEC;
}

/*
 * BIO_ADDR_make - non-public routine to fill a BIO_ADDR with the contents
 * of a struct sockaddr.
 */
int BIO_ADDR_make(BIO_ADDR *ap, const struct sockaddr *sa)
{
    if (sa->sa_family == AF_INET) {
        memcpy(&(ap->s_in), sa, sizeof(struct sockaddr_in));
        return 1;
    }
#if OPENSSL_USE_IPV6
    if (sa->sa_family == AF_INET6) {
        memcpy(&(ap->s_in6), sa, sizeof(struct sockaddr_in6));
        return 1;
    }
#endif
#ifdef AF_UNIX
    if (sa->sa_family == AF_UNIX) {
        memcpy(&(ap->s_un), sa, sizeof(struct sockaddr_un));
        return 1;
    }
#endif

    return 0;
}

int BIO_ADDR_rawmake(BIO_ADDR *ap, int family,
                     const void *where, size_t wherelen,
                     unsigned short port)
{
#ifdef AF_UNIX
    if (family == AF_UNIX) {
        if (wherelen + 1 > sizeof(ap->s_un.sun_path))
            return 0;
        memset(&ap->s_un, 0, sizeof(ap->s_un));
        ap->s_un.sun_family = family;
        strncpy(ap->s_un.sun_path, where, sizeof(ap->s_un.sun_path) - 1);
        return 1;
    }
#endif
    if (family == AF_INET) {
        if (wherelen != sizeof(struct in_addr))
            return 0;
        memset(&ap->s_in, 0, sizeof(ap->s_in));
        ap->s_in.sin_family = family;
        ap->s_in.sin_port = port;
        ap->s_in.sin_addr = *(struct in_addr *)where;
        return 1;
    }
#if OPENSSL_USE_IPV6
    if (family == AF_INET6) {
        if (wherelen != sizeof(struct in6_addr))
            return 0;
        memset(&ap->s_in6, 0, sizeof(ap->s_in6));
        ap->s_in6.sin6_family = family;
        ap->s_in6.sin6_port = port;
        ap->s_in6.sin6_addr = *(struct in6_addr *)where;
        return 1;
    }
#endif

    return 0;
}

int BIO_ADDR_family(const BIO_ADDR *ap)
{
    return ap->sa.sa_family;
}

int BIO_ADDR_rawaddress(const BIO_ADDR *ap, void *p, size_t *l)
{
    size_t len = 0;
    const void *addrptr = NULL;

    if (ap->sa.sa_family == AF_INET) {
        len = sizeof(ap->s_in.sin_addr);
        addrptr = &ap->s_in.sin_addr;
    }
#if OPENSSL_USE_IPV6
    else if (ap->sa.sa_family == AF_INET6) {
        len = sizeof(ap->s_in6.sin6_addr);
        addrptr = &ap->s_in6.sin6_addr;
    }
#endif
#ifdef AF_UNIX
    else if (ap->sa.sa_family == AF_UNIX) {
        len = strlen(ap->s_un.sun_path);
        addrptr = &ap->s_un.sun_path;
    }
#endif

    if (addrptr == NULL)
        return 0;

    if (p != NULL) {
        memcpy(p, addrptr, len);
    }
    if (l != NULL)
        *l = len;

    return 1;
}

unsigned short BIO_ADDR_rawport(const BIO_ADDR *ap)
{
    if (ap->sa.sa_family == AF_INET)
        return ap->s_in.sin_port;
#if OPENSSL_USE_IPV6
    if (ap->sa.sa_family == AF_INET6)
        return ap->s_in6.sin6_port;
#endif
    return 0;
}

/*-
 * addr_strings - helper function to get host and service names
 * @ap: the BIO_ADDR that has the input info
 * @numeric: 0 if actual names should be returned, 1 if the numeric
 * representation should be returned.
 * @hostname: a pointer to a pointer to a memory area to store the
 * host name or numeric representation.  Unused if NULL.
 * @service: a pointer to a pointer to a memory area to store the
 * service name or numeric representation.  Unused if NULL.
 *
 * The return value is 0 on failure, with the error code in the error
 * stack, and 1 on success.
 */
static int addr_strings(const BIO_ADDR *ap, int numeric,
                        char **hostname, char **service)
{
    if (BIO_sock_init() != 1)
        return 0;

    if (1) {
#ifdef AI_PASSIVE
        int ret = 0;
        char host[NI_MAXHOST] = "", serv[NI_MAXSERV] = "";
        int flags = 0;

        if (numeric)
            flags |= NI_NUMERICHOST | NI_NUMERICSERV;

        if ((ret = getnameinfo(BIO_ADDR_sockaddr(ap),
                               BIO_ADDR_sockaddr_size(ap),
                               host, sizeof(host), serv, sizeof(serv),
                               flags)) != 0) {
# ifdef EAI_SYSTEM
            if (ret == EAI_SYSTEM) {
                ERR_raise_data(ERR_LIB_SYS, get_last_socket_error(),
                               "calling getnameinfo()");
            } else
# endif
            {
                ERR_raise_data(ERR_LIB_BIO, ERR_R_SYS_LIB, gai_strerror(ret));
            }
            return 0;
        }

        /* VMS getnameinfo() has a bug, it doesn't fill in serv, which
         * leaves it with whatever garbage that happens to be there.
         * However, we initialise serv with the empty string (serv[0]
         * is therefore NUL), so it gets real easy to detect when things
         * didn't go the way one might expect.
         */
        if (serv[0] == '\0') {
            BIO_snprintf(serv, sizeof(serv), "%d",
                         ntohs(BIO_ADDR_rawport(ap)));
        }

        if (hostname != NULL)
            *hostname = OPENSSL_strdup(host);
        if (service != NULL)
            *service = OPENSSL_strdup(serv);
    } else {
#endif
        if (hostname != NULL)
            *hostname = OPENSSL_strdup(inet_ntoa(ap->s_in.sin_addr));
        if (service != NULL) {
            char serv[6];        /* port is 16 bits => max 5 decimal digits */
            BIO_snprintf(serv, sizeof(serv), "%d", ntohs(ap->s_in.sin_port));
            *service = OPENSSL_strdup(serv);
        }
    }

    if ((hostname != NULL && *hostname == NULL)
            || (service != NULL && *service == NULL)) {
        if (hostname != NULL) {
            OPENSSL_free(*hostname);
            *hostname = NULL;
        }
        if (service != NULL) {
            OPENSSL_free(*service);
            *service = NULL;
        }
        ERR_raise(ERR_LIB_BIO, ERR_R_MALLOC_FAILURE);
        return 0;
    }

    return 1;
}

char *BIO_ADDR_hostname_string(const BIO_ADDR *ap, int numeric)
{
    char *hostname = NULL;

    if (addr_strings(ap, numeric, &hostname, NULL))
        return hostname;

    return NULL;
}

char *BIO_ADDR_service_string(const BIO_ADDR *ap, int numeric)
{
    char *service = NULL;

    if (addr_strings(ap, numeric, NULL, &service))
        return service;

    return NULL;
}

char *BIO_ADDR_path_string(const BIO_ADDR *ap)
{
#ifdef AF_UNIX
    if (ap->sa.sa_family == AF_UNIX)
        return OPENSSL_strdup(ap->s_un.sun_path);
#endif
    return NULL;
}

/*
 * BIO_ADDR_sockaddr - non-public routine to return the struct sockaddr
 * for a given BIO_ADDR.  In reality, this is simply a type safe cast.
 * The returned struct sockaddr is const, so it can't be tampered with.
 */
const struct sockaddr *BIO_ADDR_sockaddr(const BIO_ADDR *ap)
{
    return &(ap->sa);
}

/*
 * BIO_ADDR_sockaddr_noconst - non-public function that does the same
 * as BIO_ADDR_sockaddr, but returns a non-const.  USE WITH CARE, as
 * it allows you to tamper with the data (and thereby the contents
 * of the input BIO_ADDR).
 */
struct sockaddr *BIO_ADDR_sockaddr_noconst(BIO_ADDR *ap)
{
    return &(ap->sa);
}

/*
 * BIO_ADDR_sockaddr_size - non-public function that returns the size
 * of the struct sockaddr the BIO_ADDR is using.  If the protocol family
 * isn't set or is something other than AF_INET, AF_INET6 or AF_UNIX,
 * the size of the BIO_ADDR type is returned.
 */
socklen_t BIO_ADDR_sockaddr_size(const BIO_ADDR *ap)
{
    if (ap->sa.sa_family == AF_INET)
        return sizeof(ap->s_in);
#if OPENSSL_USE_IPV6
    if (ap->sa.sa_family == AF_INET6)
        return sizeof(ap->s_in6);
#endif
#ifdef AF_UNIX
    if (ap->sa.sa_family == AF_UNIX)
        return sizeof(ap->s_un);
#endif
    return sizeof(*ap);
}

/**********************************************************************
 *
 * Address info database
 *
 */

const BIO_ADDRINFO *BIO_ADDRINFO_next(const BIO_ADDRINFO *bai)
{
    if (bai != NULL)
        return bai->bai_next;
    return NULL;
}

int BIO_ADDRINFO_family(const BIO_ADDRINFO *bai)
{
    if (bai != NULL)
        return bai->bai_family;
    return 0;
}

int BIO_ADDRINFO_socktype(const BIO_ADDRINFO *bai)
{
    if (bai != NULL)
        return bai->bai_socktype;
    return 0;
}

int BIO_ADDRINFO_protocol(const BIO_ADDRINFO *bai)
{
    if (bai != NULL) {
        if (bai->bai_protocol != 0)
            return bai->bai_protocol;

#ifdef AF_UNIX
        if (bai->bai_family == AF_UNIX)
            return 0;
#endif

        switch (bai->bai_socktype) {
        case SOCK_STREAM:
            return IPPROTO_TCP;
        case SOCK_DGRAM:
            return IPPROTO_UDP;
        default:
            break;
        }
    }
    return 0;
}

/*
 * BIO_ADDRINFO_sockaddr_size - non-public function that returns the size
 * of the struct sockaddr inside the BIO_ADDRINFO.
 */
socklen_t BIO_ADDRINFO_sockaddr_size(const BIO_ADDRINFO *bai)
{
    if (bai != NULL)
        return bai->bai_addrlen;
    return 0;
}

/*
 * BIO_ADDRINFO_sockaddr - non-public function that returns bai_addr
 * as the struct sockaddr it is.
 */
const struct sockaddr *BIO_ADDRINFO_sockaddr(const BIO_ADDRINFO *bai)
{
    if (bai != NULL)
        return bai->bai_addr;
    return NULL;
}

const BIO_ADDR *BIO_ADDRINFO_address(const BIO_ADDRINFO *bai)
{
    if (bai != NULL)
        return (BIO_ADDR *)bai->bai_addr;
    return NULL;
}

void BIO_ADDRINFO_free(BIO_ADDRINFO *bai)
{
    if (bai == NULL)
        return;

#ifdef AI_PASSIVE
# ifdef AF_UNIX
#  define _cond bai->bai_family != AF_UNIX
# else
#  define _cond 1
# endif
    if (_cond) {
        freeaddrinfo(bai);
        return;
    }
#endif

    /* Free manually when we know that addrinfo_wrap() was used.
     * See further comment above addrinfo_wrap()
     */
    while (bai != NULL) {
        BIO_ADDRINFO *next = bai->bai_next;
        OPENSSL_free(bai->bai_addr);
        OPENSSL_free(bai);
        bai = next;
    }
}

/**********************************************************************
 *
 * Service functions
 *
 */

/*-
 * The specs in hostserv can take these forms:
 *
 * host:service         => *host = "host", *service = "service"
 * host:*               => *host = "host", *service = NULL
 * host:                => *host = "host", *service = NULL
 * :service             => *host = NULL, *service = "service"
 * *:service            => *host = NULL, *service = "service"
 *
 * in case no : is present in the string, the result depends on
 * hostserv_prio, as follows:
 *
 * when hostserv_prio == BIO_PARSE_PRIO_HOST
 * host                 => *host = "host", *service untouched
 *
 * when hostserv_prio == BIO_PARSE_PRIO_SERV
 * service              => *host untouched, *service = "service"
 *
 */
int BIO_parse_hostserv(const char *hostserv, char **host, char **service,
                       enum BIO_hostserv_priorities hostserv_prio)
{
    const char *h = NULL; size_t hl = 0;
    const char *p = NULL; size_t pl = 0;

    if (*hostserv == '[') {
        if ((p = strchr(hostserv, ']')) == NULL)
            goto spec_err;
        h = hostserv + 1;
        hl = p - h;
        p++;
        if (*p == '\0')
            p = NULL;
        else if (*p != ':')
            goto spec_err;
        else {
            p++;
            pl = strlen(p);
        }
    } else {
        const char *p2 = strrchr(hostserv, ':');
        p = strchr(hostserv, ':');

        /*-
         * Check for more than one colon.  There are three possible
         * interpretations:
         * 1. IPv6 address with port number, last colon being separator.
         * 2. IPv6 address only.
         * 3. IPv6 address only if hostserv_prio == BIO_PARSE_PRIO_HOST,
         *    IPv6 address and port number if hostserv_prio == BIO_PARSE_PRIO_SERV
         * Because of this ambiguity, we currently choose to make it an
         * error.
         */
        if (p != p2)
            goto amb_err;

        if (p != NULL) {
            h = hostserv;
            hl = p - h;
            p++;
            pl = strlen(p);
        } else if (hostserv_prio == BIO_PARSE_PRIO_HOST) {
            h = hostserv;
            hl = strlen(h);
        } else {
            p = hostserv;
            pl = strlen(p);
        }
    }

    if (p != NULL && strchr(p, ':'))
        goto spec_err;

    if (h != NULL && host != NULL) {
        if (hl == 0
            || (hl == 1 && h[0] == '*')) {
            *host = NULL;
        } else {
            *host = OPENSSL_strndup(h, hl);
            if (*host == NULL)
                goto memerr;
        }
    }
    if (p != NULL && service != NULL) {
        if (pl == 0
            || (pl == 1 && p[0] == '*')) {
            *service = NULL;
        } else {
            *service = OPENSSL_strndup(p, pl);
            if (*service == NULL)
                goto memerr;
        }
    }

    return 1;
 amb_err:
    ERR_raise(ERR_LIB_BIO, BIO_R_AMBIGUOUS_HOST_OR_SERVICE);
    return 0;
 spec_err:
    ERR_raise(ERR_LIB_BIO, BIO_R_MALFORMED_HOST_OR_SERVICE);
    return 0;
 memerr:
    ERR_raise(ERR_LIB_BIO, ERR_R_MALLOC_FAILURE);
    return 0;
}

/* addrinfo_wrap is used to build our own addrinfo "chain".
 * (it has only one entry, so calling it a chain may be a stretch)
 * It should ONLY be called when getaddrinfo() and friends
 * aren't available, OR when dealing with a non IP protocol
 * family, such as AF_UNIX
 *
 * the return value is 1 on success, or 0 on failure, which
 * only happens if a memory allocation error occurred.
 */
static int addrinfo_wrap(int family, int socktype,
                         const void *where, size_t wherelen,
                         unsigned short port,
                         BIO_ADDRINFO **bai)
{
    if ((*bai = OPENSSL_zalloc(sizeof(**bai))) == NULL) {
        ERR_raise(ERR_LIB_BIO, ERR_R_MALLOC_FAILURE);
        return 0;
    }

    (*bai)->bai_family = family;
    (*bai)->bai_socktype = socktype;
    if (socktype == SOCK_STREAM)
        (*bai)->bai_protocol = IPPROTO_TCP;
    if (socktype == SOCK_DGRAM)
        (*bai)->bai_protocol = IPPROTO_UDP;
#ifdef AF_UNIX
    if (family == AF_UNIX)
        (*bai)->bai_protocol = 0;
#endif
    {
        /* Magic: We know that BIO_ADDR_sockaddr_noconst is really
           just an advanced cast of BIO_ADDR* to struct sockaddr *
           by the power of union, so while it may seem that we're
           creating a memory leak here, we are not.  It will be
           all right. */
        BIO_ADDR *addr = BIO_ADDR_new();
        if (addr != NULL) {
            BIO_ADDR_rawmake(addr, family, where, wherelen, port);
            (*bai)->bai_addr = BIO_ADDR_sockaddr_noconst(addr);
        }
    }
    (*bai)->bai_next = NULL;
    if ((*bai)->bai_addr == NULL) {
        BIO_ADDRINFO_free(*bai);
        *bai = NULL;
        return 0;
    }
    return 1;
}

DEFINE_RUN_ONCE_STATIC(do_bio_lookup_init)
{
    bio_lookup_lock = CRYPTO_THREAD_lock_new();
    return bio_lookup_lock != NULL;
}

int BIO_lookup(const char *host, const char *service,
               enum BIO_lookup_type lookup_type,
               int family, int socktype, BIO_ADDRINFO **res)
{
    return BIO_lookup_ex(host, service, lookup_type, family, socktype, 0, res);
}

/*-
 * BIO_lookup_ex - look up the host and service you want to connect to.
 * @host: the host (or node, in case family == AF_UNIX) you want to connect to.
 * @service: the service you want to connect to.
 * @lookup_type: declare intent with the result, client or server.
 * @family: the address family you want to use.  Use AF_UNSPEC for any, or
 *  AF_INET, AF_INET6 or AF_UNIX.
 * @socktype: The socket type you want to use.  Can be SOCK_STREAM, SOCK_DGRAM
 *  or 0 for all.
 * @protocol: The protocol to use, e.g. IPPROTO_TCP or IPPROTO_UDP or 0 for all.
 *            Note that some platforms may not return IPPROTO_SCTP without
 *            explicitly requesting it (i.e. IPPROTO_SCTP may not be returned
 *            with 0 for the protocol)
 * @res: Storage place for the resulting list of returned addresses
 *
 * This will do a lookup of the host and service that you want to connect to.
 * It returns a linked list of different addresses you can try to connect to.
 *
 * When no longer needed you should call BIO_ADDRINFO_free() to free the result.
 *
 * The return value is 1 on success or 0 in case of error.
 */
int BIO_lookup_ex(const char *host, const char *service, int lookup_type,
                  int family, int socktype, int protocol, BIO_ADDRINFO **res)
{
    int ret = 0;                 /* Assume failure */

    switch (family) {
    case AF_INET:
#if OPENSSL_USE_IPV6
    case AF_INET6:
#endif
#ifdef AF_UNIX
    case AF_UNIX:
#endif
#ifdef AF_UNSPEC
    case AF_UNSPEC:
#endif
        break;
    default:
        ERR_raise(ERR_LIB_BIO, BIO_R_UNSUPPORTED_PROTOCOL_FAMILY);
        return 0;
    }

#ifdef AF_UNIX
    if (family == AF_UNIX) {
        if (addrinfo_wrap(family, socktype, host, strlen(host), 0, res))
            return 1;
        else
            ERR_raise(ERR_LIB_BIO, ERR_R_MALLOC_FAILURE);
        return 0;
    }
#endif

    if (BIO_sock_init() != 1)
        return 0;

    if (1) {
#ifdef AI_PASSIVE
        int gai_ret = 0, old_ret = 0;
        struct addrinfo hints;

        memset(&hints, 0, sizeof(hints));

        hints.ai_family = family;
        hints.ai_socktype = socktype;
        hints.ai_protocol = protocol;
# ifdef AI_ADDRCONFIG
#  ifdef AF_UNSPEC
        if (host != NULL && family == AF_UNSPEC)
#  endif
            hints.ai_flags |= AI_ADDRCONFIG;
# endif

        if (lookup_type == BIO_LOOKUP_SERVER)
            hints.ai_flags |= AI_PASSIVE;

        /* Note that |res| SHOULD be a 'struct addrinfo **' thanks to
         * macro magic in bio_local.h
         */
# if defined(AI_ADDRCONFIG) && defined(AI_NUMERICHOST)
      retry:
# endif
        switch ((gai_ret = getaddrinfo(host, service, &hints, res))) {
# ifdef EAI_SYSTEM
        case EAI_SYSTEM:
            ERR_raise_data(ERR_LIB_SYS, get_last_socket_error(),
                           "calling getaddrinfo()");
            ERR_raise(ERR_LIB_BIO, ERR_R_SYS_LIB);
            break;
# endif
# ifdef EAI_MEMORY
        case EAI_MEMORY:
            ERR_raise(ERR_LIB_BIO, ERR_R_MALLOC_FAILURE);
            break;
# endif
        case 0:
            ret = 1;             /* Success */
            break;
        default:
# if defined(AI_ADDRCONFIG) && defined(AI_NUMERICHOST)
            if (hints.ai_flags & AI_ADDRCONFIG) {
                hints.ai_flags &= ~AI_ADDRCONFIG;
                hints.ai_flags |= AI_NUMERICHOST;
                old_ret = gai_ret;
                goto retry;
            }
# endif
            ERR_raise_data(ERR_LIB_BIO, ERR_R_SYS_LIB,
                           gai_strerror(old_ret ? old_ret : gai_ret));
            break;
        }
    } else {
#endif
        const struct hostent *he;
/*
 * Because struct hostent is defined for 32-bit pointers only with
 * VMS C, we need to make sure that '&he_fallback_address' and
 * '&he_fallback_addresses' are 32-bit pointers
 */
#if defined(OPENSSL_SYS_VMS) && defined(__DECC)
# pragma pointer_size save
# pragma pointer_size 32
#endif
        /* Windows doesn't seem to have in_addr_t */
#if defined(OPENSSL_SYS_WINDOWS) || defined(OPENSSL_SYS_MSDOS)
        static uint32_t he_fallback_address;
        static const char *he_fallback_addresses[] =
            { (char *)&he_fallback_address, NULL };
#else
        static in_addr_t he_fallback_address;
        static const char *he_fallback_addresses[] =
            { (char *)&he_fallback_address, NULL };
#endif
        static const struct hostent he_fallback =
            { NULL, NULL, AF_INET, sizeof(he_fallback_address),
              (char **)&he_fallback_addresses };
#if defined(OPENSSL_SYS_VMS) && defined(__DECC)
# pragma pointer_size restore
#endif

        struct servent *se;
        /* Apparently, on WIN64, s_proto and s_port have traded places... */
#ifdef _WIN64
        struct servent se_fallback = { NULL, NULL, NULL, 0 };
#else
        struct servent se_fallback = { NULL, NULL, 0, NULL };
#endif

        if (!RUN_ONCE(&bio_lookup_init, do_bio_lookup_init)) {
            ERR_raise(ERR_LIB_BIO, ERR_R_MALLOC_FAILURE);
            ret = 0;
            goto err;
        }

        if (!CRYPTO_THREAD_write_lock(bio_lookup_lock)) {
            ret = 0;
            goto err;
        }
        he_fallback_address = INADDR_ANY;
        if (host == NULL) {
            he = &he_fallback;
            switch (lookup_type) {
            case BIO_LOOKUP_CLIENT:
                he_fallback_address = INADDR_LOOPBACK;
                break;
            case BIO_LOOKUP_SERVER:
                he_fallback_address = INADDR_ANY;
                break;
            default:
                /* We forgot to handle a lookup type! */
                assert("We forgot to handle a lookup type!" == NULL);
                ERR_raise(ERR_LIB_BIO, ERR_R_INTERNAL_ERROR);
                ret = 0;
                goto err;
            }
        } else {
            he = gethostbyname(host);

            if (he == NULL) {
#ifndef OPENSSL_SYS_WINDOWS
                /*
                 * This might be misleading, because h_errno is used as if
                 * it was errno. To minimize mixup add 1000. Underlying
                 * reason for this is that hstrerror is declared obsolete,
                 * not to mention that a) h_errno is not always guaranteed
                 * to be meaningless; b) hstrerror can reside in yet another
                 * library, linking for sake of hstrerror is an overkill;
                 * c) this path is not executed on contemporary systems
                 * anyway [above getaddrinfo/gai_strerror is]. We just let
                 * system administrator figure this out...
                 */
# if defined(OPENSSL_SYS_VXWORKS)
                /* h_errno doesn't exist on VxWorks */
                ERR_raise_data(ERR_LIB_SYS, 1000,
                               "calling gethostbyname()");
# else
                ERR_raise_data(ERR_LIB_SYS, 1000 + h_errno,
                               "calling gethostbyname()");
# endif
#else
                ERR_raise_data(ERR_LIB_SYS, get_last_socket_error(),
                               "calling gethostbyname()");
#endif
                ret = 0;
                goto err;
            }
        }

        if (service == NULL) {
            se_fallback.s_port = 0;
            se_fallback.s_proto = NULL;
            se = &se_fallback;
        } else {
            char *endp = NULL;
            long portnum = strtol(service, &endp, 10);

/*
 * Because struct servent is defined for 32-bit pointers only with
 * VMS C, we need to make sure that 'proto' is a 32-bit pointer.
 */
#if defined(OPENSSL_SYS_VMS) && defined(__DECC)
# pragma pointer_size save
# pragma pointer_size 32
#endif
            char *proto = NULL;
#if defined(OPENSSL_SYS_VMS) && defined(__DECC)
# pragma pointer_size restore
#endif

            switch (socktype) {
            case SOCK_STREAM:
                proto = "tcp";
                break;
            case SOCK_DGRAM:
                proto = "udp";
                break;
            }

            if (endp != service && *endp == '\0'
                    && portnum > 0 && portnum < 65536) {
                se_fallback.s_port = htons((unsigned short)portnum);
                se_fallback.s_proto = proto;
                se = &se_fallback;
            } else if (endp == service) {
                se = getservbyname(service, proto);

                if (se == NULL) {
                    ERR_raise_data(ERR_LIB_SYS, get_last_socket_error(),
                                   "calling getservbyname()");
                    goto err;
                }
            } else {
                ERR_raise(ERR_LIB_BIO, BIO_R_MALFORMED_HOST_OR_SERVICE);
                goto err;
            }
        }

        *res = NULL;

        {
/*
 * Because hostent::h_addr_list is an array of 32-bit pointers with VMS C,
 * we must make sure our iterator designates the same element type, hence
 * the pointer size dance.
 */
#if defined(OPENSSL_SYS_VMS) && defined(__DECC)
# pragma pointer_size save
# pragma pointer_size 32
#endif
            char **addrlistp;
#if defined(OPENSSL_SYS_VMS) && defined(__DECC)
# pragma pointer_size restore
#endif
            size_t addresses;
            BIO_ADDRINFO *tmp_bai = NULL;

            /* The easiest way to create a linked list from an
               array is to start from the back */
            for (addrlistp = he->h_addr_list; *addrlistp != NULL;
                 addrlistp++)
                ;

            for (addresses = addrlistp - he->h_addr_list;
                 addrlistp--, addresses-- > 0; ) {
                if (!addrinfo_wrap(he->h_addrtype, socktype,
                                   *addrlistp, he->h_length,
                                   se->s_port, &tmp_bai))
                    goto addrinfo_malloc_err;
                tmp_bai->bai_next = *res;
                *res = tmp_bai;
                continue;
             addrinfo_malloc_err:
                BIO_ADDRINFO_free(*res);
                *res = NULL;
                ERR_raise(ERR_LIB_BIO, ERR_R_MALLOC_FAILURE);
                ret = 0;
                goto err;
            }

            ret = 1;
        }
     err:
        CRYPTO_THREAD_unlock(bio_lookup_lock);
    }

    return ret;
}

#endif /* OPENSSL_NO_SOCK */
