summaryrefslogtreecommitdiff
path: root/sal
diff options
context:
space:
mode:
authorMichael Meeks <michael.meeks@suse.com>2011-11-21 17:38:12 +0000
committerMichael Meeks <michael.meeks@suse.com>2011-11-21 17:40:47 +0000
commit441227374cf285c2e133f8889db244d2f19609c5 (patch)
tree60398a1176c0756f13ef00b12b5ea2b84fef06fb /sal
parentd714c17c21bb061672ac0e900644f09380eaa140 (diff)
Revert "Remove internal gethostbyname_r implementation." - OSX needs it
Diffstat (limited to 'sal')
-rw-r--r--sal/osl/unx/system.c94
-rw-r--r--sal/osl/unx/system.h4
2 files changed, 98 insertions, 0 deletions
diff --git a/sal/osl/unx/system.c b/sal/osl/unx/system.c
index 63d67bcf46f2..4bb0e4643d1f 100644
--- a/sal/osl/unx/system.c
+++ b/sal/osl/unx/system.c
@@ -32,6 +32,100 @@
static pthread_mutex_t getrtl_mutex = PTHREAD_MUTEX_INITIALIZER;
+/* struct passwd differs on some platforms */
+#if !defined(FREEBSD) || (__FreeBSD_version < 601103)
+
+extern int h_errno;
+
+struct hostent *gethostbyname_r(const char *name, struct hostent *result,
+ char *buffer, int buflen, int *h_errnop)
+{
+ /* buffer layout: name\0
+ * array_of_pointer_to_aliases
+ * NULL
+ * alias1\0...aliasn\0
+ * array_of_pointer_to_addresses
+ * NULL
+ * addr1addr2addr3...addrn
+ */
+ struct hostent* res;
+
+ pthread_mutex_lock(&getrtl_mutex);
+
+ if ( (res = gethostbyname(name)) )
+ {
+ int nname, naliases, naddr_list, naliasesdata, n;
+ char **p, **parray, *data;
+
+ /* Check buffer size before copying, we want to leave the
+ * buffers unmodified in case something goes wrong.
+ *
+ * Is this required?
+ */
+
+ nname= strlen(res->h_name)+1;
+
+ naliases = naddr_list = naliasesdata = 0;
+
+ for ( p = res->h_aliases; *p != NULL; p++) {
+ naliases++;
+ naliasesdata += strlen(*p)+1;
+ }
+
+ for ( p = res->h_addr_list; *p != NULL; p++)
+ naddr_list++;
+
+ if ( nname
+ + (naliases+1)*sizeof(char*) + naliasesdata
+ + (naddr_list+1)*sizeof(char*) + naddr_list*res->h_length
+ <= buflen )
+ {
+ memcpy(result, res, sizeof(struct hostent));
+
+ strcpy(buffer, res->h_name);
+ result->h_name = buffer;
+ buffer += nname;
+
+ parray = (char**)buffer;
+ result->h_aliases = parray;
+ data = buffer + (naliases+1)*sizeof(char*);
+ for ( p = res->h_aliases; *p != NULL; p++) {
+ n = strlen(*p)+1;
+ *parray++ = data;
+ memcpy(data, *p, n);
+ data += n;
+ }
+ *parray = NULL;
+ buffer = data;
+ parray = (char**)buffer;
+ result->h_addr_list = parray;
+ data = buffer + (naddr_list+1)*sizeof(char*);
+ for ( p = res->h_addr_list; *p != NULL; p++) {
+ *parray++ = data;
+ memcpy(data, *p, res->h_length);
+ data += res->h_length;
+ }
+ *parray = NULL;
+
+ res = result;
+ }
+ else
+ {
+ errno = ERANGE;
+ res = NULL;
+ }
+ }
+ else
+ {
+ *h_errnop = h_errno;
+ }
+
+ pthread_mutex_unlock(&getrtl_mutex);
+
+ return res;
+}
+#endif /* !defined(FREEBSD) || (__FreeBSD_version < 601103) */
+
#if defined(MACOSX)
/*
* Add support for resolving Mac native alias files (not the same as unix alias files)
diff --git a/sal/osl/unx/system.h b/sal/osl/unx/system.h
index d3293ad6ceb0..c8f487170ba5 100644
--- a/sal/osl/unx/system.h
+++ b/sal/osl/unx/system.h
@@ -504,6 +504,10 @@ extern struct spwd *getspnam_r(const char *name, struct spwd *result,
struct tm *localtime_r(const time_t *timep, struct tm *buffer);
struct tm *gmtime_r(const time_t *timep, struct tm *buffer);
#endif /* !defined FREEBSD || (__FreeBSD_version < 500112) */
+#if !defined(FREEBSD) || (__FreeBSD_version < 601103)
+struct hostent *gethostbyname_r(const char *name, struct hostent *result,
+ char *buffer, int buflen, int *h_errnop);
+#endif /* !defined(FREEBSD) || (__FreeBSD_version < 601103) */
#endif
#endif /* __OSL_SYSTEM_H__ */