From: Roy Marples Date: Thu, 26 Apr 2007 16:16:56 +0000 (+0000) Subject: Send a FQDN hostname if it contains dots, strip the domain from a looked up hostname... X-Git-Tag: v3.2.3~270 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=0731074b52e211799a419ce90462562643b4f658;p=thirdparty%2Fdhcpcd.git Send a FQDN hostname if it contains dots, strip the domain from a looked up hostname if it matches our domain or search and sanitize our fd's a little better. --- diff --git a/ChangeLog b/ChangeLog index 8dbd7126..53a333af 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,4 @@ +If the current hostname contains dots then send it as a FQDN. Ensure that static routes are always added before routers. Use getnameinfo instead of gethostbyaddr. Remove gateways from the ROUTES and add to GATEWAYS diff --git a/Makefile b/Makefile index 265bece0..93127ca4 100644 --- a/Makefile +++ b/Makefile @@ -1,4 +1,4 @@ -VERSION = 3.0.18_pre1 +VERSION = 3.0.18_pre2 CFLAGS ?= -O2 -pipe # Should work for both GNU make and BSD make diff --git a/arp.c b/arp.c index 9a54453e..0828ec1c 100644 --- a/arp.c +++ b/arp.c @@ -51,6 +51,9 @@ (ap)->ar_hln + (ap)->ar_pln) #define ar_tpa(ap) (((unsigned char *) ((ap) + 1)) + \ 2 * (ap)->ar_hln + (ap)->ar_pln) +#endif + +#ifndef arphdr_len #define arphdr_len2(ar_hln, ar_pln) (sizeof (struct arphdr) + \ 2 * (ar_hln) + 2 * (ar_pln)) #define arphdr_len(ap) (arphdr_len2 ((ap)->ar_hln, (ap)->ar_pln)) diff --git a/client.c b/client.c index 1aa8a88e..adf4b3d3 100644 --- a/client.c +++ b/client.c @@ -94,6 +94,7 @@ static int daemonise (const char *pidfile) { logger (LOG_DEBUG, "forking to background"); + if (daemon (0, 0) < 0) { logger (LOG_ERR, "daemon: %s", strerror (errno)); return -1; diff --git a/common.c b/common.c index bbddf3cd..c609abaa 100644 --- a/common.c +++ b/common.c @@ -104,6 +104,20 @@ void *xmalloc (size_t size) return value; logger (LOG_ERR, "memory exhausted"); - exit (1); + exit (EXIT_FAILURE); +} + +char *xstrdup (const char *str) +{ + char *value; + + if (! str) + return (NULL); + + if ((value = strdup (str))) + return (value); + + logger (LOG_ERR, "memory exhausted"); + exit (EXIT_FAILURE); } diff --git a/common.h b/common.h index 30a2781d..da2962cb 100644 --- a/common.h +++ b/common.h @@ -34,6 +34,6 @@ size_t strlcpy (char *dst, const char *src, size_t size); long uptime (void); void *xmalloc (size_t size); - +char *xstrdup (const char *str); #endif diff --git a/configure.c b/configure.c index 20794b2c..1904a242 100644 --- a/configure.c +++ b/configure.c @@ -661,8 +661,8 @@ int configure (const options_t *options, interface_t *iface, make_nis(iface->name, dhcp); #endif - /* Now we have made a resolv.conf we can obtain a hostname if we need one */ - if (options->dohostname && ! dhcp->hostname) { + /* Now we have made a resolv.conf we can obtain a hostname if we need it */ + if (options->dohostname && ! dhcp->hostname) { union { struct sockaddr sa; struct sockaddr_in sin; @@ -670,33 +670,55 @@ int configure (const options_t *options, interface_t *iface, socklen_t salen; char addr[NI_MAXHOST]; struct addrinfo hints, *res; + int result; salen = sizeof (struct sockaddr); memset (&su.sa, 0, salen); su.sin.sin_family = AF_INET; memcpy (&su.sin.sin_addr, &dhcp->address, sizeof (struct in_addr)); - if (getnameinfo (&su.sa, salen, addr, sizeof (addr), - NULL, 0, NI_NAMEREQD) == 0) { + logger (LOG_DEBUG, "Looking up hostname via DNS"); + if ((result = getnameinfo (&su.sa, salen, addr, sizeof (addr), + NULL, 0, NI_NAMEREQD)) != 0) + logger (LOG_ERR, "Failed to lookup hostname via DNS: %s", gai_strerror (result)); + else { + /* Check for a malicious PTR record */ memset (&hints, 0, sizeof (hints)); hints.ai_socktype = SOCK_DGRAM; hints.ai_flags = AI_NUMERICHOST; - /* Check for a malicious PTR record */ if (getaddrinfo (addr, "0", &hints, &res) == 0) { freeaddrinfo (res); addr[0] = '\0'; logger (LOG_ERR, "malicious PTR record detected"); + } else if (*addr) { + /* Strip out the domain if it matches */ + char *p = addr; + char *token = strsep (&p, "."); + bool match_domain = false; + + if (p && *p) { + if (dhcp->dnssearch) { + char *s = xstrdup (dhcp->dnssearch); + char *sp = s; + char *t; + + while ((t = strsep (&sp, " "))) + if (strcmp (t, p) == 0) { + match_domain = true; + break; + } + free (s); + } else if (dhcp->dnsdomain) { + if (strcmp (dhcp->dnsdomain, p) == 0) + match_domain = true; + } + } + if (match_domain) + strlcpy (newhostname, token, sizeof (newhostname)); + else + snprintf (newhostname, sizeof (newhostname), "%s.%s", token, p); } } - - /* Split the hostname from the domain */ - if (addr[0]) { - char *p = addr; - char *token = strsep (&p, "."); - if (token) - strlcpy (newhostname, token, sizeof (newhostname)); - } else - logger (LOG_ERR, "failed to lookup the hostname"); } gethostname (curhostname, sizeof (curhostname)); diff --git a/dhcpcd.c b/dhcpcd.c index 7c87d54e..2a952e6b 100644 --- a/dhcpcd.c +++ b/dhcpcd.c @@ -109,6 +109,7 @@ int main(int argc, char **argv) char prefix[IF_NAMESIZE + 3]; pid_t pid; int debug = 0; + int i; const struct option longopts[] = { {"arp", no_argument, NULL, 'a'}, @@ -137,13 +138,9 @@ int main(int argc, char **argv) {NULL, 0, NULL, 0} }; - /* Sanitize our fd's */ - int zero; - if ((zero = open (_PATH_DEVNULL, O_RDWR, 0)) >= 0) { - while (zero < 3) - zero = dup (zero); - close(zero); - } + /* Close any un-needed fd's */ + for (i = getdtablesize() - 1; i >= 3; --i) + close (i); openlog (PACKAGE, LOG_PID, LOG_LOCAL0); @@ -158,10 +155,6 @@ int main(int argc, char **argv) options.dontp = true; options.dogateway = true; options.daemonise = true; - gethostname (options.hostname, sizeof (options.hostname)); - if (strcmp (options.hostname, "(none)") == 0 || - strcmp (options.hostname, "localhost") == 0) - memset (options.hostname, 0, sizeof (options.hostname)); options.timeout = DEFAULT_TIMEOUT; while ((ch = getopt_long(argc, argv, "ac:dh:i:kl:m:nps:t:u:F:GHI:MNRY", longopts, @@ -242,7 +235,6 @@ int main(int argc, char **argv) break; case 'u': { - int i; int offset = 0; for (i = 0; i < userclasses; i++) offset += (int) options.userclass[offset] + 1; @@ -258,11 +250,11 @@ int main(int argc, char **argv) } break; case 'F': - if (strcmp (optarg, "none") == 0) + if (strncmp (optarg, "none", strlen (optarg)) == 0) options.fqdn = FQDN_NONE; - else if (strcmp (optarg, "ptr") == 0) + else if (strncmp (optarg, "ptr", strlen (optarg)) == 0) options.fqdn = FQDN_PTR; - else if (strcmp (optarg, "both") == 0) + else if (strncmp (optarg, "both", strlen (optarg)) == 0) options.fqdn = FQDN_BOTH; else { logger (LOG_ERR, "invalid value `%s' for FQDN", optarg); @@ -326,6 +318,19 @@ int main(int argc, char **argv) exit (EXIT_FAILURE); } + /* If we are given a hostname use it and set FQDN if it contains a . */ + if (! options.hostname[0]) { + gethostname (options.hostname, sizeof (options.hostname)); + if (strcmp (options.hostname, "(none)") == 0 || + strcmp (options.hostname, "localhost") == 0) + memset (options.hostname, 0, sizeof (options.hostname)); + } + if (strchr (options.hostname, '.')) { + if (options.fqdn == FQDN_DISABLE) + options.fqdn = FQDN_BOTH; + } else + options.fqdn = FQDN_DISABLE; + if (geteuid ()) { logger (LOG_ERR, "you need to be root to run "PACKAGE); exit (EXIT_FAILURE); diff --git a/interface.c b/interface.c index 9494c715..ffee7444 100644 --- a/interface.c +++ b/interface.c @@ -407,7 +407,7 @@ static int do_route (const char *ifname, /* Do something with metric to satisfy compiler warnings */ metric = 0; - dstd = strdup (inet_ntoa (destination)); + dstd = xstrdup (inet_ntoa (destination)); if (gateway.s_addr == destination.s_addr) logger (LOG_INFO, "%s route to %s/%d", change ? "changing" : del ? "removing" : "adding", @@ -738,8 +738,8 @@ static int do_route (const char *ifname, if (! ifname) return -1; - dstd = strdup (inet_ntoa (destination)); - gend = strdup (inet_ntoa (netmask)); + dstd = xstrdup (inet_ntoa (destination)); + gend = xstrdup (inet_ntoa (netmask)); if (gateway.s_addr == destination.s_addr) logger (LOG_INFO, "%s route to %s (%s) metric %d", change ? "changing" : del ? "removing" : "adding", diff --git a/logger.c b/logger.c index 0fe75174..26634431 100644 --- a/logger.c +++ b/logger.c @@ -91,6 +91,10 @@ void logger(int level, const char *fmt, ...) fprintf (f, "%s, %s", syslog_level_msg[level], logprefix); vfprintf (f, fmt, p); fputc ('\n', f); + + /* stdout, stderr may be re-directed to some kind of buffer. + * So we always flush to ensure it's written. */ + fflush (f); } if (level < LOG_DEBUG || level <= loglevel) { diff --git a/socket.c b/socket.c index 1428e3bd..860a98b4 100644 --- a/socket.c +++ b/socket.c @@ -24,6 +24,7 @@ #include #include #include +#include #include #include #ifndef __OpenBSD__ @@ -32,10 +33,6 @@ #include #endif #include -#ifndef __linux__ -#include -#endif -#include #include #include #include