aboutsummaryrefslogtreecommitdiffstats
path: root/src/libserver/spf.c
diff options
context:
space:
mode:
authorVsevolod Stakhov <vsevolod@highsecure.ru>2016-01-15 22:15:25 +0000
committerVsevolod Stakhov <vsevolod@highsecure.ru>2016-01-15 22:15:25 +0000
commit04bfc92c1357c0f908ce9371ab303f8bf57657df (patch)
treef91065a44fcbbd9bdfedb9f483f25e88ca852f48 /src/libserver/spf.c
parent6ef35e3b2219338be95a1f1fc31f77c5c8cbed29 (diff)
downloadrspamd-04bfc92c1357c0f908ce9371ab303f8bf57657df.tar.gz
rspamd-04bfc92c1357c0f908ce9371ab303f8bf57657df.zip
Unify processing of includes/redirects in SPF
Issue: #483 Reported by: @dnl555
Diffstat (limited to 'src/libserver/spf.c')
-rw-r--r--src/libserver/spf.c72
1 files changed, 38 insertions, 34 deletions
diff --git a/src/libserver/spf.c b/src/libserver/spf.c
index fde0030d3..959cfe7f1 100644
--- a/src/libserver/spf.c
+++ b/src/libserver/spf.c
@@ -504,16 +504,48 @@ spf_record_addr_set (struct spf_addr *addr, gboolean allow_any)
addr->flags |= RSPAMD_SPF_FLAG_IPV6;
}
+static gboolean
+spf_process_txt_record (struct spf_record *rec, struct spf_resolved_element *resolved,
+ struct rdns_reply *reply)
+{
+ struct rdns_reply_entry *elt, *selected = NULL;
+ gboolean ret = FALSE;
+
+ /*
+ * We prefer spf version 1 as other records are mostly likely garbadge
+ * or incorrect records (e.g. spf2 records)
+ */
+ LL_FOREACH (reply->entries, elt) {
+ if (strncmp (elt->content.txt.data, "v=spf1", sizeof ("v=spf1") - 1)
+ == 0) {
+ selected = elt;
+ break;
+ }
+ }
+
+ if (!selected) {
+ LL_FOREACH (reply->entries, elt) {
+ if (start_spf_parse (rec, resolved, elt->content.txt.data)) {
+ ret = TRUE;
+ break;
+ }
+ }
+ }
+ else {
+ ret = start_spf_parse (rec, resolved, selected->content.txt.data);
+ }
+
+ return ret;
+}
+
static void
spf_record_dns_callback (struct rdns_reply *reply, gpointer arg)
{
struct spf_dns_cb *cb = arg;
- gchar *begin;
struct rdns_reply_entry *elt_data;
struct rspamd_task *task;
struct spf_addr *addr;
struct spf_record *rec;
- gboolean ret;
rec = cb->rec;
task = rec->task;
@@ -585,10 +617,7 @@ spf_record_dns_callback (struct rdns_reply *reply, gpointer arg)
break;
case SPF_RESOLVE_REDIRECT:
if (elt_data->type == RDNS_REQUEST_TXT) {
- begin = elt_data->content.txt.data;
- ret = start_spf_parse (rec, cb->resolved, begin);
-
- if (ret) {
+ if (spf_process_txt_record (rec, cb->resolved, reply)) {
cb->addr->flags |= RSPAMD_SPF_FLAG_PARSED;
}
else {
@@ -598,10 +627,7 @@ spf_record_dns_callback (struct rdns_reply *reply, gpointer arg)
break;
case SPF_RESOLVE_INCLUDE:
if (elt_data->type == RDNS_REQUEST_TXT) {
- begin = elt_data->content.txt.data;
- ret = start_spf_parse (rec, cb->resolved, begin);
-
- if (ret) {
+ if (spf_process_txt_record (rec, cb->resolved, reply)) {
cb->addr->flags |= RSPAMD_SPF_FLAG_PARSED;
}
else {
@@ -1671,7 +1697,7 @@ start_spf_parse (struct spf_record *rec, struct spf_resolved_element *resolved,
}
else {
msg_debug_spf (
- "<%s>: spf error for domain %s: bad spf record version: %*s",
+ "<%s>: spf error for domain %s: bad spf record start: %*s",
rec->task->message_id,
rec->sender_domain,
(gint)sizeof (SPF_VER1_STR) - 1,
@@ -1705,7 +1731,6 @@ static void
spf_dns_callback (struct rdns_reply *reply, gpointer arg)
{
struct spf_record *rec = arg;
- struct rdns_reply_entry *elt, *selected = NULL;
struct spf_resolved_element *resolved;
rec->requests_inflight--;
@@ -1717,28 +1742,7 @@ spf_dns_callback (struct rdns_reply *reply, gpointer arg)
rec->ttl = reply->entries->ttl;
}
- /*
- * We prefer spf version 1 as other records are mostly likely garbadge
- * or incorrect records (e.g. spf2 records)
- */
- LL_FOREACH (reply->entries, elt) {
- if (strncmp (elt->content.txt.data, "v=spf1", sizeof ("v=spf1") - 1)
- == 0) {
- selected = elt;
- break;
- }
- }
-
- if (!selected) {
- LL_FOREACH (reply->entries, elt) {
- if (start_spf_parse (rec, resolved, elt->content.txt.data)) {
- break;
- }
- }
- }
- else {
- start_spf_parse (rec, resolved, elt->content.txt.data);
- }
+ spf_process_txt_record (rec, resolved, reply);
}
rspamd_spf_maybe_return (rec);