1
/* $Cambridge: exim/exim-src/src/host.c,v 1.10 2005/06/22 15:44:38 ph10 Exp $ */
1
3
/*************************************************
2
4
* Exim - an Internet mail transport agent *
3
5
*************************************************/
5
/* Copyright (c) University of Cambridge 1995 - 2004 */
7
/* Copyright (c) University of Cambridge 1995 - 2005 */
6
8
/* See the file NOTICE for conditions of use and distribution. */
8
10
/* Functions for finding hosts, either by gethostbyname(), gethostbyaddr(), or
91
93
/*************************************************
94
* Sort addresses when testing *
95
*************************************************/
97
/* This function is called only when running in the test harness. It sorts a
98
number of multihomed host IP addresses into the order, so as to get
99
repeatability. This doesn't have to be efficient. But don't interchange IPv4
103
host -> the first host item
104
last -> the last host item
110
sort_addresses(host_item *host, host_item *last)
117
for (h = host; h != last; h = h->next)
119
if ((Ustrchr(h->address, ':') == NULL) !=
120
(Ustrchr(h->next->address, ':') == NULL))
122
if (Ustrcmp(h->address, h->next->address) > 0)
124
uschar *temp = h->address;
125
h->address = h->next->address;
126
h->next->address = temp;
135
/*************************************************
92
136
* Build chain of host items from list *
93
137
*************************************************/
325
369
sender_rcvhost[ptr] = 0; /* string_cat() always leaves room */
371
/* Release store, because string_cat allocated a minimum of 100 bytes that
372
are rarely completely used. */
374
store_reset(sender_rcvhost + ptr + 1);
328
377
/* Host name is known and verified. */
394
443
uschar *flag = useflag? US"H=" : US"";
444
uschar *iface = US"";
445
if ((log_extra_selector & LX_incoming_interface) != 0 &&
446
interface_address != NULL)
447
iface = string_sprintf(" I=[%s]:%d", interface_address, interface_port);
395
448
if (sender_ident == NULL)
396
(void)string_format(big_buffer, big_buffer_size, "%s%s",
397
flag, sender_fullhost);
449
(void)string_format(big_buffer, big_buffer_size, "%s%s%s",
450
flag, sender_fullhost, iface);
399
(void)string_format(big_buffer, big_buffer_size, "%s%s U=%s",
400
flag, sender_fullhost, sender_ident);
452
(void)string_format(big_buffer, big_buffer_size, "%s%s%s U=%s",
453
flag, sender_fullhost, iface, sender_ident);
402
455
return big_buffer;
440
493
while ((s = string_nextinlist(&list, &sep, buffer, sizeof(buffer))) != NULL)
442
495
int port = host_extract_port(s); /* Leaves just the IP address */
443
if (!string_is_ip_address(s, NULL))
496
if (string_is_ip_address(s, NULL) == 0)
444
497
log_write(0, LOG_MAIN|LOG_PANIC_DIE, "Malformed IP address \"%s\" in %s",
683
736
int v4offset = 0;
685
/* Handle IPv6 address, which may end with an IPv4 address */
738
/* Handle IPv6 address, which may end with an IPv4 address. It may also end
739
with a "scope", introduced by a percent sign. This code is NOT enclosed in #if
740
HAVE_IPV6 in order that IPv6 addresses are recognized even if IPv6 is not
688
743
if (Ustrchr(address, ':') != NULL)
690
745
uschar *p = address;
701
756
if (*p == ':') p++;
703
/* Split the address into components separated by colons. */
758
/* Split the address into components separated by colons. The input address
759
is supposed to be checked for syntax. There was a case where this was
760
overlooked; to guard against that happening again, check here and crash if
761
there are too many components. */
763
while (*p != 0 && *p != '%')
707
int len = Ustrcspn(p, ":");
765
int len = Ustrcspn(p, ":%");
708
766
if (len == 0) nulloffset = ci;
767
if (ci > 7) log_write(0, LOG_MAIN|LOG_PANIC_DIE,
768
"Internal error: invalid IPv6 address \"%s\" passed to host_aton()",
709
770
component[ci++] = p;
711
772
if (*p == ':') p++;
746
807
if (!ipv4_ends) return 4;
750
810
/* Handle IPv4 address */
752
sscanf(CS address, "%d.%d.%d.%d", x, x+1, x+2, x+3);
812
(void)sscanf(CS address, "%d.%d.%d.%d", x, x+1, x+2, x+3);
753
813
bin[v4offset] = (x[0] << 24) + (x[1] << 16) + (x[2] << 8) + x[3];
754
814
return v4offset+1;
803
863
/* We can't use host_ntoa() because it assumes the binary values are in network
804
864
byte order, and these are the result of host_aton(), which puts them in ints in
805
865
host byte order. Also, we really want IPv6 addresses to be in a canonical
806
format, so we output them with no abbreviation. However, we can't use the
807
normal colon separator in them because it terminates keys in lsearch files, so
866
format, so we output them with no abbreviation. In a number of cases we can't
867
use the normal colon separator in them because it terminates keys in lsearch
868
files, so we want to use dot instead. There's an argument that specifies what
869
to use for IPv6 addresses.
811
872
count 1 or 4 (number of ints)
812
873
binary points to the ints
813
874
mask mask value; if < 0 don't add to result
814
875
buffer big enough to hold the result
876
sep component separator character for IPv6 addresses
816
878
Returns: the number of characters placed in buffer, not counting
821
host_nmtoa(int count, int *binary, int mask, uschar *buffer)
883
host_nmtoa(int count, int *binary, int mask, uschar *buffer, int sep)
824
886
uschar *tt = buffer;
837
899
for (i = 0; i < 4; i++)
840
sprintf(CS tt, "%04x.%04x.", (j >> 16) & 0xffff, j & 0xffff);
902
sprintf(CS tt, "%04x%c%04x%c", (j >> 16) & 0xffff, sep, j & 0xffff, sep);
841
903
while (*tt) tt++;
845
tt--; /* lose final . */
907
tt--; /* lose final separator */
860
922
/*************************************************
923
* Check port for tls_on_connect *
924
*************************************************/
926
/* This function checks whether a given incoming port is configured for tls-
927
on-connect. It is called from the daemon and from inetd handling. If the global
928
option tls_on_connect is already set, all ports operate this way. Otherwise, we
929
check the tls_on_connect_ports option for a list of ports.
931
Argument: a port number
932
Returns: TRUE or FALSE
936
host_is_tls_on_connect_port(int port)
940
uschar *list = tls_on_connect_ports;
943
if (tls_on_connect) return TRUE;
945
while ((s = string_nextinlist(&list, &sep, buffer, sizeof(buffer))) != NULL)
948
int lport = Ustrtol(s, &end, 10);
949
if (*end != 0) log_write(0, LOG_MAIN|LOG_PANIC_DIE, "tls_on_connect_ports "
950
"contains \"%s\", which is not a port number: exim abandoned", s);
951
if (lport == port) return TRUE;
959
/*************************************************
861
960
* Check whether host is in a network *
862
961
*************************************************/
1238
1337
The variable host_lookup_msg is set to an empty string on sucess, or to a
1239
1338
reason for the failure otherwise, in a form suitable for tagging onto an error
1240
message, and also host_lookup_failed is set TRUE if the lookup failed. Any
1241
dynamically constructed string for host_lookup_msg must be in permanent store,
1242
because it might be used for several incoming messages on the same SMTP
1339
message, and also host_lookup_failed is set TRUE if the lookup failed. If there
1340
was a defer, host_lookup_deferred is set TRUE.
1342
Any dynamically constructed string for host_lookup_msg must be in permanent
1343
store, because it might be used for several incoming messages on the same SMTP
1367
1472
HDEBUG(D_host_lookup)
1368
1473
debug_printf("IP address lookup using gethostbyaddr()\n");
1370
1474
rc = host_name_lookup_byaddr();
1371
if (rc == DEFER) return rc; /* Can't carry on */
1477
host_lookup_deferred = TRUE;
1478
return rc; /* Can't carry on */
1372
1480
if (rc == OK) break; /* Found a name */
1374
1482
} /* Loop for bydns/byaddr scanning */
1382
1490
log_write(L_host_lookup_failed, LOG_MAIN, "no host name found for IP "
1383
1491
"address %s", sender_host_address);
1384
1492
host_lookup_msg = US" (failed to find host name from IP address)";
1386
host_lookup_failed = TRUE;
1493
host_lookup_failed = TRUE;
1565
1672
uschar **addrlist;
1566
1673
host_item *last = NULL;
1567
1674
BOOL temp_error = FALSE;
1679
/* If we are in the test harness, a name ending in .test.again.dns always
1680
forces a temporary error response. */
1682
if (running_in_test_harness)
1684
uschar *endname = host->name + Ustrlen(host->name);
1685
if (Ustrcmp(endname - 14, "test.again.dns") == 0)
1686
return HOST_FIND_AGAIN;
1569
1689
/* In an IPv6 world, we need to scan for both kinds of address, so go round the
1570
1690
loop twice. Note that we have ensured that AF_INET6 is defined even in an IPv4
1573
1693
standalone). */
1578
1696
#ifndef STAND_ALONE
1579
1697
if (dns_ipv4_lookup != NULL &&
1580
1698
match_isinlist(host->name, &dns_ipv4_lookup, 0, NULL, NULL, MCL_DOMAIN,
1743
1861
host_scan_for_local_hosts(host, &last, NULL) : HOST_FOUND;
1745
1863
/* When running in the test harness, sort into the order of addresses so as to
1746
get repeatability. This doesn't have to be efficient. But don't interchange
1747
IPv4 and IPv6 addresses! */
1864
get repeatability. */
1749
if (running_in_test_harness)
1756
for (h = host; h != last; h = h->next)
1758
if ((Ustrchr(h->address, ':') == NULL) !=
1759
(Ustrchr(h->next->address, ':') == NULL))
1761
if (Ustrcmp(h->address, h->next->address) > 0)
1763
uschar *temp = h->address;
1764
h->address = h->next->address;
1765
h->next->address = temp;
1866
if (running_in_test_harness) sort_addresses(host, last);
1772
1868
HDEBUG(D_host_lookup)
2066
2162
HOST_FIND_BY_SRV => look for SRV
2067
2163
HOST_FIND_BY_MX => look for MX
2068
2164
HOST_FIND_BY_A => look for A or AAAA
2165
also flags indicating how the lookup is done
2166
HOST_FIND_QUALIFY_SINGLE ) passed to the
2167
HOST_FIND_SEARCH_PARENTS ) resolver
2069
2168
srv_service when SRV used, the service name
2070
qualify_single if TRUE, ask DNS to qualify single-component names
2071
search_parents if TRUE, asd DNS to search parent domains
2169
srv_fail_domains DNS errors for these domains => assume nonexist
2170
mx_fail_domains DNS errors for these domains => assume nonexist
2072
2171
fully_qualified_name if not NULL, return fully-qualified name
2073
2172
removed set TRUE if local host was removed from the list
2087
2186
host_find_bydns(host_item *host, uschar *ignore_target_hosts, int whichrrs,
2088
uschar *srv_service, BOOL qualify_single, BOOL search_parents,
2187
uschar *srv_service, uschar *srv_fail_domains, uschar *mx_fail_domains,
2089
2188
uschar **fully_qualified_name, BOOL *removed)
2091
2190
host_item *h, *last;
2101
2200
that gets set for DNS syntax check errors. */
2103
2202
if (fully_qualified_name != NULL) *fully_qualified_name = host->name;
2104
dns_init(qualify_single, search_parents);
2203
dns_init((whichrrs & HOST_FIND_QUALIFY_SINGLE) != 0,
2204
(whichrrs & HOST_FIND_SEARCH_PARENTS) != 0);
2105
2205
host_find_failed_syntax = FALSE;
2107
2207
/* First, if requested, look for SRV records. The service name is given; we
2126
2226
if (temp_fully_qualified_name != buffer && fully_qualified_name != NULL)
2127
2227
*fully_qualified_name = temp_fully_qualified_name + prefix_length;
2129
if (rc == DNS_FAIL || rc == DNS_AGAIN) return HOST_FIND_AGAIN;
2229
/* On DNS failures, we give the "try again" error unless the domain is
2230
listed as one for which we continue. */
2232
if (rc == DNS_FAIL || rc == DNS_AGAIN)
2234
if (match_isinlist(host->name, &srv_fail_domains, 0, NULL, NULL, MCL_DOMAIN,
2236
return HOST_FIND_AGAIN;
2237
DEBUG(D_host_lookup) debug_printf("DNS_%s treated as DNS_NODATA "
2238
"(domain in srv_fail_domains)\n", (rc == DNS_FAIL)? "FAIL":"AGAIN");
2132
2242
/* If we did not find any SRV records, search the DNS for MX records, if
2133
2243
requested to do so. If the result is DNS_NOMATCH, it means there is no such
2134
2244
domain, and there's no point in going on to look for address records with the
2135
2245
same domain. The result will be DNS_NODATA if the domain exists but has no MX
2246
records. On DNS failures, we give the "try again" error unless the domain is
2247
listed as one for which we continue. */
2138
2249
if (rc != DNS_SUCCEED && (whichrrs & HOST_FIND_BY_MX) != 0)
2140
2251
ind_type = T_MX;
2141
2252
rc = dns_lookup(&dnsa, host->name, ind_type, fully_qualified_name);
2142
if (rc == DNS_FAIL || rc == DNS_AGAIN) return HOST_FIND_AGAIN;
2143
2253
if (rc == DNS_NOMATCH) return HOST_FIND_FAILED;
2254
if (rc == DNS_FAIL || rc == DNS_AGAIN)
2256
if (match_isinlist(host->name, &mx_fail_domains, 0, NULL, NULL, MCL_DOMAIN,
2258
return HOST_FIND_AGAIN;
2259
DEBUG(D_host_lookup) debug_printf("DNS_%s treated as DNS_NODATA "
2260
"(domain in mx_fail_domains)\n", (rc == DNS_FAIL)? "FAIL":"AGAIN");
2146
2264
/* If we haven't found anything yet, and we are requested to do so, try for an
2173
2291
if (rc == HOST_IGNORED) rc = HOST_FIND_FAILED; /* No special action */
2293
/* When running in the test harness, sort into the order of addresses so as
2294
to get repeatability. */
2296
if (running_in_test_harness) sort_addresses(host, last);
2175
2298
DEBUG(D_host_lookup)
2846
2969
else if (Ustrcmp(buffer, "no_search_parents") == 0) search_parents = FALSE;
2847
2970
else if (Ustrncmp(buffer, "retrans", 7) == 0)
2849
sscanf(CS(buffer+8), "%d", &dns_retrans);
2972
(void)sscanf(CS(buffer+8), "%d", &dns_retrans);
2850
2973
_res.retrans = dns_retrans;
2852
2975
else if (Ustrncmp(buffer, "retry", 5) == 0)
2854
sscanf(CS(buffer+6), "%d", &dns_retry);
2977
(void)sscanf(CS(buffer+6), "%d", &dns_retry);
2855
2978
_res.retry = dns_retry;
2857
2980
else if (alldigits(buffer))
2870
2995
h.why = hwhy_unknown;
2871
2996
h.address = NULL;
2998
if (qualify_single) flags |= HOST_FIND_QUALIFY_SINGLE;
2999
if (search_parents) flags |= HOST_FIND_SEARCH_PARENTS;
2874
3002
host_find_byname(&h, NULL, &fully_qualified_name, TRUE)
2876
host_find_bydns(&h, NULL, whichrrs, US"smtp", qualify_single,
2877
search_parents, &fully_qualified_name, NULL);
3004
host_find_bydns(&h, NULL, flags, US"smtp", NULL, NULL,
3005
&fully_qualified_name, NULL);
2879
3007
if (rc == HOST_FIND_FAILED) printf("Failed\n");
2880
3008
else if (rc == HOST_FIND_AGAIN) printf("Again\n");