diff options
author | Bojan Smojver <bojan@apache.org> | 2008-05-29 01:57:16 +0000 |
---|---|---|
committer | Bojan Smojver <bojan@apache.org> | 2008-05-29 01:57:16 +0000 |
commit | 9f935aaede411677912713e6ca8ce2ccbb210cac (patch) | |
tree | 6cc6bb9ee6d4b23e7db6490bfddc35a06910a95c /network_io | |
parent | 7c72118c012ae6caf1870b36c35c20b8634c127c (diff) | |
download | apr-9f935aaede411677912713e6ca8ce2ccbb210cac.tar.gz |
Fix PR44367.
Caveats:
- no idea if IBM's proprietary OSes actually have thread-safe
version of getservbyname() function, just assumed that by looking at
other similar functions being marked safe in APR detection code
- works on Linux (Fedora 9, i.e. glibc2)
Use thread safe versions of getservbyname().
git-svn-id: https://svn.apache.org/repos/asf/apr/apr/trunk@661178 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'network_io')
-rw-r--r-- | network_io/unix/sockaddr.c | 46 |
1 files changed, 46 insertions, 0 deletions
diff --git a/network_io/unix/sockaddr.c b/network_io/unix/sockaddr.c index 31a0eb5be..4e79f8934 100644 --- a/network_io/unix/sockaddr.c +++ b/network_io/unix/sockaddr.c @@ -705,17 +705,63 @@ APR_DECLARE(apr_status_t) apr_getnameinfo(char **hostname, APR_DECLARE(apr_status_t) apr_getservbyname(apr_sockaddr_t *sockaddr, const char *servname) { +#if APR_HAS_THREADS && !defined(GETSERVBYNAME_IS_THREAD_SAFE) && \ + defined(HAVE_GETSERVBYNAME_R) && \ + (defined(GETSERVBYNAME_R_GLIBC2) || defined(GETSERVBYNAME_R_SOLARIS) || \ + defined(GETSERVBYNAME_R_OSF1)) + struct servent se; +#if defined(GETSERVBYNAME_R_OSF1) + struct servent_data sed; + + memset(&sed, 0, sizeof(sed)); /* must zero fill before use */ +#else +#if defined(GETSERVBYNAME_R_GLIBC2) + struct servent *res; +#endif + char buf[1024]; +#endif +#else struct servent *se; +#endif if (servname == NULL) return APR_EINVAL; +#if APR_HAS_THREADS && !defined(GETSERVBYNAME_IS_THREAD_SAFE) && \ + defined(HAVE_GETSERVBYNAME_R) && \ + (defined(GETSERVBYNAME_R_GLIBC2) || defined(GETSERVBYNAME_R_SOLARIS) || \ + defined(GETSERVBYNAME_R_OSF1)) +#if defined(GETSERVBYNAME_R_GLIBC2) + if (getservbyname_r(servname, NULL, + &se, buf, sizeof(buf), &res) == 0 && res != NULL) { + sockaddr->port = ntohs(res->s_port); + sockaddr->servname = apr_pstrdup(sockaddr->pool, servname); + sockaddr->sa.sin.sin_port = res->s_port; + return APR_SUCCESS; + } +#elif defined(GETSERVBYNAME_R_SOLARIS) + if (getservbyname_r(servname, NULL, &se, buf, sizeof(buf)) != NULL) { + sockaddr->port = ntohs(se.s_port); + sockaddr->servname = apr_pstrdup(sockaddr->pool, servname); + sockaddr->sa.sin.sin_port = se.s_port; + return APR_SUCCESS; + } +#elif defined(GETSERVBYNAME_R_OSF1) + if (getservbyname_r(servname, NULL, &se, &sed) == 0) { + sockaddr->port = ntohs(se.s_port); + sockaddr->servname = apr_pstrdup(sockaddr->pool, servname); + sockaddr->sa.sin.sin_port = se.s_port; + return APR_SUCCESS; + } +#endif +#else if ((se = getservbyname(servname, NULL)) != NULL){ sockaddr->port = ntohs(se->s_port); sockaddr->servname = apr_pstrdup(sockaddr->pool, servname); sockaddr->sa.sin.sin_port = se->s_port; return APR_SUCCESS; } +#endif return APR_ENOENT; } |