From: Michael Elkins Date: Wed, 10 Apr 2013 23:40:18 +0000 (+0000) Subject: use gethostname() to determine the system host name X-Git-Tag: neomutt-20160307~166 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=8aaad6372ec24425e1c157f9153779d5f8216ee0;p=neomutt use gethostname() to determine the system host name use getaddrinfo() to look up canonical DNS name, and fall back to hinting from /etc/resolv.conf see #3298 --- diff --git a/getdomain.c b/getdomain.c index 71636279c..13c4fa257 100644 --- a/getdomain.c +++ b/getdomain.c @@ -6,6 +6,10 @@ #include #include +/* for getaddrinfo() */ +#include +#include + #include "mutt.h" #ifndef STDC_HEADERS @@ -29,40 +33,63 @@ static void strip_trailing_dot (char *q) int getdnsdomainname (char *s, size_t l) { +#ifdef DOMAIN + /* specified at compile time */ + snprintf(s, l, "%s.%s", Hostname, DOMAIN); +#else FILE *f; char tmp[1024]; char *p = NULL; char *q; + struct addrinfo hints; + struct addrinfo *res; - if ((f = fopen ("/etc/resolv.conf", "r")) == NULL) return (-1); + /* Try a DNS lookup on the hostname to find the canonical name. */ + memset(&hints, 0, sizeof(hints)); + hints.ai_flags = AI_CANONNAME; + if (getaddrinfo(Hostname, NULL, &hints, &res) == 0) + { + snprintf(s, l, "%s", res->ai_canonname); + freeaddrinfo(res); + } + else + { + /* Otherwise inspect /etc/resolve.conf for a hint. */ - tmp[sizeof (tmp) - 1] = 0; + if ((f = fopen ("/etc/resolv.conf", "r")) == NULL) return (-1); - l--; /* save room for the terminal \0 */ + tmp[sizeof (tmp) - 1] = 0; - while (fgets (tmp, sizeof (tmp) - 1, f) != NULL) - { - p = tmp; - while (ISSPACE (*p)) p++; - if (mutt_strncmp ("domain", p, 6) == 0 || mutt_strncmp ("search", p, 6) == 0) - { - p += 6; - - for (q = strtok (p, " \t\n"); q; q = strtok (NULL, " \t\n")) - if (strcmp (q, ".")) - break; + l--; /* save room for the terminal \0 */ - if (q) + while (fgets (tmp, sizeof (tmp) - 1, f) != NULL) + { + p = tmp; + while (ISSPACE (*p)) p++; + if (mutt_strncmp ("domain", p, 6) == 0 || mutt_strncmp ("search", p, 6) == 0) { - strip_trailing_dot (q); - strfcpy (s, q, l); - safe_fclose (&f); - return 0; + p += 6; + + for (q = strtok (p, " \t\n"); q; q = strtok (NULL, " \t\n")) + if (strcmp (q, ".")) + break; + + if (q) + { + strip_trailing_dot (q); + snprintf (s, l, "%s.%s", Hostname, q); + safe_fclose (&f); + return 0; + } + } - } - } - safe_fclose (&f); - return (-1); + safe_fclose (&f); + + /* fall back to using just the bare hostname */ + snprintf(s, l, "%s", Hostname); + } +#endif + return 0; } diff --git a/init.c b/init.c index 0cc362b75..9fcd53f28 100644 --- a/init.c +++ b/init.c @@ -2887,7 +2887,6 @@ static void mutt_srandom (void) void mutt_init (int skip_sys_rc, LIST *commands) { struct passwd *pw; - struct utsname utsname; char *p, buffer[STRING]; int i, default_rc = 0, need_pause = 0; BUFFER err; @@ -2953,30 +2952,21 @@ void mutt_init (int skip_sys_rc, LIST *commands) #endif /* And about the host... */ - uname (&utsname); - /* some systems report the FQDN instead of just the hostname */ - if ((p = strchr (utsname.nodename, '.'))) { - Hostname = mutt_substrdup (utsname.nodename, p); - p++; - strfcpy (buffer, p, sizeof (buffer)); /* save the domain for below */ + size_t namelen = sysconf(_SC_HOST_NAME_MAX); + char *name = safe_malloc(namelen + 1); + if (gethostname(name, namelen) == -1) + { + fputs (_("unable to determine hostname"), stderr); + exit (1); + } + Hostname = safe_strdup(name); + FREE (&name); } - else - Hostname = safe_strdup (utsname.nodename); -#ifndef DOMAIN -#define DOMAIN buffer - if (!p && getdnsdomainname (buffer, sizeof (buffer)) == -1) - Fqdn = safe_strdup ("@"); - else -#endif /* DOMAIN */ - if (*DOMAIN != '@') - { - Fqdn = safe_malloc (mutt_strlen (DOMAIN) + mutt_strlen (Hostname) + 2); - sprintf (Fqdn, "%s.%s", NONULL(Hostname), DOMAIN); /* __SPRINTF_CHECKED__ */ - } - else - Fqdn = safe_strdup(NONULL(Hostname)); + /* determine the DNS domain name */ + getdnsdomainname (buffer, sizeof (buffer)); + Fqdn = safe_strdup(buffer); if ((p = getenv ("MAIL"))) Spoolfile = safe_strdup (p);