The potential bug incurred by "one_addr".

speedfirst nginx-forum at
Thu Dec 16 11:36:15 MSK 2010

In ngx_inet.c, there is a code piece of function
"ngx_inet_resolve_host". If I set u->one_addr to 1, but unfortunately
this hostname map to multiple IP addresses, such as 
[code] myhost myhost
in /etc/hosts.

h->h_addr_list will be 2 entries before NULL. Each of them will be
converted to human readable format and assigned to u->addrs[ i ].
However, when one_addr is set, [b]u->addrs will be allocated ONLY ONE
ngx_addr_t mem.[/b] In this way, a mem crash is inevitable.

I set one_addr to 1 because I'm writing a custom module and want to
connect another server. Sadly the server is also running on the local
host with multiple IP in /etc/hosts. I want to connect the first IP
match that host name ( because that server require a
non-lookback IP. I thought "one_addr" means "fetch the first found IP".
But seems I was wrong.

Besides this, I insist alloc mem with "i", but loop will h->h_addr_list
is very dangerous. Report an error is more suitable  rather than leave a
time bomb.

Affected version: all versions!!!

if (u->one_addr == 0) {
            for (i = 0; h->h_addr_list[i] != NULL; i++) { /* void */ }

        } else {
            i = 1;

        /* MP: ngx_shared_palloc() */

        u->addrs = ngx_pcalloc(pool, i * sizeof(ngx_addr_t));
        if (u->addrs == NULL) {
            return NGX_ERROR;

        u->naddrs = i;

        for (i = 0; h->h_addr_list[ i ] != NULL; i++) {

            sin = ngx_pcalloc(pool, sizeof(struct sockaddr_in));
            if (sin == NULL) {
                return NGX_ERROR;

            sin->sin_family = AF_INET;
            sin->sin_port = port;
            sin->sin_addr.s_addr = *(in_addr_t *) (h->h_addr_list[ i

            u->addrs[ i ].sockaddr = (struct sockaddr *) sin;
            u->addrs[ i ].socklen = sizeof(struct sockaddr_in);

            len = NGX_INET_ADDRSTRLEN + sizeof(":65535") - 1;

            p = ngx_pnalloc(pool, len);
            if (p == NULL) {
                return NGX_ERROR;

            len = ngx_sock_ntop((struct sockaddr *) sin, p, len, 1);

            u->addrs[ i ].name.len = len;
            u->addrs[ i ] = p;

Posted at Nginx Forum:,159051,159051#msg-159051

More information about the nginx mailing list