この記事ではOpenDMRCを使っているが、迷惑メール対策でRspamdを利用しているならRspamdにもDMARCの機能があるのでOpenDMARCは使わずRspamdを使うのが良さそう。個別機能のmilterを一掃してRspamdを活用を参照。
毎日届く大量のメールのヘッダを見ると、まともなところはSPFやDKIMは導入しているみたい。でも、DMARC対応はそんなに多くはない印象。
せっかくDKIMまで対応しているならあとちょっと頑張ってDMARCにも対応したいところ。
- SPF: 送信元のIPアドレスで正しい送信元を確認
- DKIM: 送信するメールに電子署名してメールの詐称を確認
- DMARC: 自分ドメインを詐称するメールの処理方法を指定・指定を受けて処理
DMARCは送信ドメイン認証のSPFやDKIMがあることが前提となる。送信ドメイン認証の結果を受けてどうして欲しいかというポリシーがDMARC。
つまり、「もし、オイラのドメインを送信元とするメールがあんたのメールサーバーに届いたとき、SPFやDKIMで調べて詐称だと判明したなら(何もしない|迷惑メール扱い|受け付けない)という扱いにしてね」と宣言するのがDMARC。
所有しているドメインを送信元とするメールが100%自分のところのメールサーバから送信されててDKIMの署名も確実に付いているということであれば「詐称したメールは受け付けなくてもいいよ」と宣言できるし、そうじゃないよということであれば「うちのメールサーバ以外から届いても迷惑メール扱いにしないでおいてね」と宣言しておいた方がいい。そういうもの。
ただし、MLとかも含めて考えると迂闊に「受け付けないで」にするのは怖いかも。
送信メールに関わる宣言側
DNSの設定に書き込む。以下はBINDの例。
1 2 3 4 5 6 7 | $ORIGIN example.com. ;1行目でoriginを宣言しているなら以下
;
;中略
;
IN TXT "v=spf1 +ip4:192.168.0.0/24 +ip6:2001:db8::/32 +mx -all" ;これはSPFの例
hoge._domainkey IN TXT "v=DKIM1; g=*; k=rsa; p=ABCDEFG実際は超長い鍵0123456789" ;これはDKIMの例
_dmarc IN TXT "v=DMARC1; p=none; sp=none; ri=3600; rua=mailto:postmaster@example.com; ruf=mailto:postmaster@example.com" ;これがDMARCの例
|
今回はドメインのポリシーpとサブドメインのポリシーspの両方をnone(何もしない最も緩いポリシー)にして宣言している。暫く運用して問題ないようであればnoneからquarantine(迷惑メール扱い・隔離)やreject(受け付けない)に変更する。riは集約レポートの報告間隔(秒)で上の例では(3600=1時間)を指定しているが初期値は86400=1日で普通はこれで良いと思うので指定無しにする。
ruaは集計レポートの宛先(基本はドメインの管理者宛)。rufは認証の失敗レポートの宛先をそれぞれ指定。上の例では失敗レポートだけ指定している。(変更した)
失敗レポートの形式を指定するならrf=afrfとか書く筈だが、afrf以外の値が存在しないのでrfは無指定で良い筈。
ごちゃごちゃ書いたけど、ぶっちゃけvとpとruaだけ指定というので良いかと。
変更したらシリアルの数値を増やすのもお忘れなく。
BINDであればrndc reloadで設定を反映させる。
受信したメールの処理
宣言するだけでもいいんだけどせっかくDMARCに手を付けるなら他所からメールを受信したときに他所様のドメインが宣言しているDMARCの指定に沿ってメールを扱ってやりたいところ。皆が勝手に宣言するだけで受信時に処理しないなら意味がない。「オマエラはオレ様の宣言通りに処理しろ、オレ様はオマエラの宣言は無視して勝手にやる」というところもあるかもだけど。
今回はPostfixで受信したメールのヘッダにDMARCの認証結果を追加する。
# cd /usr/ports/mail/opendmarc # make install
設定ファイルは/usr/local/etc/mail/opendmarc.conf.sampleを参考に。(FreeBSDのports/pkgの場合)
/usr/local/etc/mail/opendmarc.conf1 2 3 4 5 6 | AutoRestart true
BaseDirectory /var/run/opendmarc
IgnoreHosts /usr/local/etc/mail/opendmarc_ignore.hosts
IgnoreMailFrom example.com
Socket local:/var/run/opendmarc/dmarc.sock
SPFSelfValidate true
|
SPFはSPFSelfValidate trueで面倒見てくれる。つまり他のSPFのmilter等は停めていい。
1 2 3 4 5 | localhost
::1
2001:db8::/32
127.0.0.0/8
192.168.0.0/24
|
ローカルホストとかメールサーバのIPアドレスとか特定のネットワークを無視させる用。
/usr/local/etc/postfix/main.cf1 2 3 4 5 6 7 8 9 10 11 | smtpd_milters =
unix:/var/run/opendkim/dkim.sock #DKIM
unix:/var/run/opendmarc/dmarc.sock
unix:/var/run/clamav/clmilter.sock #ClamAV
unix:/var/run/rmilter/rmilter.sock #Rmilter
non_smtpd_milters =
unix:/var/run/opendkim/dkim.sock #DKIM
unix:/var/run/opendmarc/dmarc.sock
unix:/var/run/clamav/clmilter.sock #ClamAV
unix:/var/run/rmilter/rmilter.sock #Rmilter
|
ClamAVとかRmilterなどは使っている使っていないがある筈。
/etc/rc.conf (追記)1 2 3 4 | opendmarc_enable="YES"
opendmarc_pidfile="/var/run/opendmarc.pid"
opendmarc_socketspec="/var/run/opendmarc/dmarc.sock"
opendmarc_runas="postfix:vmail"
|
運用開始
# service opendmarc start # service postfix restart #こっちは稼働中だろうから再起動
DMARCを宣言していないドメインからのメール Authentication-Results: mx.example.com; dmarc=none (p=none dis=none) header.from=example.net DMARCを宣言していて詐称でないメールが届いた。pとdisが表示されている Authentication-Results: mx.example.com; dmarc=pass (p=none dis=none) header.from=example.org送信したメールが相手先で宣言したDMARCポリシーが正しく認識されていることを確認する。
今回はDMARCを処理しているGmailで確認。
ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@example.com header.s=hoge header.b=xxxxxxxx; spf=pass (google.com: domain of foobar@example.com designates 2001:db8::1 as permitted sender) smtp.mailfrom=foobar@example.com; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=example.com
あなたのドメインがexample.comでメールサーバ(2001:db8::1)が送信したメールアドレスがfoobar@example.comとする。
今回は受信したメールのヘッダにDMARCの結果がAuthentication-Results行として追加されるところまで。受信したメールのDMARCがreject扱いになった場合にそのメールがどう処理されるのかはそういうメールを受けたことがないので未確認。(メールヘッダのAuthentication-Results行にdmarc=failとか書くだけで後はSpamAssassin, Rspamd等配送時の振り分けに任せる?配送に回さず削除?SMTPで550とか554を返して拒否?)
レポート周りは次の記事で。