Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Android ssl: javax.net.ssl.SSLPeerUnverifiedException: No peer certificate (yet again)

I've got a web site that I'm enabling ssl on for a RESTful service. We have registered with RapidSSL, installed the certs, and it passes the RapidSSL checker. I'm able to access the site with various browsers, including the android browsers (built in, firefox and opera) with no problems, no warnings.

However, when I try to access it with my android app, I get the following exception:

08-11 20:04:05.586   363   381 E HttpProvider: Error executing request: No peer certificate 08-11 20:04:05.586   363   381 E HttpProvider: javax.net.ssl.SSLPeerUnverifiedException: No peer certificate 08-11 20:04:05.586   363   381 E HttpProvider:  at org.apache.harmony.xnet.provider.jsse.SSLSessionImpl.getPeerCertificates(SSLSessionImpl.java:259) 08-11 20:04:05.586   363   381 E HttpProvider:  at org.apache.http.conn.ssl.AbstractVerifier.verify(AbstractVerifier.java:93) 08-11 20:04:05.586   363   381 E HttpProvider:  at org.apache.http.conn.ssl.SSLSocketFactory.createSocket(SSLSocketFactory.java:381) 08-11 20:04:05.586   363   381 E HttpProvider:  at org.apache.http.impl.conn.DefaultClientConnectionOperator.openConnection(DefaultClientConnectionOperator.java:164) 08-11 20:04:05.586   363   381 E HttpProvider:  at org.apache.http.impl.conn.AbstractPoolEntry.open(AbstractPoolEntry.java:164) 08-11 20:04:05.586   363   381 E HttpProvider:  at org.apache.http.impl.conn.AbstractPooledConnAdapter.open(AbstractPooledConnAdapter.java:119) 08-11 20:04:05.586   363   381 E HttpProvider:  at org.apache.http.impl.client.DefaultRequestDirector.execute(DefaultRequestDirector.java:359) 08-11 20:04:05.586   363   381 E HttpProvider:  at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:555) 08-11 20:04:05.586   363   381 E HttpProvider:  at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:487) 08-11 20:04:05.586   363   381 E HttpProvider:  at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:465) 08-11 20:04:05.586   363   381 E HttpProvider:  at com.xxxxx.netlib.http.HttpProvider.executeRequest(HttpProvider.java:75) 

This occurs on android 2.3.3 on the emulator and on a 3.2 tablet. I've seen lots of hits on this, but nothing I've found helps me to fix the issue.

More data:

$ openssl s_client -CAfile www.xxxxx.com.pem -connect www.xxxxx.com:443 CONNECTED(00000003) depth=3 C = US, O = Equifax, OU = Equifax Secure Certificate Authority verify return:1 depth=2 C = US, O = GeoTrust Inc., CN = GeoTrust Global CA verify return:1 depth=1 C = US, O = "GeoTrust, Inc.", CN = RapidSSL CA verify return:1 depth=0 serialNumber = 1-7wArtEjdTwJ94d5iVDooDmmC4mXyVj, OU = GT82425783, OU = See www.rapidssl.com/resources/cps (c)12, OU = Domain Control Validated - RapidSSL(R), CN = www.xxxxx.com verify return:1 --- Certificate chain 0 s:/serialNumber=1-7wArtEjdTwJ94d5iVDooDmmC4mXyVj/OU=GT82425783/OU=See www.rapidssl.com/resources/cps (c)12/OU=Domain Control Validated - RapidSSL(R)/CN=www.xxxxx.com   i:/C=US/O=GeoTrust, Inc./CN=RapidSSL CA 1 s:/C=US/O=GeoTrust, Inc./CN=RapidSSL CA   i:/C=US/O=GeoTrust Inc./CN=GeoTrust Global CA 2 s:/C=US/O=GeoTrust Inc./CN=GeoTrust Global CA   i:/C=US/O=Equifax/OU=Equifax Secure Certificate Authority --- [snip] 

The code I'm running to set up the client:

public class HttpProvider implements INetworkProvider {   private static final String LOG = "HttpProvider";   protected DefaultHttpClient client;    public HttpProvider() {     SchemeRegistry registry = new SchemeRegistry();     registry.register(new Scheme("http", PlainSocketFactory.getSocketFactory(), 80));     final SSLSocketFactory sslSocketFactory = SSLSocketFactory.getSocketFactory();     sslSocketFactory.setHostnameVerifier(SSLSocketFactory.BROWSER_COMPATIBLE_HOSTNAME_VERIFIER);     registry.register(new Scheme("https", sslSocketFactory, 443));      client = new DefaultHttpClient(       new ThreadSafeClientConnManager((new BasicHttpParams()), registry), new BasicHttpParams()     );   } [snip] 

I've also tried with STRICT_HOSTNAME_VERIFIER and still no joy.

From what I understand I shouldn't need to set up any custom truststores or keystores since I'm registered with a recognized cert provider.

I'm very new with ssl and find I'm swimming in a sea of Three Letter Acronyms, and I was hoping someone here may be able to give me a shove in the right direction.

like image 592
mvsjes2 Avatar asked Aug 12 '12 15:08

mvsjes2


People also ask

How do I fix SSLPeerUnverifiedException?

The solution is to use ProviderInstaller from Google Play Services to try to update the device to support the latest and greatest security protocols.

What is SSLPeerUnverifiedException?

Class SSLPeerUnverifiedExceptionIndicates that the peer's identity has not been verified.

What is SSL peer certificate?

Peer authentication means that the other side of the SSL connection is authenticated based on a trusted certificate installed locally. Alternatively, a Certification Authority (CA) certificate may be installed locally and the peer has a certificate signed by that authority.


1 Answers

After piles of digging and experimentation, I finally realized that the url I was using had hard coded port 80 instead of defaulting to 443. Dumb dumb dumb.

The answer to this question Trusting all certificates using HttpClient over HTTPS helped tremendously for my understanding of SSL.

like image 165
mvsjes2 Avatar answered Oct 03 '22 16:10

mvsjes2