Session Fixation

An attack where the attacker sets a victim's session ID to a known value, then waits for the victim to authenticate, allowing the attacker to hijack the authenticated session.
HIGH SEVERITY SESSION HIJACKING AUTHENTICATION
What is Session Fixation?
Session Hijacking
Session Fixation allows attackers to hijack authenticated sessions by forcing victims to use attacker-controlled session IDs. Unlike session theft, the attacker sets the session ID BEFORE the victim logs in.
In Simple Terms:
Imagine a hotel key card system. Session Fixation is like:
- Attacker gets blank key card from hotel
- Attacker gives YOU the blank card
- You check in using that card - hotel activates it
- Attacker uses their copy of the SAME card to access your room!
How It Works
Attack Flow
Attacker visits site: https://bank.com
Receives session cookie: SID=abc123
html<!-- Phishing email link -->
<a href="https://bank.com/login?SID=abc123">
Login to your account
</a>
OR via cookie injection:
html<script>
document.cookie = "SID=abc123; domain=bank.com";
</script>
Victim clicks link
Logs in with credentials
Session abc123 is now authenticated!
Attacker uses same SID=abc123
Now has access to victim's account!
Real-World Example
Banking Platform Attack (2018)
Vulnerability: Session ID accepted from URL parameter
Attack:
1. Attacker sends email:
"Verify your account: bank.com/login?sessionid=ATTACKER123"
2. 5000 users click link and login
3. Attacker uses sessionid=ATTACKER123 → Access to all 5000 accounts!
Impact:
- $8 million stolen
- 5000 accounts compromised
- Bank sued for negligence
Prevention
1. Regenerate Session on Login
python@app.route('/login', methods=['POST'])
def login():
username = request.form['username']
password = request.form['password']
if authenticate(username, password):
# CRITICAL: Regenerate session ID after login
session.regenerate()
session['user_id'] = user.id
session['authenticated'] = True
return redirect('/dashboard')
2. Don't Accept Session ID from URL
python# SECURE: Only accept session from cookies
app.config['SESSION_COOKIE_HTTPONLY'] = True
app.config['SESSION_COOKIE_SECURE'] = True
app.config['SESSION_COOKIE_SAMESITE'] = 'Strict'
# Ignore session ID in URL/POST data
@app.before_request
def validate_session_source():
if 'sessionid' in request.args or 'SID' in request.args:
return "Invalid request", 400
3. Bind Session to User Agent/IP
pythondef create_session(user_id):
session_id = generate_secure_token()
# Bind to user context
session_data = {
'user_id': user_id,
'user_agent': request.headers.get('User-Agent'),
'ip_address': request.remote_addr,
'created_at': time.time()
}
redis.setex(f'session:{session_id}', 3600, json.dumps(session_data))
return session_id
def validate_session(session_id):
data = json.loads(redis.get(f'session:{session_id}'))
# Validate binding
if data['user_agent'] != request.headers.get('User-Agent'):
return False
if data['ip_address'] != request.remote_addr:
return False
return True
Security Checklist
- [ ] Regenerate session ID after login
- [ ] Never accept session ID from URL parameters
- [ ] Use HttpOnly, Secure, SameSite cookies
- [ ] Implement session binding (IP, User-Agent)
- [ ] Set session expiration
- [ ] Clear old session on logout
- [ ] Use cryptographically secure session IDs
- [ ] Implement CSRF protection
Last Updated: November 2025