From: Siddhesh Poyarekar Date: Mon, 19 Nov 2012 07:31:43 +0000 (+0530) Subject: Return EAI_SYSTEM if we're out of file descriptors X-Git-Tag: glibc-2.17~174 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=cfde9b463d63092ff0908d4c2748ace648e2ead8;p=thirdparty%2Fglibc.git Return EAI_SYSTEM if we're out of file descriptors Resolves BZ #14719. --- diff --git a/ChangeLog b/ChangeLog index 8f2f6d221c4..75d315a9cc5 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,14 @@ +2012-11-19 Siddhesh Poyarekar + + [BZ #14719] + * nss/getXXbyYY_r.c (INTERNAL (REENTRANT_NAME)): Set h_errno to + NETDB_INTERNAL when NSS_STATUS_UNAVAIL. + * resolv/nss_dns/dns-host.c (_nss_dns_gethostbyname3_r): Set + h_errno to NETDB_INTERNAL when errno is EMFILE or ENFILE. + (_nss_dns_gethostbyname4_r): Likewise. + * sysdeps/posix/getaddrinfo.c (gaih_inet): Set result to + EAI_SYSTEM if NSS_STATUS_UNAVAIL. + 2012-11-19 Peng Haitao [BZ #13763] diff --git a/NEWS b/NEWS index d3e64c40d85..d59465c942d 100644 --- a/NEWS +++ b/NEWS @@ -19,8 +19,8 @@ Version 2.17 14518, 14519, 14530, 14532, 14538, 14543, 14544, 14545, 14557, 14562, 14568, 14576, 14579, 14583, 14587, 14595, 14602, 14610, 14621, 14638, 14645, 14648, 14652, 14660, 14661, 14669, 14672, 14683, 14694, 14716, - 14743, 14767, 14783, 14784, 14785, 14793, 14796, 14797, 14801, 14805, - 14807, 14809, 14811, 14815, 14821, 14824, 14828, 14831, 14838. + 14719, 14743, 14767, 14783, 14784, 14785, 14793, 14796, 14797, 14801, + 14805, 14807, 14809, 14811, 14815, 14821, 14824, 14828, 14831, 14838. * Port to ARM AArch64 contributed by Linaro. diff --git a/nss/getXXbyYY_r.c b/nss/getXXbyYY_r.c index 8b3b61b663e..885b53b60b0 100644 --- a/nss/getXXbyYY_r.c +++ b/nss/getXXbyYY_r.c @@ -284,7 +284,12 @@ done: #endif *result = status == NSS_STATUS_SUCCESS ? resbuf : NULL; #ifdef NEED_H_ERRNO - if (status != NSS_STATUS_SUCCESS && ! any_service) + if (status == NSS_STATUS_UNAVAIL) + /* Either we failed to lookup the functions or the functions themselves + had a system error. Set NETDB_INTERNAL here to let the caller know + that the errno may have the real reason for failure. */ + *h_errnop = NETDB_INTERNAL; + else if (status != NSS_STATUS_SUCCESS && !any_service) /* We were not able to use any service. */ *h_errnop = NO_RECOVERY; #endif diff --git a/resolv/nss_dns/dns-host.c b/resolv/nss_dns/dns-host.c index 6b62c058837..f78b87990fd 100644 --- a/resolv/nss_dns/dns-host.c +++ b/resolv/nss_dns/dns-host.c @@ -199,6 +199,11 @@ _nss_dns_gethostbyname3_r (const char *name, int af, struct hostent *result, status = NSS_STATUS_TRYAGAIN; h_errno = TRY_AGAIN; break; + /* System has run out of file descriptors. */ + case EMFILE: + case ENFILE: + h_errno = NETDB_INTERNAL; + /* Fall through. */ case ECONNREFUSED: case ETIMEDOUT: status = NSS_STATUS_UNAVAIL; @@ -311,14 +316,26 @@ _nss_dns_gethostbyname4_r (const char *name, struct gaih_addrtuple **pat, &ans2p, &nans2p, &resplen2); if (n < 0) { - if (errno == ESRCH) + switch (errno) { + case ESRCH: status = NSS_STATUS_TRYAGAIN; h_errno = TRY_AGAIN; + break; + /* System has run out of file descriptors. */ + case EMFILE: + case ENFILE: + h_errno = NETDB_INTERNAL; + /* Fall through. */ + case ECONNREFUSED: + case ETIMEDOUT: + status = NSS_STATUS_UNAVAIL; + break; + default: + status = NSS_STATUS_NOTFOUND; + break; } - else - status = (errno == ECONNREFUSED - ? NSS_STATUS_UNAVAIL : NSS_STATUS_NOTFOUND); + *herrnop = h_errno; if (h_errno == TRY_AGAIN) *errnop = EAGAIN; diff --git a/sysdeps/posix/getaddrinfo.c b/sysdeps/posix/getaddrinfo.c index 3cc244b7fd1..d95c2d1156b 100644 --- a/sysdeps/posix/getaddrinfo.c +++ b/sysdeps/posix/getaddrinfo.c @@ -1049,6 +1049,12 @@ gaih_inet (const char *name, const struct gaih_service *service, _res.options |= old_res_options & RES_USE_INET6; + if (status == NSS_STATUS_UNAVAIL) + { + result = GAIH_OKIFUNSPEC | -EAI_SYSTEM; + goto free_and_return; + } + if (no_data != 0 && no_inet6_data != 0) { /* If both requests timed out report this. */