Apache Ignite seems to cause session fixation - session

I'm using Apache Ignite to cluster web sessions, and use Spring security to do the form-based authentication. The software I use are:
JDK 1.8.0_60
Apache Tomcat 7.0.68
Apache Ignite 1.5.0.final
Spring Security 3.1.3.RELEASE
(Without Apache Ignite, the form based authentication works fine, and the JSESSIONID cookie gets changed upon the success of authentication to protect against session fixation attacks, as expected.)
With Apache Ignite, I cannot log in, and I get the following warning:
2016-04-18 16:49:07,283 WARN org.springframework.security.web.authentication.session.SessionFixationProtectionStrategy/onAuthentication 102 - Your servlet container did not change the session ID when a new session was created. You will not be adequately protected against session-fixation attacks
If I turn off session fixation protection in the Spring configuration as below:
<http>
...
<session-management session-fixation-protection="none" />
...
</http>
It works. (However as a result, the JSESSIONID cookie does not change upon the success of authentication.)

As advised by Valentin (, thanks), I tried the nightly build from Apache Ignite, of version 1.6.0-SNAPSHOT#20160419-sha1:186c8604. Indeed, it works.
It works with the following Spring security configuration:
<http>
...
<session-management session-fixation-protection="none" />
...
</http>
And of course the JSESSIONID cookie does not change upon the success of Spring security authentication.
Then I comment out the following configuration:
<session-management session-fixation-protection="none" />
It also works. And upon the success of authentication, the JSESSIONID cookie gets changed as it is supposed to do.
OK, I'll use Ignite version 1.5.0.final for now (with no session-fixation-protection), and wait for the release of version 1.6.x.

Tomcat 7 has in-built functionality for session fixation,
Changing the jsessionid on authentication to prevent session fixation attacks altogether
Tomcat is not letting the application to change the session ID.

Related

changeSessionIdOnAuthentication in WebSphere 8.5?

Our security team ran a scan that tells us that we're vulnerable to session fixation and the docs tells us that in tomcat we should use the changeSessionIdOnAuthentication setting in context.xml.
What would be the equivalent move in WebSphere 8.5?
I had the same issue with WAS 8.5. Ended up using spring security to configure the session fixation issue.
<security:session-management invalid-session-url="/login" session-authentication-error-url="/login" session-fixation-protection="newSession">
<security:concurrency-control error-if-maximum-exceeded="true" max-sessions="1" expired-url="/login"/>
WebSphere 8.5 is using a servlet api version that is < 3.1, therefore you can't use changeSessionId() method of HttpServlet Request.
What you can do instead is, at the point where you are authenticating your user in your application, probably, attemptAuthentication() or similar methods, you can do:
HttpSession session = request.getSession(false);
if(session != null)
session.invalidate();
session = request.getSession();
The above provides protection against session fixation attack.

httpsession lifecycle events not working after using my custom UserDetailsService

I've created my own UserDetailsService and UserDetails implementations and hooked it up. I can create users, and login as users. However, if I login, logout, and then login again, I'm getting a redirect to a timeout error page. This is because I'm preventing concurrent logins, but it's not working - it used to with the "hello world" auth examples, but now with my own implementations that piece has stopped working correctly for some reason. Spring basically thinks there are 2 sessions when I login, logout, and login again.
Now - I thought this was all handled automatically ....perhaps using your own UserDetailsService means you actually have to implement session management somewhere else as well? I'm sort of blown away that's not mentioned in the docs or in the book Spring Security 3.1 so I'm assuming I'm missing something.
This is in my web.xml bit for listening to session life cycle events
<!-- This listener updates spring-security on httpsession lifecycle events,
in this case to ensure each user can have only 1 session at a time. -->
<listener>
<listener-class>org.springframework.security.web.session.HttpSessionEventPublisher</listener-class>
</listener>
and this is in my security.xml to prevent concurrent logins
<!-- This prevents the user from logging in more than once simultaneously -->
<security:session-management
invalid-session-url="/timeout.htm">
<security:concurrency-control
max-sessions="1" error-if-maximum-exceeded="true" />
</security:session-management>
My logout in the security context file is
<security:logout logout-url="/logout"
invalidate-session="true" delete-cookies="JSESSIONID,SPRING_SECURITY_REMEMBER_ME_COOKIE"
logout-success-url="/login.htm?logout" />
I've tried a few permutations of that. None seem to work. invalidate-session="true" is the default value, so I shouldn't even have to specify this. But it doesn't seem to be happening.
O.k., I just reverted everything to try and do in-memory auth and I'm getting the same errors. Meaning, I'm not using my custom implementations anymore. Sorry - I clearly have something wrong somewhere...and this is proving extremely difficult to find. I might have to start from scratch.
Do I have to do something special on logout with my custom UserDetailsService?
Any feedback or guidance is much appreciated.
To my understanding the error-if-maximum-exceeded attribute should be false. Settings the value to false will cause the original session to expire instead of throwing a exception as explained in http://docs.spring.io/spring-security/site/docs/3.0.x/reference/appendix-namespace.html#d0e7768
I discovered it was a conflict between using <session-management> in my configuration and my servlet container. I'm using STS 3.5 (custom Eclipse for Spring projects) with vFabric server that runs in the IDE. The Reference documentation did not refer to this in the actual Session Management section (Section 8). However, buried in Section 4 on auth is this little gem:
Note that if you use this mechanism to detect session timeouts, it may falsely report an error if the user logs out and then logs back in without closing the browser. This is because the session cookie is not cleared when you invalidate the session and will be resubmitted even if the user has logged out. You may be able to explicitly delete the JSESSIONID cookie on logging out, for example by using the following syntax in the logout handler:
<http>
<logout delete-cookies="JSESSIONID" />
</http>
Unfortunately this can’t be guaranteed to work with every servlet container, so you will need to test it in your environment
Well, apparently it doesn't work in STS 3.5
At first I tried to eliminate sections of my <session-management> tag so I could just control concurrency (i.e. have the user only able to log in with one session at a time). However, I just kept getting errors.
So, at this point I've removed the session management stuff altogether and will come back to it when ready to deploy.

Redis as a session store in glassfish

I got an open-source component called tomcat-redis-session-manager can store http session in redis, to provide high-availability in many tomcat servers.
So I want to find if there is a way to store glassfish http session in redis or memcached.
But I have not find what is the http session creation or acquire interceptor in glassfish.
Can anyone tell me how?
Tomcat does it by adding the following in context.xml
<Valve className="com.radiadesign.catalina.session.RedisSessionHandlerValve" />
<Manager className="com.radiadesign.catalina.session.RedisSessionManager"
host="localhost"
port="6379"
database="0"
maxInactiveInterval="60"
/>

Changing JSESSION ID with Tomcat 7

According to the tomcat docs, tomcat7 is not vulnerable to session fixation attack. But my tomcat 7.0.25 as well as 7.0.27 is vulnerable to this attack. JSESSIONID cookie value is not getting changed on successful login.
I added following Valves to my conf/context.xml. But this didn't work. Please help me.
<Valve className="org.apache.catalina.authenticator.BasicAuthenticator" changeSessionIdOnAuthentication="true" />
<Valve className="org.apache.catalina.authenticator.SSLAuthenticator" changeSessionIdOnAuthentication="true" />
<Valve className="org.apache.catalina.authenticator.SpnegoAuthenticator" changeSessionIdOnAuthentication="true" />
<Valve className="org.apache.catalina.authenticator.DigestAuthenticator" changeSessionIdOnAuthentication="true" />
<Valve className="org.apache.catalina.authenticator.FormAuthenticator" changeSessionIdOnAuthentication="true" />
I have also come to know that JSESSION ID cookie value only changes on authentication. What does authentication means ? Is it switching the application from http to https ?
Is there anything already built which can change the the jsession id value on login ? Right now I am changing this via code.
Thanks in advance. Please let me know if you need more info.
Regards,
Prashant Gupta
Are you sure your application uses server security.
These configuration only affect this behaviour if you're using it.
If your authentication uses for example custom or spring security authentication they will not apply and you will have to do this yourself.
For example in spring sec there are parameters for that.
Regards

Acegi pligin not enabling HTTPS with 'forceHttps' param

I am working on an old application which has huge code from legacy.
Application is based on Spring 2.0 and using Acegi plugin for security. The Tomcat server is successfully configured on HTTPS port.
Now I need to redirect the login over HTTPS. I tries setting following in my template_spring_config.xml
<bean id="authenticationEntryPoint" class="src.auth.acegi.myAuthenticationProcessingFilterEntryPoint">
<property name="loginFormUrl" value="http://#domain.name#/welcome"/>
<property name="forceHttps" value="true"/>
</bean>
Help found so far indicates that this much should be enough to redirect on HTTPS. But this is not working at all and my Request for login remains on HTTP.
I cannot switch to Spring-Security and higher Spring versions due to time constraint.
Please help if you know what else I need to do.
It's difficult to say for sure since you are using a custom entry point implementation (which may behave differently), but you are using an absolute URL, which will probably override the default logic for building the redirect. Try using https:// rather than http:// for your login URL scheme.
Note that you really shouldn't be using Acegi since development stopped on it a long time ago. It contains most (possibly all) of the vulnerabilities that have subsequently been patched in Spring Security. The same goes for Spring itself.

Resources