postfix

とあるドメインにメールが送れない。
initial server greeting で弾かれる。向こうのGreeting Bannerを受け取る前に切断されてる感じ。
相手のドメインにはいくつかMXレコードがあるんだけど、一番プライオリティの高いMXに対して試行しただけで、セカンダリ以降には試行してないようだ。
こういう動きでいいんだっけ…。
少なくとも 25番ポート は反応があるのでセカンダリ以降につなぎに行かないんだろうか?

static SMTP_SESSION *smtp_connect_addr(const char *destination, DNS_RR *addr,
                                               unsigned port, DSN_BUF *why,
                                               int sess_flags)
{

~略~
    return (smtp_connect_sock(sock, sa, salen, SMTP_HNAME(addr), hostaddr.buf,
                              port, destination, why, sess_flags));
}

smtp_connect.c
の 1033 lines あたりから。
smtp_connect_remote 関数をよく読むと動きが解るかもしれない。
もしくは、smtp_update_addr_list 関数がMX RRを引っ張ってるのか?

    /*
     * Don't give up after a hard host lookup error until we have tried the
     * fallback relay servers.
     *
     * Don't bounce mail after a host lookup problem with a relayhost or with a
     * fallback relay.
     *
     * Don't give up after a qualifying soft error until we have tried all
     * qualifying backup mail servers.
     *
     * All this means that error handling and error reporting depends on whether
     * the error qualifies for trying to deliver to a backup mail server, or
     * whether we're looking up a relayhost or fallback relay. The challenge
     * then is to build this into the pre-existing SMTP client without
     * getting lost in the complexity.
     */

とか。

        /*
         * Connect to an SMTP server: create primary MX connections, and
         * reuse or create backup MX connections.
         *
         * At the start of an SMTP session, all recipients are unmarked. In the
         * course of an SMTP session, recipients are marked as KEEP (deliver
         * to alternate mail server) or DROP (remove from recipient list). At
         * the end of an SMTP session, weed out the recipient list. Unmark
         * any left-over recipients and try to deliver them to a backup mail
         * server.
         *
         * Cache the first good session under the next-hop destination name.
         * Cache all good sessions under their physical endpoint.
         *
         * Don't query the session cache for primary MX hosts. We already did
         * that in smtp_reuse_session(), and if any were found in the cache,
         * they were already deleted from the address list.
         */

このコメントから下を読むと解るかもしれない。
プログラム苦手だから読むの疲れる…合ってるかも解らないし。
for (addr = addr_list; SMTP_RCPT_LEFT(state) > 0 && addr; addr = next) {
~略~
}
おそらく、このfor文の中で有効なMXホスト、利用可能なSMTPセッションキャッシュなどを探しているっぽい。
SMTP_FEATURE_BEST_MX っていうのが何を意味しているのか気になる…。
session = smtp_connect_addr(dest, addr, port, why,state->misc_flags); 関数でsmtpセッションを張りに行ってると思うんだけど。
この関数の中では最終的に、
return (smtp_connect_sock(sock, sa, salen, SMTP_HNAME(addr), hostaddr.buf,port, destination, why, sess_flags));
smtp_connect_sock 関数を呼び出しているのでまたそっちを見てみる。

と思ったけど面倒になってきた…わからん。
ぐぐろう。

Postfix が全ての MX アドレスを試しません
http://www.kobitosan.net/postfix/archives/faq-jp-20010228pl02.html#skip_greeting

smtp_skip_4xx_greeting
smtp_skip_5xx_greeting
http://www.postfix-jp.info/trans-2.3/jhtml/postconf.5.html#smtp_skip_4xx_greeting

この辺を読むと、今の新しいPostfix(2.0以上)では、4xx または 5xx が返ってくれば次のMXホストに移るようだ。
25番ポートに繋がるけど、Greeting Bannerを返される前に切断されるとダメってことか。
ソース読む場所が見当違いだったかな…?
時間があったら、実際にどういう動きをしているのか追ってみたいところ。