Index: opendmarc-1.2.0.beta1/opendmarc/opendmarc.c =================================================================== --- opendmarc-1.2.0.beta1.orig/opendmarc/opendmarc.c 2014-01-26 22:02:51.000000000 +0100 +++ opendmarc-1.2.0.beta1/opendmarc/opendmarc.c 2014-01-26 22:10:59.000000000 +0100 @@ -126,6 +126,7 @@ struct dmarcf_config { _Bool conf_reqhdrs; + _Bool conf_rejectreqhdrsfail; _Bool conf_afrf; _Bool conf_afrfnone; _Bool conf_rejectfail; @@ -1231,6 +1232,10 @@ &conf->conf_reqhdrs, sizeof conf->conf_reqhdrs); + (void) config_get(data, "RejectRequiredHeadersFailures", + &conf->conf_rejectreqhdrsfail, + sizeof conf->conf_rejectreqhdrsfail); + (void) config_get(data, "ForensicReports", &conf->conf_afrf, sizeof conf->conf_afrf); @@ -1996,60 +2001,59 @@ /* if requested, verify RFC5322-required headers (RFC5322 3.6) */ if (conf->conf_reqhdrs) { - _Bool ok = TRUE; + unsigned char* reqhdrs_error = NULL; /* no error */ - /* exactly one From: */ if (dmarcf_findheader(dfc, "From", 0) == NULL || dmarcf_findheader(dfc, "From", 1) != NULL) - ok = FALSE; + reqhdrs_error = "not exactly one From:"; - /* exactly one Date: */ if (dmarcf_findheader(dfc, "Date", 0) == NULL || dmarcf_findheader(dfc, "Date", 1) != NULL) - ok = FALSE; + reqhdrs_error = "not exactly one Date:"; - /* no more than one Reply-To: */ if (dmarcf_findheader(dfc, "Reply-To", 1) != NULL) - ok = FALSE; + reqhdrs_error = "more than one Reply-To:"; - /* no more than one To: */ if (dmarcf_findheader(dfc, "To", 1) != NULL) - ok = FALSE; + reqhdrs_error = "more than one To:"; - /* no more than one Cc: */ if (dmarcf_findheader(dfc, "Cc", 1) != NULL) - ok = FALSE; + reqhdrs_error = "more than one Cc:"; - /* no more than one Bcc: */ if (dmarcf_findheader(dfc, "Bcc", 1) != NULL) - ok = FALSE; + reqhdrs_error = "more than one Bcc:"; - /* no more than one Message-Id: */ if (dmarcf_findheader(dfc, "Message-Id", 1) != NULL) - ok = FALSE; + reqhdrs_error = "more than one Message-Id:"; - /* no more than one In-Reply-To: */ if (dmarcf_findheader(dfc, "In-Reply-To", 1) != NULL) - ok = FALSE; + reqhdrs_error = "more than one In-Reply-To:"; - /* no more than one References: */ if (dmarcf_findheader(dfc, "References", 1) != NULL) - ok = FALSE; + reqhdrs_error = "more than one References:"; - /* no more than one Subject: */ if (dmarcf_findheader(dfc, "Subject", 1) != NULL) - ok = FALSE; + reqhdrs_error = "more than one Subject:"; - if (!ok) + if (reqhdrs_error) { + unsigned char replybuf[BUFRSZ + 1]; + if (conf->conf_dolog) { syslog(LOG_INFO, - "%s: RFC5322 header requirement error", - dfc->mctx_jobid); + "%s: RFC5322 requirement error: %s header", + dfc->mctx_jobid, reqhdrs_error); } - return SMFIS_REJECT; + if (conf->conf_rejectreqhdrsfail) { + /* TODO: handle setreply failures */ + snprintf(replybuf, sizeof replybuf, + "RFC5322 header requirement error"); + dmarcf_setreply(ctx, DMARC_REJECT_SMTP, + DMARC_REJECT_ESC, replybuf); + return SMFIS_REJECT; + } } } @@ -2067,7 +2071,7 @@ dfc->mctx_jobid); } - if (conf->conf_reqhdrs) + if (conf->conf_rejectreqhdrsfail) return SMFIS_REJECT; else return SMFIS_ACCEPT; Index: opendmarc-1.2.0.beta1/opendmarc/opendmarc.conf.5.in =================================================================== --- opendmarc-1.2.0.beta1.orig/opendmarc/opendmarc.conf.5.in 2014-01-26 22:02:51.000000000 +0100 +++ opendmarc-1.2.0.beta1/opendmarc/opendmarc.conf.5.in 2014-01-26 22:07:28.000000000 +0100 @@ -225,8 +225,12 @@ .I RequiredHeaders (Boolean) If set, the filter will ensure the header of the message conforms to the basic header field count restrictions laid out in RFC5322, Section 3.6. Messages -failing this test are rejected without further processing. A From: -field from which no domain name could be extracted will also be rejected. +failing this test are logged. A From: +field from which no domain name could be extracted will also be logged. + +.TP +.I RejectRequiredHeadersFailures (Boolean) +Messages failing the above tests are rejected without further processing. .TP .I Socket (string) Index: opendmarc-1.2.0.beta1/opendmarc/opendmarc-config.h =================================================================== --- opendmarc-1.2.0.beta1.orig/opendmarc/opendmarc-config.h 2014-01-26 22:09:08.000000000 +0100 +++ opendmarc-1.2.0.beta1/opendmarc/opendmarc-config.h 2014-01-26 22:10:01.000000000 +0100 @@ -39,6 +39,7 @@ { "PublicSuffixList", CONFIG_TYPE_STRING, FALSE }, { "RecordAllMessages", CONFIG_TYPE_BOOLEAN, FALSE }, { "RequiredHeaders", CONFIG_TYPE_BOOLEAN, FALSE }, + { "RejectRequiredHeadersFailures", CONFIG_TYPE_BOOLEAN, FALSE }, { "RejectFailures", CONFIG_TYPE_BOOLEAN, FALSE }, { "ReportCommand", CONFIG_TYPE_STRING, FALSE }, { "Socket", CONFIG_TYPE_STRING, FALSE },