summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authoreric <eric@openbsd.org>2012-08-21 15:14:40 +0000
committereric <eric@openbsd.org>2012-08-21 15:14:40 +0000
commitfff8492961d71016e7ac0404bf724c8b2c6b77c5 (patch)
treed6b599a490f75a19c8d60e6842db8246d4a9fe8c
parentAdd NOPIE= bits for sys/arch/*/stand to ensure that bootblocks will always be (diff)
downloadwireguard-openbsd-fff8492961d71016e7ac0404bf724c8b2c6b77c5.tar.xz
wireguard-openbsd-fff8492961d71016e7ac0404bf724c8b2c6b77c5.zip
Use TAILQ rather than array for mx list.
ok gilles@
-rw-r--r--usr.sbin/smtpd/dns.c73
1 files changed, 44 insertions, 29 deletions
diff --git a/usr.sbin/smtpd/dns.c b/usr.sbin/smtpd/dns.c
index 0349e0e31e0..94e17990357 100644
--- a/usr.sbin/smtpd/dns.c
+++ b/usr.sbin/smtpd/dns.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: dns.c,v 1.54 2012/08/21 14:00:59 eric Exp $ */
+/* $OpenBSD: dns.c,v 1.55 2012/08/21 15:14:40 eric Exp $ */
/*
* Copyright (c) 2008 Gilles Chehade <gilles@openbsd.org>
@@ -41,8 +41,9 @@
struct mx {
- char host[MAXHOSTNAMELEN];
- int prio;
+ TAILQ_ENTRY(mx) entry;
+ char *host;
+ int preference;
};
struct dnssession {
@@ -50,10 +51,9 @@ struct dnssession {
struct dns query;
struct event ev;
struct async *as;
- struct mx mxarray[MAX_MX_COUNT];
- size_t mxarraysz;
- size_t mxcurrent;
+
size_t mxfound;
+ TAILQ_HEAD(, mx) mx;
};
static struct dnssession *dnssession_init(struct dns *);
@@ -138,6 +138,7 @@ dns_async(struct imsgev *asker, int type, struct dns *query)
}
dnssession_mx_insert(s, query->host, 0);
stat_increment("lka.session.host");
+ query->error = DNS_ENOTFOUND; /* override later */
dns_asr_dispatch_host(s);
return;
case IMSG_DNS_PTR:
@@ -269,6 +270,7 @@ dns_asr_dispatch_mx(struct dnssession *s)
*/
s->as = NULL;
s->query.type = IMSG_DNS_HOST;
+ s->query.error = DNS_ENOTFOUND; /* override later */
dns_asr_dispatch_host(s);
}
@@ -280,14 +282,12 @@ dns_asr_dispatch_host(struct dnssession *s)
struct async_res ar;
struct addrinfo hints, *ai;
- /* default to notfound, override with retry or ok later */
- if (s->mxcurrent == 0)
- query->error = DNS_ENOTFOUND;
-
next:
/* query all listed hosts in turn */
while (s->as == NULL) {
- if (s->mxcurrent == s->mxarraysz) {
+
+ mx = TAILQ_FIRST(&s->mx);
+ if (mx == NULL) {
if (s->mxfound)
query->error = DNS_OK;
dns_reply(query, IMSG_DNS_HOST_END);
@@ -295,11 +295,15 @@ next:
return;
}
- mx = s->mxarray + s->mxcurrent++;
+ log_debug("dns: resolving address for \"%s\"", mx->host);
+
memset(&hints, 0, sizeof(hints));
- hints.ai_family = PF_UNSPEC;
- hints.ai_socktype = SOCK_STREAM;
+ hints.ai_family = PF_UNSPEC;
+ hints.ai_socktype = SOCK_STREAM;
s->as = getaddrinfo_async(mx->host, NULL, &hints, NULL);
+ TAILQ_REMOVE(&s->mx, mx, entry);
+ free(mx->host);
+ free(mx);
}
if (async_run(s->as, &ar) == ASYNC_COND) {
@@ -310,6 +314,7 @@ next:
if (ar.ar_gai_errno == 0) {
for (ai = ar.ar_addrinfo; ai; ai = ai->ai_next) {
memcpy(&query->ss, ai->ai_addr, ai->ai_addrlen);
+ log_debug("dns: got address %s", ss_to_text(&query->ss));
dns_reply(query, IMSG_DNS_HOST);
s->mxfound++;
}
@@ -350,36 +355,46 @@ dnssession_init(struct dns *query)
s->id = query->id;
s->query = *query;
+
+ TAILQ_INIT(&s->mx);
+
return (s);
}
static void
dnssession_destroy(struct dnssession *s)
{
+ struct mx *mx;
+
stat_decrement("lka.session");
event_del(&s->ev);
+
+ while((mx = TAILQ_FIRST(&s->mx))) {
+ TAILQ_REMOVE(&s->mx, mx, entry);
+ free(mx->host);
+ free(mx);
+ }
+
free(s);
}
static void
-dnssession_mx_insert(struct dnssession *s, const char *host, int prio)
+dnssession_mx_insert(struct dnssession *s, const char *host, int preference)
{
- size_t i, j;
-
- for (i = 0; i < s->mxarraysz; i++)
- if (prio < s->mxarray[i].prio)
- break;
+ struct mx *mx, *e;
- if (i == MAX_MX_COUNT)
- return;
+ mx = xcalloc(1, sizeof *mx, "dnssession_mx_insert");
+ mx->host = xstrdup(host, "dnssession_mx_insert");
+ mx->preference = preference;
- if (s->mxarraysz < MAX_MX_COUNT)
- s->mxarraysz++;
+ log_debug("dns: found mx \"%s\" with preference %i", host, preference);
- for (j = s->mxarraysz - 1; j > i; j--)
- s->mxarray[j] = s->mxarray[j - 1];
+ TAILQ_FOREACH(e, &s->mx, entry) {
+ if (mx->preference <= e->preference) {
+ TAILQ_INSERT_BEFORE(e, mx, entry);
+ return;
+ }
+ }
- s->mxarray[i].prio = prio;
- strlcpy(s->mxarray[i].host, host,
- sizeof (s->mxarray[i].host));
+ TAILQ_INSERT_TAIL(&s->mx, mx, entry);
}