secure web authentication using cookies
i'm developing a PHP web application and the main focus of the app is security. Until now i've stored the authentication data into 2 cookies:
- one cookie for a unique hash string (30 chars)
- one cookie for a unique id (the primary key of the mysql database table which holds the cookie info and user id)
Db tables look like this:
- Users (user_id, username, password)
- Cookies (cookie_id, user_id, hash, time, ip)
When a user visits the page the app checks for existing cookies (cookie check) on the client and compares them to the database table Cookies. If the hash string and the id match, the session is extended and if they don't, the session is destroyed (if exists) and the user is prompted to login. It also checks if the session expired by comparing the current time stamp to the time stamp of the last activity.
When the user 开发者_如何学Pythonlogs in a hash strings is generated and stored in the database (the current time stamp and IP is also stored). The primary id of the newly generated row and the hash string are then stored into two cookies and used for authentication.
I would like to implement additional security to prevent dictionary or brute force attacks, by throttling the login and cookie check attempts. I'd like to achive that when the user fails N times to login or to validate cookies that he gets blocked for 20 minutes. But if i do this using the IP i would potentially block every user using that IP.
I could lock the specific user account when there are more than X failed attempts, but the problem is when the attacker doesn't supply a valid username (so i would have to block the whole IP for N minutes).
The login form has also a captcha check, but that just slows down a attack (nothing compared to denying login attempts for X minutes).
- Is there any other way of denying login attempts without blocking out the whole network using that IP?
- Should i bother with denying login attempts when there are N failed cookie checks?
- If the users cookies are stolen, i use the IP in Cookie table to prevent reusing it, so the cookies are usable only from the same IP as the users. Is this secure or should i do it somehow else?
Thanks in advance,
PS: all passwords in database are hashed, the cookie values are encoded before used in a db query (so injections aren't possible).
I'm developing a PHP web application and the main focus of the app is security
If you care about security You should not implement authentication yourself, but use OpenID just like stackoverflow.com => http://www.codinghorror.com/blog/2008/05/openid-does-the-world-really-need-yet-another-username-and-password.html
LightOpenID is a very nice/easy openID library => http://gitorious.org/lightopenid
I would like to implement additional security to prevent dictionary or brute force attacks, by throttling the login and session check attempts. I'd like to achive that when the user fails N times to login or to validate cookies that he gets blocked for 20 minutes. But if i do this using the IP i would potentially block every user using that IP.
P.S: I would use OpenID, but below I will tell how I would do this.
The blocking of IP's is bad like you are saying, because a lot of users share them same IP via NAT. but when you suspect brute-force attack(from IP) I would just let them authenticate only if they enter the captcha correctly. This way the users behind NAT can still login while the hacker is shut out.
The login form has also a captcha check, but that just slows down a attack (nothing compared to denying login attempts for X minutes).
When you protect your site with captcha, hacking your site is almost impossible if length of passwords is long enough(you should enforce this). Because let's say you can solve a captcha in 5 seconds, which comes to 12 captchas per minute. What you could do is lock out an account when attempted a number of times. You sent a very long string to the users account which he can use to set a new password
Security is not achieved by complicated code, but by simplicity. Instead of inventing your own session handling, you should use php's builtin one.
Also, there's no reason to store the user name in a cookie, doing so only makes your application prone to all kinds of vulnerabilities caused by mismatch between user and session. Instead, store the user's ID with each session entry.
You should rate-limit authentication attempts (i.e. password entries), possibly with CAPTCHAs, or better yet, not store passwords at all and use OpenID. Also, just hashing passwords is not enough; make sure to use a salt.
精彩评论