El manejo personalizado de SSL dejó de funcionar en Android 2.2 FroYo

Para mi aplicación, Transdroid, me estoy conectando a servidores remotos a través de HTTP y opcionalmente de forma segura a través de HTTPS. Para estas conexiones HTTPS con HttpClient, estoy usando una implementación de fábrica de sockets SSL personalizada para asegurarme de que los certificados autofirmados funcionen. Básicamente, acepto todo e ignoro cada comprobación de cualquier certificado.

Esto ha estado funcionando bien desde hace un tiempo, pero ya no funciona para Android 2.2 FroYo. Al intentar conectarse, devolverá una excepción:

java.io.IOException: SSL handshake failure: I/O error during system call, Broken pipe 

Aquí es cómo inicializo el HttpClient:

  SchemeRegistry registry = new SchemeRegistry(); registry.register(new Scheme("http", new PlainSocketFactory(), 80)); registry.register(new Scheme("https", (trustAll ? new FakeSocketFactory() : SSLSocketFactory.getSocketFactory()), 443)); client = new DefaultHttpClient(new ThreadSafeClientConnManager(httpParams, registry), httpParams); 

Hago uso de FakeSocketFactory y FakeTrustManager, cuya fuente se puede encontrar aquí .

Una vez más, no entiendo por qué de repente se detuvo el trabajo, o incluso lo que significa el error ‘Broken pipe’. He visto mensajes en Twitter de que Seesmic y Twidroid fallan con SSL habilitado en FroYo también, pero no estoy seguro de si está relacionado.

Gracias por cualquier dirección / ayuda!

Aquí está la respuesta, con muchas, muchas gracias a un desarrollador de Seesmic útil dispuesto a compartir la solución:

En la fábrica de socket personalizado, la creación de socket (con createSocket ) aparentemente ha cambiado específicamente para la implementación de SSLSocketFactory . Entonces el viejo:

  @Override public Socket createSocket(Socket socket, String host, int port, boolean autoClose) throws IOException, UnknownHostException { return getSSLContext().getSocketFactory().createSocket(); } 

Necesita ser cambiado a:

  @Override public Socket createSocket(Socket socket, String host, int port, boolean autoClose) throws IOException, UnknownHostException { return getSSLContext().getSocketFactory().createSocket(socket, host, port, autoClose); } 

¡Y luego funcionó de nuevo para mí!

ACTUALIZACIÓN: como esta sigue siendo una respuesta popular, déjame actualizar mi enlace al código de trabajo. Esta fábrica de sockets habilitada para SSl admite protocolos modernos (TLS 1.1+), SNI y, opcionalmente, permite aceptar todos los certificados (inseguro, ignora todos los certificados SSL) o certificados autofirmados (mediante hash SHA-1).

Más información sobre este problema http://code.google.com/p/android/issues/detail?id=10472 Esto solucionó el problema de SSL que teníamos para HTC Desire cuando lo actualizamos a Android 2.2