Prerequisite. This lesson builds directly on how HTTP responses are structured. If you have not yet completed the [HTTP Fundamentals](/#/) lesson, do that first — the concepts of status lines, headers, and response bodies are assumed knowledge here.
Practical prerequisite. The hands-on exercise in step 3 requires an intercepting proxy (Burp Suite or ZAP) to view raw response headers — a browser does not expose them. If you have not set up Burp Suite yet, complete the [Intercepting Proxies](/#/) lesson before reaching that step.
Every time your browser loads a page, the server sends back an HTTP response — a block of plain text with a strict shape: a status line, a block of headers, a blank line, and then the body. For example:
HTTP/1.1 302 Found
Location: /dashboard
Set-Cookie: lang=en
<html>Redirecting…</html>That blank line between the last header and the body is the key to everything in this lesson. The character that ends each header line — and, doubled, ends the whole header block — is the CRLF: a carriage return (\r, %0d) followed by a line feed (\n, %0a).
This lesson is about what happens when your input reaches a response header carrying those bytes. If a server copies an attacker-controlled value into a header without stripping CR and LF, the attacker can write new header lines — and with a doubled CRLF, end the headers early and write their own response body. That is CRLF injection, and the body-writing form is HTTP response splitting.
Authorised targets only. Forging headers, planting cookies, splitting responses, and poisoning caches are active attacks on a live service. Use only a lab you own or an app you are explicitly authorised to test — a PortSwigger Web Security Academy lab, a local DVWA, or your own app that reflects a parameter into a header. Review [Hacking Ethics and Authorization](/#/) first. NovaCart has no clear native CRLF challenge, so this lesson requires an external authorised lab.
In this lesson you will:
- See exactly how HTTP uses **
\r\nto delimit headers and\r\n\r\n** to end them. - Learn the encodings of CR/LF (
%0d%0a, the bare%0a, and the bare%0d) and why a single-string blacklist never holds — advanced bypass forms such as double-encoding and overlong/Unicode are covered in a callout box in the next step. - Map the impacts (each explained in full on the next screen):
Set-Cookieinjection / session fixation (forcing a victim to use a session ID the attacker controls), response splitting → reflected XSS, cache poisoning, and log forging. - Find a header-reflected parameter on a lab and inject an encoded CRLF.
- Take away the durable fix: never reflect raw input into a header — strip CR/LF, use an encoding header API, and allow-list redirect targets.
Click Continue when you are ready.