tateisu / SubwayTooter

Mastodon client app for Android
Apache License 2.0
234 stars 23 forks source link

一部のインスタンスと一部の端末の組み合わせでHTTPS接続のhandshakeに失敗する #4

Closed tateisu closed 4 years ago

tateisu commented 7 years ago

事案URL https://masatodon.jp/users/admin/updates/98 https://mastodon.cloud/@rolling_maki/6134926 https://mastodon.juggler.jp/@tateisu/700457 https://mastodon.juggler.jp/@tateisu/699821 https://masatodon.jp/users/admin/updates/98

mastodon.cloud m.sighash.info

どちらもウチの端末だと接続できてるんだよね…

https://www.ssllabs.com/ssltest/analyze.html?d=mastodon.cloud&latest https://www.ssllabs.com/ssltest/analyze.html?d=m.sighash.info を参考に okhttpの暗号化スイートの指定を増やしてみた

TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256 TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384 TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384 TLS_DHE_RSA_WITH_AES_256_GCM_SHA384 TLS_DHE_RSA_WITH_AES_256_CBC_SHA256 TLS_DHE_RSA_WITH_AES_256_CBC_SHA

https://www.dropbox.com/s/8ac51m7qsgsxzpj/SubwayTooter-rc-37-0.3.7-20170506_010159.apk?dl=0 ユーザさんにテスト用APKを試してもらったが効果なし

報告された端末は 「ZenFone3 ZE520KL をAndroid 7.0 にしたもの」 「Xperia(詳細忘れた)」 「Qua Phone PX、OSはAndroid7.0」

何かしら端末を調達しないとコレ以上のことは分からなさそう

tateisu commented 7 years ago

Nexus 5x (Android 7.1.2) は問題なし。 エミュレータで Android 7.0 (Google APIs) のイメージを動かしてようやく再現

javax.net.ssl.SSLHandshakeException: Handshake failed
    at com.android.org.conscrypt.OpenSSLSocketImpl.startHandshake(OpenSSLSocketImpl.java:429)
    at okhttp3.internal.connection.RealConnection.connectTls(RealConnection.java:268)
    at okhttp3.internal.connection.RealConnection.establishProtocol(RealConnection.java:238)
    at okhttp3.internal.connection.RealConnection.connect(RealConnection.java:149)
    at okhttp3.internal.connection.StreamAllocation.findConnection(StreamAllocation.java:192)
    at okhttp3.internal.connection.StreamAllocation.findHealthyConnection(StreamAllocation.java:121)
    at okhttp3.internal.connection.StreamAllocation.newStream(StreamAllocation.java:100)
    at okhttp3.internal.connection.ConnectInterceptor.intercept(ConnectInterceptor.java:42)
    at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:92)
    at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:67)
    at okhttp3.internal.cache.CacheInterceptor.intercept(CacheInterceptor.java:93)
    at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:92)
    at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:67)
    at okhttp3.internal.http.BridgeInterceptor.intercept(BridgeInterceptor.java:93)
    at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:92)
    at okhttp3.internal.http.RetryAndFollowUpInterceptor.intercept(RetryAndFollowUpInterceptor.java:120)
    at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:92)
    at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:67)
    at okhttp3.RealCall.getResponseWithInterceptorChain(RealCall.java:185)
    at okhttp3.RealCall.execute(RealCall.java:69)
    at jp.juggler.subwaytooter.api.TootApiClient.authorize1(TootApiClient.java:229)
    at jp.juggler.subwaytooter.ActMain$7$1.doInBackground(ActMain.java:494)
    at jp.juggler.subwaytooter.ActMain$7$1.doInBackground(ActMain.java:471)
    at android.os.AsyncTask$2.call(AsyncTask.java:304)
    at java.util.concurrent.FutureTask.run(FutureTask.java:237)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1133)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607)
    at java.lang.Thread.run(Thread.java:761)
Caused by: javax.net.ssl.SSLProtocolException: SSL handshake terminated: ssl=0x7ab20c947780: Failure in SSL library, usually a protocol error
error:10000410:SSL routines:OPENSSL_internal:SSLV3_ALERT_HANDSHAKE_FAILURE (external/boringssl/src/ssl/s3_pkt.c:610 0x7ab1f6e40e80:0x00000001)
error:1000009a:SSL routines:OPENSSL_internal:HANDSHAKE_FAILURE_ON_CLIENT_HELLO (external/boringssl/src/ssl/s3_clnt.c:764 0x7ab203baa76a:0x00000000)
    at com.android.org.conscrypt.NativeCrypto.SSL_do_handshake(Native Method)
    at com.android.org.conscrypt.OpenSSLSocketImpl.startHandshake(OpenSSLSocketImpl.java:357)
    ... 27 more
SubwayTooter: ActMain: Network error. :SSLHandshakeException Handshake failed
tateisu commented 7 years ago

http://stackoverflow.com/questions/39133437/sslhandshakeexception-handshake-failed-on-android-n-7-0 によると

This is a known regression in Android 7.0, acknowledged by Google and fixed sometime before the release of Android 7.1.1. Here is the bug report: https://code.google.com/p/android/issues/detail?id=224438.

tateisu commented 7 years ago

Volley 用のワークアラウンドは http://stackoverflow.com/a/40198170 で説明されてるけど、 okhttp でどうやるのかはよく分からない

tateisu commented 7 years ago

mastodon.cloudに関してはアプリ的には詰んでることがわかりました

https://www.ssllabs.com/ssltest/analyze.html?d=mastodon.cloud&s=91.121.119.225

サーバ管理者に、 ssl_ecdh_curve に prime256v1 を含めてくれと要望してください

tateisu commented 7 years ago

m.sighash.info の方は 0.3.7 で暗号化スイートの指定を増やしたあたりでブラウザ認証まで進められるようになりました。

アプリ側でこれ以上できることはなさそうです。

tateisu commented 7 years ago

v0.5.8 で、このエラーに遭遇したら免責ダイアログを表示するようにした

tateisu commented 7 years ago

media.masto.host https://www.ssllabs.com/ssltest/analyze.html?d=media.masto.host&s=217.182.83.177 は 「Supported EC Named Curves secp256r1」と出るのに7.0イメージのエミュレータから接続しようとするとSocketTimeoutException になる

mastodon.cloud https://www.ssllabs.com/ssltest/analyze.html?d=mastodon.cloud&s=104.20.42.123 もよく見ると「Supported EC Named Curves secp256r1」と出るのに7.0イメージのエミュレータから接続しようとすると SSLHandshakeException になる

7.0 うんこ…

tateisu commented 6 years ago

googleのConscrypt https://github.com/google/conscrypt/ を導入すれば4.xの端末や7.0の端末のTLSの問題を改善できるらしい。

しかし7.0でHandshakeエラーの出るタンスの情報や手持ちの7.0端末が不足してる

tateisu commented 6 years ago

Security.insertProviderAt(Conscrypt.newProvider(),1);

tateisu commented 4 years ago

conscrypt ライブラリを組み込んだのでもう再現しないと思う