Look at the address bar
after your login page
catches somebody
who was not signed in.
There is usually a parameter
on the end of it.
Next. Return. Continue.
It remembers where the person
was trying to go,
so that after the password
you can send them back.
A kind feature.
Now read it the other way.
It is a field in a URL
that decides where your site
sends a freshly signed in user,
and anybody can write URLs.
So somebody writes one.
It starts with your real domain.
Your real certificate.
Your real login page,
with your logo,
because it is yours.
Everything the security training
told people to check
checks out.
The person signs in,
properly,
on the genuine page.
And your site, obligingly,
forwards them to the address
at the end of the link,
which looks like your site
and says the session timed out,
please enter your password again.
They have just done it once.
Doing it twice feels like
the kind of thing computers
make you do.
You lent the attacker
the moment when a user
trusts a page the most,
right after they proved
who they are.
It gets worse where tokens travel.
A sign in flow that attaches a code
to the redirect
hands that code
to wherever the redirect points.
And the checks people write first
are the ones that fail.
Starts with a slash,
until two slashes
mean another host.
Contains our domain,
until our domain
turns up inside
somebody else's address.
A backslash some browsers read
as a slash.
An encoded character
that becomes the thing it encodes.
So do not parse your way to safety.
Keep the destination
on your side.
Store where they were going
in the session
and put an opaque key in the URL,
or accept only paths
you rebuild yourself,
on your own host,
from a short list of places
a person can legitimately return to.
Anything else
lands on the home page.
Nobody has ever complained
about arriving at the home page.
Then search your code
for every response
that takes its location
from the request.
Each one is a signpost
that anybody can repaint.
– Serguey Asael Shinder
Top comments (0)