title: SSL/TLS Connection reset - how to force Java client to use SNI?
body: <p>I had BOTH: a STS server and spring web application on localhost. And it worked. I've tested OAuth2 Authorization Code Grant Flow - fully working.</p>
  
  <p>I moved STS to other machine and there is a problem from web application in acquiring an access token - full trace (stop/error after redirection from STS; just in the beginning of acquiring token from: <code>https://sts-machine/authz/oauth2-resource/oauth/token</code> endpoint; stop at visiting url: <code>https://localwebapp:7443/swd/webLogin?code=306b88903d394f0b8145b2e8035fd306&amp;state=PtTrt8</code>):</p>
  
  <pre><code>SEVERE: Servlet.service() for servlet [swdServlet] in context with path [/swd] threw exception
  error="access_denied", error_description="Error requesting access token."
      at org.springframework.security.oauth2.client.token.OAuth2AccessTokenSupport.retrieveToken(OAuth2AccessTokenSupport.java:144)
      at org.springframework.security.oauth2.client.token.grant.code.AuthorizationCodeAccessTokenProvider.obtainAccessToken(AuthorizationCodeAccessTokenProvider.java:198)
      at org.springframework.security.oauth2.client.token.AccessTokenProviderChain.obtainNewAccessTokenInternal(AccessTokenProviderChain.java:142)
      at org.springframework.security.oauth2.client.token.AccessTokenProviderChain.obtainAccessToken(AccessTokenProviderChain.java:118)
      at org.springframework.security.oauth2.client.OAuth2RestTemplate.acquireAccessToken(OAuth2RestTemplate.java:221)
      at org.springframework.security.oauth2.client.OAuth2RestTemplate.getAccessToken(OAuth2RestTemplate.java:173)
      at org.springframework.security.oauth2.client.filter.OAuth2ClientAuthenticationProcessingFilter.attemptAuthentication(OAuth2ClientAuthenticationProcessingFilter.java:90)
      at org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter.doFilter(AbstractAuthenticationProcessingFilter.java:211)
      at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
      at org.springframework.security.oauth2.client.filter.OAuth2ClientContextFilter.doFilter(OAuth2ClientContextFilter.java:57)
      at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
      at org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:113)
      at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
      at org.springframework.security.web.session.SessionManagementFilter.doFilter(SessionManagementFilter.java:103)
      at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
      at org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter.doFilter(SecurityContextHolderAwareRequestFilter.java:154)
      at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
      at org.springframework.security.web.savedrequest.RequestCacheAwareFilter.doFilter(RequestCacheAwareFilter.java:45)
      at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
      at org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter.doFilterInternal(WebAsyncManagerIntegrationFilter.java:50)
      at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:108)
      at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
      at org.springframework.security.web.context.SecurityContextPersistenceFilter.doFilter(SecurityContextPersistenceFilter.java:87)
      at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
      at org.springframework.security.web.access.channel.ChannelProcessingFilter.doFilter(ChannelProcessingFilter.java:144)
      at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
      at org.springframework.security.web.FilterChainProxy.doFilterInternal(FilterChainProxy.java:192)
      at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:160)
      at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:344)
      at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:261)
      at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239)
      at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
      at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:219)
      at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:106)
      at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:503)
      at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:136)
      at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:79)
      at org.apache.catalina.valves.AbstractAccessLogValve.invoke(AbstractAccessLogValve.java:610)
      at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:88)
      at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:526)
      at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1078)
      at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:655)
      at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:146)
      at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:279)
      at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
      at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615)
      at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)
      at java.lang.Thread.run(Thread.java:745)
  Caused by: org.springframework.web.client.ResourceAccessException: I/O error on POST request for "https://sts-machine/authz/oauth2-resource/oauth/token":Connection reset; nested exception is java.net.SocketException: Connection reset
      at org.springframework.web.client.RestTemplate.doExecute(RestTemplate.java:557)
      at org.springframework.web.client.RestTemplate.execute(RestTemplate.java:510)
      at org.springframework.security.oauth2.client.token.OAuth2AccessTokenSupport.retrieveToken(OAuth2AccessTokenSupport.java:136)
      ... 47 more
  Caused by: java.net.SocketException: Connection reset
      at java.net.SocketInputStream.read(SocketInputStream.java:196)
      at java.net.SocketInputStream.read(SocketInputStream.java:122)
      at sun.security.ssl.InputRecord.readFully(InputRecord.java:442)
      at sun.security.ssl.InputRecord.read(InputRecord.java:480)
      at sun.security.ssl.SSLSocketImpl.readRecord(SSLSocketImpl.java:927)
      at sun.security.ssl.SSLSocketImpl.performInitialHandshake(SSLSocketImpl.java:1312)
      at sun.security.ssl.SSLSocketImpl.startHandshake(SSLSocketImpl.java:1339)
      at sun.security.ssl.SSLSocketImpl.startHandshake(SSLSocketImpl.java:1323)
      at sun.net.www.protocol.https.HttpsClient.afterConnect(HttpsClient.java:563)
      at sun.net.www.protocol.https.AbstractDelegateHttpsURLConnection.connect(AbstractDelegateHttpsURLConnection.java:185)
      at sun.net.www.protocol.https.HttpsURLConnectionImpl.connect(HttpsURLConnectionImpl.java:153)
      at org.springframework.http.client.SimpleBufferingClientHttpRequest.executeInternal(SimpleBufferingClientHttpRequest.java:78)
      at org.springframework.http.client.AbstractBufferingClientHttpRequest.executeInternal(AbstractBufferingClientHttpRequest.java:46)
      at org.springframework.http.client.AbstractClientHttpRequest.execute(AbstractClientHttpRequest.java:52)
      at org.springframework.web.client.RestTemplate.doExecute(RestTemplate.java:541)
      ... 49 more
  </code></pre>
  
  <p>So there is connection reset when webapp tries to exchange "code" from access token from: <code>https://sts-machine/authz/oauth2-resource/oauth/token</code>.</p>
  
  <p>Fun fact: Making request manually works well! (Manually exchanging code for access token) Tested with Chrome application "Advanced Rest Client Application" and with "Fiddler" request composer.</p>
  
  <p>I sniffed both machines using wiresharks. Same result on both - screenshot: <a href="http://i.imgur.com/2AYstN0.png" rel="nofollow">http://i.imgur.com/2AYstN0.png</a> (where: 10.1.0.121 is localwebapp machine, and: 10.1.0.80 is sts-machine)</p>
  
  <p><strong>Why there is connection reset?</strong></p>
  
  <p>Details about config:</p>
  
  <p>localwebapp: runs on tc Pivotal Server (kinda Tomcat), Win 8.1</p>
  
  <p>sts-machine: is Thinktecture Authorization Server on IIS, Win Server 2012</p>
  
  <h2>UPDATE 1</h2>
  
  <p>What I found out that:
  <code>openssl s_client -connect sts-machine:443</code> does not work, but:
  <code>openssl s_client -connect sts-machine:443 -servername sts-machine</code> does work! This indicates issue with the <a href="http://en.wikipedia.org/wiki/Server_Name_Indication" rel="nofollow">SNI</a> on Java client. Tried to solve problem with setting system property: <code>jsse.enableSNIExtension</code> to <code>true</code>, but without any success... <strong>How to enforce JVM to use SNI?</strong></p>