SkillGridLearn computer science by doing

Web security: never trust user input

Injection, XSS and CSRF are three versions of one mistake: treating something a stranger typed as if it were a command.

15 min · 48 XP

Every web vulnerability you will meet at this level is one rule broken: never trust input that came from outside your program. Your browser, your form, your API and your cookie are all outside. The input is not "bad" — it is perfectly valid text. The bug is that your program stopped treating it as data and let it become part of a command, a query, a page or a request.

the page builds a greeting from the name you typed

name you typed:   Ada
page shows:       Hello, Ada

name you typed:   <script>...</script>
page shows:       the browser obeys the script instead of printing it

cause: the server put your text into the page without escaping itThe user typed text. The page decided it was markup. The browser had no way to tell the difference.

SQL injection is the same mistake, one layer down. If code glues user text into a SQL string, then a value like an email address stops being a value and becomes part of the query grammar. The classic example is a login form where the text after a quote turns the rest of the query into a comment. The defence is not to search for quote characters: it is to use parameters, so the database always receives the query structure and the values separately and never has to guess which is which.

SELECT id, email FROM users
WHERE email = 'student@example.org' AND password_hash = '...';

-- the same query, built by gluing user input into the text:
--   1 OR 1=1 --
-- the condition stops being a condition and becomes a statementA value glued into the query text becomes query text. A parameter stays a value, however strange it looks.
VisitorAppOther userPOST /transfer to=me&amount=100the browser is told to send this, not askedcookie is attached by the browsermoney moves, and the app believed it was Ono password was ever stolen

Practice

  1. A login form builds its query by gluing text together. Which change actually removes the SQL injection?

    Hints
    • Find the place where the text stops being data and starts being part of the command.
    • Quotes are not the same thing as a parameter: one is punctuation, the other is a value the database keeps separate.

    15 XP

  2. Match each attack with the piece of the system that runs the attacker's text.

    Hints
    • Ask which program ends up running the attacker's text: the database, the browser, or the shell.
    • The fix is always the same idea, but the place where you apply it differs.

    15 XP

  3. Write isSafeNickname(name) that accepts only letters, digits and underscores, 3 to 16 characters. This is a block-list-hostile check: describe what is allowed instead of what is banned.

    Hints
    • An allow-list compares against the values you accept; a block-list removes the values you happened to think of.
    • Length is a cheap check that stops huge payloads before anything else runs.

    18 XP