Javax.net.ssl.SSLHandshakeException: javax.net.ssl.SSLProtocolException: SSL handshake aborted: Failure in SSL library, usually a protocol error

后端 未结 11 671
终归单人心
终归单人心 2020-11-22 10:55

I am trying to run the following code in android

URLConnection l_connection = null;
        // Create connection
        uzip=new UnZipData(mContext);
               


        
11条回答
  •  有刺的猬
    2020-11-22 11:58

    Scenario

    I was getting SSLHandshake exceptions on devices running versions of Android earlier than Android 5.0. In my use case I also wanted to create a TrustManager to trust my client certificate.

    I implemented NoSSLv3SocketFactory and NoSSLv3Factory to remove SSLv3 from my client's list of supported protocols but I could get neither of these solutions to work.

    Some things I learned:

    • On devices older than Android 5.0 TLSv1.1 and TLSv1.2 protocols are not enabled by default.
    • SSLv3 protocol is not disabled by default on devices older than Android 5.0.
    • SSLv3 is not a secure protocol and it is therefore desirable to remove it from our client's list of supported protocols before a connection is made.

    What worked for me

    Allow Android's security Provider to update when starting your app.

    The default Provider before 5.0+ does not disable SSLv3. Provided you have access to Google Play services it is relatively straightforward to patch Android's security Provider from your app.

    private void updateAndroidSecurityProvider(Activity callingActivity) {
        try {
            ProviderInstaller.installIfNeeded(this);
        } catch (GooglePlayServicesRepairableException e) {
            // Thrown when Google Play Services is not installed, up-to-date, or enabled
            // Show dialog to allow users to install, update, or otherwise enable Google Play services.
            GooglePlayServicesUtil.getErrorDialog(e.getConnectionStatusCode(), callingActivity, 0);
        } catch (GooglePlayServicesNotAvailableException e) {
            Log.e("SecurityException", "Google Play Services not available.");
        }
    }
    

    If you now create your OkHttpClient or HttpURLConnection TLSv1.1 and TLSv1.2 should be available as protocols and SSLv3 should be removed. If the client/connection (or more specifically it's SSLContext) was initialised before calling ProviderInstaller.installIfNeeded(...) then it will need to be recreated.

    Don't forget to add the following dependency (latest version found here):

    compile 'com.google.android.gms:play-services-auth:16.0.1'
    

    Sources:

    • Patching the Security Provider with ProviderInstaller Provider
    • Making SSLEngine use TLSv1.2 on Android (4.4.2)

    Aside

    I didn't need to explicitly set which cipher algorithms my client should use but I found a SO post recommending those considered most secure at the time of writing: Which Cipher Suites to enable for SSL Socket?

提交回复
热议问题