diff options
Diffstat (limited to 'src/lib/libc')
| -rw-r--r-- | src/lib/libc/net/gethostnamadr.c | 64 |
1 files changed, 50 insertions, 14 deletions
diff --git a/src/lib/libc/net/gethostnamadr.c b/src/lib/libc/net/gethostnamadr.c index 62e14693a4..29fbedc594 100644 --- a/src/lib/libc/net/gethostnamadr.c +++ b/src/lib/libc/net/gethostnamadr.c | |||
| @@ -52,7 +52,7 @@ | |||
| 52 | */ | 52 | */ |
| 53 | 53 | ||
| 54 | #if defined(LIBC_SCCS) && !defined(lint) | 54 | #if defined(LIBC_SCCS) && !defined(lint) |
| 55 | static char rcsid[] = "$OpenBSD: gethostnamadr.c,v 1.8 1996/09/15 10:09:12 tholo Exp $"; | 55 | static char rcsid[] = "$OpenBSD: gethostnamadr.c,v 1.9 1996/09/26 09:13:21 deraadt Exp $"; |
| 56 | #endif /* LIBC_SCCS and not lint */ | 56 | #endif /* LIBC_SCCS and not lint */ |
| 57 | 57 | ||
| 58 | #include <sys/param.h> | 58 | #include <sys/param.h> |
| @@ -101,15 +101,40 @@ typedef union { | |||
| 101 | } querybuf; | 101 | } querybuf; |
| 102 | 102 | ||
| 103 | typedef union { | 103 | typedef union { |
| 104 | int32_t al; | 104 | int32_t al; |
| 105 | char ac; | 105 | char ac; |
| 106 | } align; | 106 | } align; |
| 107 | 107 | ||
| 108 | static int qcomp __P((struct in_addr **, struct in_addr **)); | 108 | static int qcomp __P((struct in_addr **, struct in_addr **)); |
| 109 | static struct hostent *getanswer __P((querybuf *, int, int)); | 109 | static struct hostent *getanswer __P((querybuf *, int, int)); |
| 110 | static int hbadchar __P((char *)); | ||
| 110 | 111 | ||
| 111 | extern int h_errno; | 112 | extern int h_errno; |
| 112 | 113 | ||
| 114 | static int | ||
| 115 | hbadchar(p) | ||
| 116 | char *p; | ||
| 117 | { | ||
| 118 | char c; | ||
| 119 | |||
| 120 | /* | ||
| 121 | * Many people do not obey RFC 822 and 1035. The valid | ||
| 122 | * characters are a-z, A-Z, 0-9, '-' and . But the others | ||
| 123 | * tested for below can happen, and we must be more permissive | ||
| 124 | * until those idiots clean up their act. | ||
| 125 | */ | ||
| 126 | while ((c = *p++)) { | ||
| 127 | if (('a' >= c && c <= 'z') || | ||
| 128 | ('A' >= c && c <= 'Z') || | ||
| 129 | ('0' >= c && c <= '9')) | ||
| 130 | continue; | ||
| 131 | if (strchr("-_/.[]\\", c) || | ||
| 132 | (c == '.' && p[1] == '.')) | ||
| 133 | return 1; | ||
| 134 | } | ||
| 135 | return 0; | ||
| 136 | } | ||
| 137 | |||
| 113 | static struct hostent * | 138 | static struct hostent * |
| 114 | getanswer(answer, anslen, iquery) | 139 | getanswer(answer, anslen, iquery) |
| 115 | querybuf *answer; | 140 | querybuf *answer; |
| @@ -124,6 +149,7 @@ getanswer(answer, anslen, iquery) | |||
| 124 | int type, class, buflen, ancount, qdcount; | 149 | int type, class, buflen, ancount, qdcount; |
| 125 | int haveanswer, getclass = C_ANY; | 150 | int haveanswer, getclass = C_ANY; |
| 126 | char **hap; | 151 | char **hap; |
| 152 | int good = 1; | ||
| 127 | 153 | ||
| 128 | eom = answer->buf + anslen; | 154 | eom = answer->buf + anslen; |
| 129 | /* | 155 | /* |
| @@ -200,7 +226,7 @@ getanswer(answer, anslen, iquery) | |||
| 200 | n = strlen(host.h_name); | 226 | n = strlen(host.h_name); |
| 201 | if (n >= MAXHOSTNAMELEN) | 227 | if (n >= MAXHOSTNAMELEN) |
| 202 | host.h_name[MAXHOSTNAMELEN-1] = '\0'; | 228 | host.h_name[MAXHOSTNAMELEN-1] = '\0'; |
| 203 | return(&host); | 229 | goto gotent; |
| 204 | } | 230 | } |
| 205 | if (iquery || type != T_A) { | 231 | if (iquery || type != T_A) { |
| 206 | #ifdef DEBUG | 232 | #ifdef DEBUG |
| @@ -224,6 +250,8 @@ getanswer(answer, anslen, iquery) | |||
| 224 | host.h_length = n; | 250 | host.h_length = n; |
| 225 | getclass = class; | 251 | getclass = class; |
| 226 | host.h_addrtype = (class == C_IN) ? AF_INET : AF_UNSPEC; | 252 | host.h_addrtype = (class == C_IN) ? AF_INET : AF_UNSPEC; |
| 253 | if (host.h_addrtype == AF_INET) | ||
| 254 | host.h_length = sizeof(struct in_addr); | ||
| 227 | if (!iquery) { | 255 | if (!iquery) { |
| 228 | host.h_name = bp; | 256 | host.h_name = bp; |
| 229 | if (strlen(bp) >= MAXHOSTNAMELEN) | 257 | if (strlen(bp) >= MAXHOSTNAMELEN) |
| @@ -248,19 +276,27 @@ getanswer(answer, anslen, iquery) | |||
| 248 | cp += n; | 276 | cp += n; |
| 249 | haveanswer++; | 277 | haveanswer++; |
| 250 | } | 278 | } |
| 251 | if (haveanswer) { | 279 | if (!haveanswer) { |
| 252 | *ap = NULL; | ||
| 253 | *hap = NULL; | ||
| 254 | if (_res.nsort) { | ||
| 255 | qsort(host.h_addr_list, haveanswer, | ||
| 256 | sizeof(struct in_addr), | ||
| 257 | (int (*)__P((const void *, const void *)))qcomp); | ||
| 258 | } | ||
| 259 | return (&host); | ||
| 260 | } else { | ||
| 261 | h_errno = TRY_AGAIN; | 280 | h_errno = TRY_AGAIN; |
| 262 | return ((struct hostent *) NULL); | 281 | return ((struct hostent *) NULL); |
| 263 | } | 282 | } |
| 283 | *ap = NULL; | ||
| 284 | *hap = NULL; | ||
| 285 | if (_res.nsort) { | ||
| 286 | qsort(host.h_addr_list, haveanswer, | ||
| 287 | sizeof(struct in_addr), | ||
| 288 | (int (*)__P((const void *, const void *)))qcomp); | ||
| 289 | } | ||
| 290 | gotent: | ||
| 291 | if (hbadchar(host.h_name)) | ||
| 292 | good = 0; | ||
| 293 | for (ap = host_aliases; good && *ap; ap++) | ||
| 294 | if (hbadchar(*ap)) | ||
| 295 | good = 0; | ||
| 296 | if (good) | ||
| 297 | return (&host); | ||
| 298 | h_errno = NO_RECOVERY; | ||
| 299 | return ((struct hostent *) NULL); | ||
| 264 | } | 300 | } |
| 265 | 301 | ||
| 266 | struct hostent * | 302 | struct hostent * |
