This is the mail archive of the libc-hacker@sourceware.cygnus.com mailing list for the glibc project.
Note that libc-hacker is a closed list. You may look at the archives of this list, but subscription and posting are not open.
Index Nav: | [Date Index] [Subject Index] [Author Index] [Thread Index] | |
---|---|---|
Message Nav: | [Date Prev] [Date Next] | [Thread Prev] [Thread Next] |
The program below tests gethostbyname_r with an unknown host. The function returns with 0 (instead of != 0) but doesn't set the host pointer: $ ./gethst_r-test gethostbyname_r returned: 0 herr: 1 hp is null nss/getXXbyYY_r.c now has: return status == NSS_STATUS_SUCCESS ? 0 : errno; But what happens if errno is 0 and status != NSS_STATUS_SUCCESS (this happens with host not found in my test program)? Before Ulrich's change we always returned -1 and could easily check for it. The glibc manual isn't clear on this - do I have to check also the return pointer for NULL if the result is 0? The POSIX documentation seems to imply this. Let's look at an example from glibc (inet/rcmd.c): while (__gethostbyname_r (*ahost, &hostbuf, tmphstbuf, hstbuflen, &hp, &herr) != 0) if (herr != NETDB_INTERNAL || errno != ERANGE) { __set_h_errno (herr); herror(*ahost); return -1; } else { /* Enlarge the buffer. */ hstbuflen *= 2; tmphstbuf = __alloca (hstbuflen); } pfd[0].events = POLLIN; pfd[1].events = POLLIN; *ahost = hp->h_name; This code segfaults accessing hp->h_name iff the host doesn't exist. We need to add at least the following code after the loop: if (hp == NULL) { __set_h_errno (herr); herror(*ahost); return -1; } I'm appending a patch for inet/rcmd.c which fixes one of the three gethostbyname_r calls and like to get your comments on it before I fix the rest. Andreas #include <netdb.h> #include <stdio.h> #include <alloca.h> int main (void) { struct hostent hostbuf, *hp; size_t hstbuflen; char *tmphstbuf; int res; int herr; hstbuflen = 1024; tmphstbuf = alloca (hstbuflen); res = gethostbyname_r ("unknownhost", &hostbuf, tmphstbuf, hstbuflen, &hp, &herr); printf ("gethostbyname_r returned: %d\n", res); printf ("herr: %d\n", herr); printf ("hp is %s\n", hp == NULL ? "null" : "set"); return res; } --- inet/rcmd.c.~2~ Mon Jun 28 22:36:37 1999 +++ inet/rcmd.c Tue Jun 29 08:21:23 1999 @@ -79,21 +79,22 @@ hstbuflen = 1024; tmphstbuf = __alloca (hstbuflen); - while (__gethostbyname_r (*ahost, &hostbuf, tmphstbuf, hstbuflen, - &hp, &herr) != 0) - if (herr != NETDB_INTERNAL || errno != ERANGE) - { - __set_h_errno (herr); - herror(*ahost); - return -1; - } - else - { - /* Enlarge the buffer. */ - hstbuflen *= 2; - tmphstbuf = __alloca (hstbuflen); - } - + + while ((__gethostbyname_r (*ahost, &hostbuf, tmphstbuf, hstbuflen, + &hp, &herr) != 0) && + (herr == NETDB_INTERNAL) && (errno == ERANGE)) + { + /* Enlarge the buffer. */ + hstbuflen *= 2; + tmphstbuf = __alloca (hstbuflen); + } + if (herr != 0 || hp == NULL) + { + __set_h_errno (herr); + herror(*ahost); + return -1; + } + pfd[0].events = POLLIN; pfd[1].events = POLLIN; -- Andreas Jaeger aj@arthur.rhein-neckar.de jaeger@informatik.uni-kl.de for pgp-key finger ajaeger@aixd1.rhrk.uni-kl.de
Index Nav: | [Date Index] [Subject Index] [Author Index] [Thread Index] | |
---|---|---|
Message Nav: | [Date Prev] [Date Next] | [Thread Prev] [Thread Next] |