使用 TLS 的 Postfix 2.6.6 - 無法接收來自 GMail(和其他幾個 MTA)的電子郵件,但其他都可以,為什麼?

使用 TLS 的 Postfix 2.6.6 - 無法接收來自 GMail(和其他幾個 MTA)的電子郵件,但其他都可以,為什麼?

我剛剛查看了一台運行 Postfix 2.6.6 的 CentOS 6 伺服器,它能夠向每個人發送電子郵件,但由於傳入的 TLS 協商問題而無法從 GMail(以及其他一些 MTA)接收電子郵件。

.google.com來自SMTP 伺服器(即 GMail)的連線導致以下結果:

Aug 23 19:34:29 server1 postfix/smtpd[7659]: connect from mail-lf1-f44.google.com[209.85.167.44]
Aug 23 19:34:29 server1 postfix/smtpd[7659]: setting up TLS connection from mail-lf1-f44.google.com[209.85.167.44]
Aug 23 19:34:29 server1 postfix/smtpd[7659]: SSL_accept error from mail-lf1-f44.google.com[209.85.167.44]: -1
Aug 23 19:34:29 server1 postfix/smtpd[7659]: warning: TLS library problem: 7659:error:1408A0C1:SSL routines:SSL3_GET_CLIENT_HELLO:no shared cipher:s3_srvr.c:1387:
Aug 23 19:34:29 server1 postfix/smtpd[7659]: lost connection after STARTTLS from mail-lf1-f44.google.com[209.85.167.44]
Aug 23 19:34:29 server1 postfix/smtpd[7659]: disconnect from mail-lf1-f44.google.com[209.85.167.44]

增加 TLS 日誌記錄的詳細程度:

Aug 23 21:56:15 server1 postfix/smtpd[18103]: initializing the server-side TLS engine
Aug 23 21:56:15 server1 postfix/smtpd[18103]: connect from mail-lf1-f47.google.com[209.85.167.47]
Aug 23 21:56:15 server1 postfix/smtpd[18103]: setting up TLS connection from mail-lf1-f47.google.com[209.85.167.47]
Aug 23 21:56:15 server1 postfix/smtpd[18103]: mail-lf1-f47.google.com[209.85.167.47]: TLS cipher list "ALL:+RC4:@STRENGTH:!aNULL:!LOW:!EXP:!MEDIUM:!ADH:!AECDH:!MD5:!DSS:!ECDSA:!CAMELLIA128:!3DES:!CAMELLIA256:!RSA+AES:!eNULL"
Aug 23 21:56:15 server1 postfix/smtpd[18103]: SSL_accept:before/accept initialization
Aug 23 21:56:15 server1 postfix/smtpd[18103]: SSL3 alert write:fatal:handshake failure
Aug 23 21:56:15 server1 postfix/smtpd[18103]: SSL_accept:error in SSLv3 read client hello C
Aug 23 21:56:15 server1 postfix/smtpd[18103]: SSL_accept error from mail-lf1-f47.google.com[209.85.167.47]: -1
Aug 23 21:56:15 server1 postfix/smtpd[18103]: warning: TLS library problem: 18103:error:1408A0C1:SSL routines:SSL3_GET_CLIENT_HELLO:no shared cipher:s3_srvr.c:1387:
Aug 23 21:56:15 server1 postfix/smtpd[18103]: lost connection after STARTTLS from mail-lf1-f47.google.com[209.85.167.47]
Aug 23 21:56:15 server1 postfix/smtpd[18103]: disconnect from mail-lf1-f47.google.com[209.85.167.47]

沒有共享密碼?

已使用(儘管是自簽署的)伺服器憑證啟用 TLS;用戶端已成功連線並透過 IMAP/POP 使用 SASL 發送和接收郵件。

我閱讀了1408A0C1後綴錯誤的常見原因,但似乎沒有一個完全適用於這種情況。我進行的一些檢查產生的結果似乎與我的預期相矛盾;

postconf -d | grep cipherlist有這個相當簡短的排除清單:

tls_export_cipherlist = ALL:+RC4:@STRENGTH
tls_high_cipherlist = ALL:!EXPORT:!LOW:!MEDIUM:+RC4:@STRENGTH
tls_low_cipherlist = ALL:!EXPORT:+RC4:@STRENGTH
tls_medium_cipherlist = ALL:!EXPORT:!LOW:+RC4:@STRENGTH
tls_null_cipherlist = eNULL:!aNULL

且 TLS 協定相當寬鬆:

smtpd_tls_mandatory_protocols = !SSLv2, !SSLv3
smtp_tls_mandatory_protocols  = !SSLv2, !SSLv3
smtpd_tls_protocols           = !SSLv2, !SSLv3
smtp_tls_protocols            = !SSLv2, !SSLv3

那為什麼它無法協商密碼呢?

我首先開始更新 OpenSSL(這是OpenSSL 1.0.1e-fips 11 Feb 2013最新的,可透過 取得yum);我做到了按照本文的指示結果盒子運行了OpenSSL 1.0.2p 14 Aug 2018

但是,GMail 接收問題仍然存在...

我保留了這些原樣,以便為所有可能的 TLS 變體提供成功的機會,並更詳細地研究了這些密碼。

停用全部關於密碼排除,我從我的 Gmail 發送了一封測試電子郵件,不出所料,它通過了:

Aug 23 23:39:52 server1 postfix/smtpd[6036]: connect from mail-lj1-f171.google.com[209.85.208.171]
Aug 23 23:39:52 server1 postfix/smtpd[6036]: setting up TLS connection from mail-lj1-f171.google.com[209.85.208.171]
Aug 23 23:39:52 server1 postfix/smtpd[6036]: mail-lj1-f171.google.com[209.85.208.171]: TLS cipher list "ALL:+RC4:@STRENGTH"
Aug 23 23:39:52 server1 postfix/smtpd[6036]: SSL_accept:before/accept initialization
Aug 23 23:39:52 server1 postfix/smtpd[6036]: SSL_accept:SSLv3 read client hello B
Aug 23 23:39:52 server1 postfix/smtpd[6036]: SSL_accept:SSLv3 write server hello A
Aug 23 23:39:52 server1 postfix/smtpd[6036]: SSL_accept:SSLv3 write certificate A
Aug 23 23:39:52 server1 postfix/smtpd[6036]: SSL_accept:SSLv3 write server done A
Aug 23 23:39:52 server1 postfix/smtpd[6036]: SSL_accept:SSLv3 flush data
Aug 23 23:39:52 server1 postfix/smtpd[6036]: SSL_accept:SSLv3 read client key exchange A
Aug 23 23:39:52 server1 postfix/smtpd[6036]: SSL_accept:SSLv3 read finished A
Aug 23 23:39:52 server1 postfix/smtpd[6036]: SSL_accept:SSLv3 write session ticket A
Aug 23 23:39:52 server1 postfix/smtpd[6036]: SSL_accept:SSLv3 write change cipher spec A
Aug 23 23:39:52 server1 postfix/smtpd[6036]: SSL_accept:SSLv3 write finished A
Aug 23 23:39:52 server1 postfix/smtpd[6036]: SSL_accept:SSLv3 flush data
Aug 23 23:39:52 server1 postfix/smtpd[6036]: Anonymous TLS connection established from mail-lj1-f171.google.com[209.85.208.171]: TLSv1.2 with cipher AES128-GCM-SHA256 (128/128 bits)
Aug 23 23:39:52 server1 postfix/smtpd[6036]: 66BB15DC6: client=mail-lj1-f171.google.com[209.85.208.171]
Aug 23 23:39:52 server1 postfix/cleanup[6424]: 66BB15DC6: message-id=<CAK9Gk9r+6gt7g_U987A0XaGdKJGY=80n0rK595mqrmfGaL5LKQ@mail.gmail.com>
Aug 23 23:39:52 server1 opendkim[6890]: 66BB15DC6: mail-lj1-f171.google.com [209.85.208.171] not internal
Aug 23 23:39:52 server1 opendkim[6890]: 66BB15DC6: not authenticated
Aug 23 23:39:52 server1 opendkim[6890]: 66BB15DC6: DKIM verification successful
Aug 23 23:39:52 server1 postfix/qmgr[6032]: 66BB15DC6: from=<gmailaddress>, size=3988, nrcpt=1 (queue active)
Aug 23 23:39:52 server1 postfix/smtpd[6036]: disconnect from mail-lj1-f171.google.com[209.85.208.171]
Aug 23 23:39:52 server1 postfix/pipe[6425]: 66BB15DC6: to=<myinbox>, relay=dovecot, delay=0.48, delays=0.29/0.01/0/0.18, dsn=2.0.0, status=sent (delivered via dovecot service)

那麼,如果 GMailAES128-GCM-SHA256透過 TLSv1.2 進行協商——為什麼它之前不起作用?特別是他們的密碼清單似乎是任何可能的匹配,最後是 RC4,按強度順序排列?


為了測試,我採用了一個特定的密碼列表,在前面添加了 AES128 哈希深度(斜體)——ECDHE 和 DHE 方法——並在 postfix 中明確聲明它,這有效:

tls_high_cipherlist=ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-GCM-SHA384:DHE-RSA DHE-DSS-AES128-GCM-SHA256:EDH+CAMELLIA:EDH+aRSA:EECDH+aRSA+AESGCM:EECDH+aRSA+SHA384:EECDH+aRSA+SHA256:EECDH:+CAMELLIA256:+AES256:+CAMELLIA128:+AES128:+SULLv3:!a !低:!3DES:!MD5:!EXP:!PSK:!DSS:!RC4:!SEED:!ECDSA:CAMELLIA256-SHA:AES256-SHA:CAMELLIA128-SHA:AES128-SHA

不過,我不想不斷更新密碼清單食譜,因此註解掉了該tls_high_cipherlist聲明。

然後我做了一些事情。

在 postfix 中,master.cf-o smtp_tls_mandatory_protocols=TLSv1按照建議添加到了 smtpd 部分。

我想透過使用聲明來改進 TLS 協議https://blog.kruyt.org/postfix-and-tls-encryption/,在排除舊版本之前明確批准 TLSv1.2 和 TLSv1.1。然而對於 postfix 2.6.6,這不起作用;重新加載/重新啟動後不久,我在日誌中看到了這一點:

warning: Invalid TLS protocol list "TLSv1.2, TLSv1.1, !TLSv1, !SSLv2, !SSLv3": disabling TLS support

如果我將排除 !rules 與包含規則混合在一起,就會發生這種情況,因此我恢復為明確排除格式:

smtpd_tls_protocols = !TLSv1, !SSLv2, !SSLv3
smtp_tls_protocols = !TLSv1, !SSLv2, !SSLv3
smtp_tls_ciphers = high
smtpd_tls_ciphers = high
smtpd_tls_mandatory_protocols = !TLSv1, !SSLv2, !SSLv3
smtp_tls_mandatory_protocols = !TLSv1, !SSLv2, !SSLv3
smtp_tls_mandatory_ciphers = high
smtpd_tls_mandatory_ciphers = high

這被 postfix 接受了。

我設定了機會主義 TLS

smtp_tls_security_level = may
smtpd_tls_security_level = may

我注意到,即使解決了 GMail 傳送問題,其他一些 MTA 仍然失敗:

server1 postfix/smtpd[28167]: connect from mta3.email.secretescapes.com[198.245.84.110]
server1 postfix/smtpd[28167]: setting up TLS connection from mta3.email.secretescapes.com[198.245.84.110]
server1 postfix/smtpd[28167]: mta3.email.secretescapes.com[198.245.84.110]: TLS cipher list "ALL:!EXPORT:!LOW:!MEDIUM:+RC4:@STRENGTH:!MD5:!DES:!ADH:!RC4:!PSD:!SRP:!3DES:!eNULL:!aNULL"
server1 postfix/smtpd[28167]: SSL_accept:before/accept initialization
server1 postfix/smtpd[28167]: SSL_accept:error in SSLv2/v3 read client hello A
server1 postfix/smtpd[28167]: SSL_accept error from mta3.email.secretescapes.com[198.245.84.110]: -1
server1 postfix/smtpd[28167]: warning: TLS library problem: 28167:error:140760FC:SSL routines:SSL23_GET_CLIENT_HELLO:unknown protocol:s23_srvr.c:647:
server1 postfix/smtpd[28167]: lost connection after STARTTLS from mta3.email.secretescapes.com[198.245.84.110]
server1 postfix/smtpd[28167]: disconnect from mta3.email.secretescapes.com[198.245.84.110]

-

server1 postfix/smtpd[1451]: initializing the server-side TLS engine
server1 postfix/smtpd[1451]: connect from mta.email.bbc.com[198.245.84.99]
server1 postfix/smtpd[1451]: setting up TLS connection from mta.email.bbc.com[198.245.84.99]
server1 postfix/smtpd[1451]: mta.email.bbc.com[198.245.84.99]: TLS cipher list "ALL:!EXPORT:!LOW:!MEDIUM:+RC4:@STRENGTH:!MD5:!aDSS:!kECDH:!kDH:!SEED:!IDEA:!DES:!ADH:!RC2:!RC4:!RC5:!PSD:!SRP:!3DES:!eNULL:!aNULL"
server1 postfix/smtpd[1451]: SSL_accept:before/accept initialization
server1 postfix/smtpd[1451]: SSL_accept:error in SSLv2/v3 read client hello A
server1 postfix/smtpd[1451]: SSL_accept error from mta.email.bbc.com[198.245.84.99]: -1
server1 postfix/smtpd[1451]: warning: TLS library problem: 1451:error:140760FC:SSL routines:SSL23_GET_CLIENT_HELLO:unknown protocol:s23_srvr.c:647:
server1 postfix/smtpd[1451]: lost connection after STARTTLS from mta.email.bbc.com[198.245.84.99]
server1 postfix/smtpd[1451]: disconnect from mta.email.bbc.com[198.245.84.99]
server1 postfix/smtpd[1451]: connect from unknown[107.174.30.57]
server1 postfix/smtpd[1451]: 4F6D0629C: client=unknown[107.174.30.57]

然後我嘗試了 tls_high_cipherlist 的一些排列,然後最終使用bettercrypto.org 推薦列表

tls_high_cipherlist=EDH+CAMELLIA:EDH+aRSA:EECDH+aRSA+AESGCM:EECDH+aRSA+SHA256:EECDH:+CAMELLIA128:+AES128:+SSLv3:!aNULL:!eNULL:!LOW:!3DES:!MD5:!EXP:!PSK:!DSS:!RC4:!SEED:!IDEA:!ECDSA:kEDH:CAMELLIA128-SHA:AES128-SHA

該伺服器已經過各種 SSL 測試儀的測試,包括檢查TLS(100%結果),勒克斯科學(A+結果),htbridge 的 SSL 測試器(好成績)和SSL 工具

我知道您可以策略映射傳出連接,但我正在尋找等效的方法,這樣我就可以選擇性地禁用特定MTA 的任何排除(正如我找到的那樣)併計算出它們正在協商的密碼,然後調整我提供的密碼清單。

我在目前的 postfix TLS 配置中看不到任何明顯的缺陷。我不明白為什麼某些 MTA 無法協商 TLS 密碼,而其他 MTA 則管理得很好。即使是最挑剔的 GMail,現在也可以了。

有任何想法嗎?:-)


我注意到這個 SE 問題是關於為什麼 Google 更喜歡它的密碼,這使得閱讀變得有趣。

致謝這個 Postfix 使用者論壇主題,我找到了一個有用的方法,可以快速查看在所有可用密碼中成功建立了多少個 TLS 連線:

egrep "TLS connection established from.*with cipher" /var/log/maillog* | awk '{printf("%s %s %s %s\n", $12, $13, $14, $15)}' | sort | uniq -c | sort -

答案1

最終,這個問題似乎是由於某些寄件者仍然只能協商 SSLv3 造成的。這是一件壞事,但收不到電子郵件也不好。

確實就是這麼簡單。我對此並不滿意,但如果發送 MTA 拒絕與 TLS 重新協商,而只是不斷地使用 SSLv3 重試,那麼我們現在無能為力。

因此,目前我已採取允許使用 SSLv3 加密傳入電子郵件的方法,但要求伺服器上的所有用戶端仍必須透過 TLS 進行身份驗證。

我透過減輕協議否定來實現這一點main.cf

smtpd_tls_mandatory_protocols = !TLSv1, !SSLv2
smtpd_tls_protocols = !TLSv1, !SSLv2

請注意,這些smtp_tls_定義適用於從該伺服器發送的郵件,因此與用戶端連線相關,因此您可以根據自己的喜好進行嚴格設定(只要您願意向每個人解釋如何設定其電子郵件用戶端):

smtp_tls_mandatory_protocols = !TLSv1, !SSLv2, !SSLv3
smtp_tls_protocols = !TLSv1, !SSLv2, !SSLv3

如果傳送 MTA 無法協商 TLS(需要 SSLv3),那麼您通常會在郵件日誌中看到以下內容:

warning: TLS library problem: 364:error:140760FC:SSL routines:SSL23_GET_CLIENT_HELLO:unknown protocol:s23_srvr.c:647:

如果您調高日誌記錄級別,您將看到 TLS 協商失敗,並顯示更多訊息,例如

postfix/smtpd[26234]: SSL_accept:before/accept initialization
postfix/smtpd[26234]: SSL_accept:error in SSLv2/v3 read client hello A
postfix/smtpd[26234]: SSL_accept error from 201-62-89-201.life.com.br[201.62.89.201]: -1

我一直在定期測試禁止 SSLv3 連線(MTA 不可避免地會重試很多天),因此您可以允許日誌中出現一些故障,然後對其進行分析。

這個 bash 腳本幫助我分析哪些伺服器正在嘗試使用 SSLv3:

#!/bin/sh
egrep "SSL_accept error" /var/log/maillog | awk '{printf("%s %s %s\n", $9, $10, $11)}' | sort | uniq -c | sort -`

此變體顯示協商密碼 - 因此,一旦您重新啟用 SSLv3,您可以將其保留一段時間,然後確認 MTA 正在使用 SSLv3:

#!/bin/sh
egrep "TLS connection established from.*with cipher" /var/log/maillog | awk '{printf("%s %s %s %s\n", $12, $13, $14, $15)}' | sort | uniq -c | sort -

我還沒有找到更好的答案;我想採取更細緻的方法,並能夠選擇性地允許某些 MTA 的 SSLv3,具體取決於它們的連接嘗試是否因maillog.歡迎所有意見/建議。

相關內容