8

For a rich client web app, on the server I need to verify that each call comes from a legally logged in user. Obviously user ID is not enough, because that's easy to guess.

I have an idea I am skeptical about, but can't think of rational reasons not to do it.

Is using password hash protected with a sufficiently strong hashing function (bcrypt?) a good session identifier? It already is in DB, is unique for each user and cannot be guessed easily. I am using a secure channel (HTTPS) for all communications between the client and server, so I don't have to worry about eavesdropping on the session identifier.

I don't care about session expiration, state or being logged in from two computers at a time. The server app is stateless enough. All I really need is user ID and some extra means of verification that he has logged in properly.

8
  • 1
    Hi @Konrad, is this not the same question as your other question from earlier today, security.stackexchange.com/questions/4936/… ? What is the difference to you?
    – AviD
    Commented Jun 30, 2011 at 18:07
  • 1
    It's completely different. That one was whether It's better to send password or hash on authentication over an insecure channel. This one is about using password hash for identifying an open session over a secure channel. What are the possible risks? Should I avoid sending hash to client and using it this way? Commented Jun 30, 2011 at 19:24
  • 1
    @Konrad - ah, I see your point: your questions stem from certain assumptions, leading you to believe (in your point of view) that these are conceptually different; since I claim your assumption basis is faulty, they equivilate (in my PoV) to pretty much the same thing. I'm not meaning to be condescending here (and sorry if it seems that way), but this explains why the questions are in fact different, even if there is a single answer for both. Am I correct in understanding your meanings?
    – AviD
    Commented Jun 30, 2011 at 19:28
  • 1
    Can you explain which assumptions are faulty? I agree they are very similar, but I don't think they have the same answer. Secure authentication over insecure channel is different from session maintenance over secure channel. What I'm trying to find here is whether having this kind of key is secure - the fact that it's static, as well as that it's directly related to password management. Commented Jun 30, 2011 at 19:39
  • 1
    @Konrad, the answers here + my answer on the other question pretty much explain that. Point is, its not just not secure, it adds no value and the hash becomes a replacement for the password.
    – AviD
    Commented Jun 30, 2011 at 19:57

4 Answers 4

14

One problem you could have with this kind of setup is, from what you've said, it looks like the session token would be static (ie for a given user, it never changes, until they change their password). As such if an attacker manages to get access to a token for a given user (trojan, keylogger, packet sniffing (if SSL isn't used) etc), they will have persistent access to the application.

Also you'd need to be more careful than usual to ensure that session tokens aren't logged anywhere server-side as they'd essentially be as good as passwords.

5
  • 1
    This is a good point, but... If they are able to install a trojan or keylogger on client, there's little difference between capturing a password on login and capturing the hash (or session ID) later. Commented Jun 30, 2011 at 19:32
  • 2
    +1. Imagine an XSS vulnerability where attackers can easily exfiltrate your session IDs. In most systems, the session ID changes over time, so exfiltrated sessions keys won't work after the user logs out -- they have a short lifespan. But if you re-use the same session keys on every request, then lifespan is much longer. The attacker just has to wait for that user to log in again, and then they can easily steal the session. Commented Jul 1, 2011 at 15:34
  • 2
    @Konrad, your point about passwords is somewhat valid, but consider that the password typically gets transferred ONCE per session, while the session ID gets sent with every single request. Therefore, the session ID is much easier to steal than the password. Commented Jul 1, 2011 at 15:35
  • @mehaase Good points (both of them). I think my thick client with TLS is invulnerable to XSS. For a determined attacker, capturing one request is not much more difficult than capturing more of them (and that's not a problem with TLS). Commented Jul 1, 2011 at 15:46
  • Anyway, the point about gaining permanent access and having more places to secure (not just one request handler) makes much sense. Commented Jul 1, 2011 at 15:48
7

I don't know what libraries you are using for writing your application, but most provide some sort of session management.

The implication of using a password hash a session token, you will not be able to tell one session from another. And what if two users have the same password? Will you be able to tell the difference?

Further, you will make yourself vulnerable to replay attacks, unless you choose to add some random data to the session token. This you must store in a persistent storage somewhere.

When you already have gone this far, you should choose to generate the whole session token, since you already need i.e. a session table.

For a HTTPS channel, anything goes as long as no one is able to read your cookies (remember https only cookies!) or guess them.

4
  • I don't care about one session per user. Hash is not the only user identifier - I also pass user ID for some other reasons. There's no cookies, it's a rich client. This is also the reason why reusing a session mechanism is more difficult. Replay attacks are just as possible with session ID. And I assume HTTPS is there. Commented Jun 30, 2011 at 17:02
  • As for session management, you can choose to transfer the session id's with other methods than cookies, but the same security implications will apply, independently if its a rich or thin application. Commented Jun 30, 2011 at 17:10
  • 1
    Right, the only difference between rich client and browser client, is that the browser will automatically send the cookies on each request - whereas (I assume) you need to explicitly force the rich client to send the session details.
    – AviD
    Commented Jun 30, 2011 at 18:09
  • @AviD Right. I was replying to the "use a library for sessions" point. The main question is not how session works, but whether this kind of ID is secure. Commented Jun 30, 2011 at 19:30
3

A good session cookie will prepend an expiration to the serialized data and then prepend an HMAC of the expiration + serialized data to the expiration + serialized data using the application's secret key.

message = serialize_to_bytes(session_data)
random = random_bytes(16)
expiration = unix_timestamp_as_16_bytes(now + 2 * 60 * 60 /*2 hours*/)
signable = random + expiration + message
signature = HMAC-SHA256(application_key, signable)
signed_message = signature + signable

The signed_message will be unforgeable. It will be subject to replay attack for 2 hours. If the signed session cookie is hacked within the 2-hour window, the session could be infinitely extended. To do better, you would need to come up with a good scheme for nonces. In a large application with multiple web servers serving session cookies, that would require a central database of used nonces, which can be unwieldy.

Be sure to set the cookie's secure flag (so that it only is sent in HTTPS requests) and httponly flag (so that it is not available to JavaScript directly).

Be sure to use SSL always.

3

The proposed approach strikes me as a poor approach. Let the web framework do session management for you. Many web frameworks will already provide support for user authentication and will let you, in a single call, query whether there is a logged-in user associated with the session of the current request. Just use that. Rolling your own is dangerous. I don't understand why you need or want to roll some special-purpose mechanism for this.

3
  • Right. I wouldn't do it with browser-based client. I'm talking about a rich desktop client which does not really use HTTP. I know the difference between SSL and session management. Mentioned it only to prevent answers talking about channel security. Commented Aug 3, 2011 at 7:27
  • 1
    A rich desktop client doesn't seem like it changes anything substantial. There's still no way to specify a particular session key for HTTPS. As far as I can see, the proposal mentioned in the question doesn't make sense and can't be implemented.
    – D.W.
    Commented Aug 3, 2011 at 21:18
  • @JoóÁdám, thank you. Based on Konrad's response, you were totally correct: I had misunderstood what scheme he was proposing. I have edited the question to clarify it, per Konrad's comment, and I have edited my answer to remove the problematic statements. Thank you for noticing this and helping us to set it straight!
    – D.W.
    Commented Sep 22, 2015 at 15:53

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .