Special HTTP headers
Reading time: 11 minutes
tip
Ucz się i ćwicz Hacking AWS:HackTricks Training AWS Red Team Expert (ARTE)
Ucz się i ćwicz Hacking GCP: HackTricks Training GCP Red Team Expert (GRTE)
Ucz się i ćwicz Hacking Azure:
HackTricks Training Azure Red Team Expert (AzRTE)
Wsparcie dla HackTricks
- Sprawdź plany subskrypcyjne!
- Dołącz do 💬 grupy Discord lub grupy telegramowej lub śledź nas na Twitterze 🐦 @hacktricks_live.
- Dziel się trikami hackingowymi, przesyłając PR-y do HackTricks i HackTricks Cloud repozytoriów na githubie.
Wordlists & Tools
- https://github.com/danielmiessler/SecLists/tree/master/Miscellaneous/Web/http-request-headers
- https://github.com/rfc-st/humble
Headers to Change Location
Zamiana źródła IP:
X-Originating-IP: 127.0.0.1
X-Forwarded-For: 127.0.0.1
X-Forwarded: 127.0.0.1
Forwarded-For: 127.0.0.1
X-Forwarded-Host: 127.0.0.1
X-Remote-IP: 127.0.0.1
X-Remote-Addr: 127.0.0.1
X-ProxyUser-Ip: 127.0.0.1
X-Original-URL: 127.0.0.1
Client-IP: 127.0.0.1
X-Client-IP: 127.0.0.1
X-Host: 127.0.0.1
True-Client-IP: 127.0.0.1
Cluster-Client-IP: 127.0.0.1
Via: 1.0 fred, 1.1 127.0.0.1
Connection: close, X-Forwarded-For
(Sprawdź hop-by-hop headers)
Zamiana lokalizacji:
X-Original-URL: /admin/console
X-Rewrite-URL: /admin/console
Hop-by-Hop headers
Hop-by-hop header to nagłówek, który ma być przetwarzany i konsumowany przez proxy aktualnie obsługujące żądanie, w przeciwieństwie do nagłówka end-to-end.
Connection: close, X-Forwarded-For
HTTP Request Smuggling
Content-Length: 30
Transfer-Encoding: chunked
HTTP Request Smuggling / HTTP Desync Attack
The Expect header
Możliwe jest, że klient wyśle nagłówek Expect: 100-continue
, a serwer odpowie HTTP/1.1 100 Continue
, co zezwala klientowi na kontynuowanie wysyłania body żądania. Jednak niektóre proxy nie lubią tego nagłówka.
Ciekawe skutki użycia Expect: 100-continue
:
- Wysłanie żądania HEAD z body — serwer nie wziął pod uwagę, że żądania HEAD nie mają body i utrzymuje połączenie otwarte aż do timeoutu.
- Inne serwery wysyłały dziwne dane: losowe dane przeczytane z gniazda w odpowiedzi, secret keys albo nawet pozwalało to zapobiec usuwaniu wartości nagłówków przez front-end.
- Powodowało to także desync
0.CL
, gdy backend odpowiedział 400 zamiast 100, ale proxy front-end był przygotowany do wysłania body oryginalnego żądania, więc je wysłał i backend uznał to za nowe żądanie. - Wariant
Expect: y 100-continue
także spowodował desync0.CL
. - Podobny błąd, gdzie backend odpowiedział 404, wygenerował desync
CL.0
, ponieważ złośliwe żądanie wskazywałoContent-Length
, więc backend wysłał złośliwe żądanie +Content-Length
bajtów następnego żądania (ofiary). To rozregulowało kolejkę, bo backend wysyła odpowiedź 404 dla złośliwego żądania + odpowiedź dla żądań ofiary, ale front-end sądził, że wysłano tylko 1 żądanie, więc druga odpowiedź powędrowała do drugiego żądania ofiary, a odpowiedź tamtej do kolejnego...
Więcej informacji o HTTP Request Smuggling znajdziesz:
HTTP Request Smuggling / HTTP Desync Attack
Cache Headers
Server Cache Headers:
X-Cache
w odpowiedzi może mieć wartośćmiss
gdy żądanie nie było cache'owane i wartośćhit
gdy zostało zcache'owane- Podobne zachowanie w nagłówku
Cf-Cache-Status
Cache-Control
wskazuje, czy zasób jest cache'owany i kiedy nastąpi kolejna ważność:Cache-Control: public, max-age=1800
Vary
często używany jest w odpowiedzi do wskazania dodatkowych nagłówków, które są traktowane jako część klucza cache nawet jeśli normalnie nie są uwzględniane.Age
definiuje czas w sekundach, przez jaki obiekt przebywał w cache proxy.Server-Timing: cdn-cache; desc=HIT
także wskazuje, że zasób był zcache'owany
Cache Poisoning and Cache Deception
Local Cache headers:
Clear-Site-Data
: Nagłówek wskazujący, które cache'y powinny zostać usunięte:Clear-Site-Data: "cache", "cookies"
Expires
: Zawiera datę/czas wygaśnięcia odpowiedzi:Expires: Wed, 21 Oct 2015 07:28:00 GMT
Pragma: no-cache
to samo coCache-Control: no-cache
Warning
: Ogólny nagłówek HTTP zawierający informacje o możliwych problemach ze statusem wiadomości. Może wystąpić więcej niż jeden nagłówekWarning
w odpowiedzi.Warning: 110 anderson/1.3.37 "Response is stale"
Conditionals
- Żądania używające nagłówków:
If-Modified-Since
iIf-Unmodified-Since
zostaną zwrócone z danymi tylko jeśli nagłówek odpowiedziLast-Modified
zawiera inną datę. - Warunkowe żądania używające
If-Match
iIf-None-Match
używają wartości Etag, więc serwer wyśle treść odpowiedzi jeśli dane (Etag) uległy zmianie.Etag
jest pobierany z odpowiedzi HTTP. - Wartość Etag jest zazwyczaj obliczana na podstawie zawartości odpowiedzi. Na przykład,
ETag: W/"37-eL2g8DEyqntYlaLp5XLInBWsjWI"
wskazuje, żeEtag
jest Sha1 z 37 bajtów.
Range requests
Accept-Ranges
: Wskazuje czy serwer obsługuje range requests, i jeśli tak, w jakiej jednostce zakres może być wyrażony.Accept-Ranges: <range-unit>
Range
: Wskazuje część dokumentu, którą serwer powinien zwrócić. Na przykład,Range:80-100
zwróci bajty 80 do 100 oryginalnej odpowiedzi ze statusem 206 Partial Content. Pamiętaj też, aby usunąć nagłówekAccept-Encoding
z żądania.- To może być użyteczne, by otrzymać odpowiedź z arbitralnym reflektowanym kodem javascript, który normalnie byłby escapowany. Aby to nadużyć musiałbyś wstrzyknąć te nagłówki w żądaniu.
If-Range
: Tworzy warunkowe żądanie zakresu, które zostanie zrealizowane tylko jeśli podany etag lub data pasuje do zdalnego zasobu. Używane, by zapobiec pobieraniu dwóch zakresów z niekompatybilnych wersji zasobu.Content-Range
: Wskazuje, gdzie w pełnym ciele wiadomości mieści się fragmentowa wiadomość.
Message body information
Content-Length
: Rozmiar zasobu, w dziesiętnych bajtach.Content-Type
: Wskazuje typ mediów zasobuContent-Encoding
: Używany do określenia algorytmu kompresji.Content-Language
: Opisuje język(i) przeznaczenia dla odbiorców, pozwalając użytkownikowi rozróżnić zgodnie z preferencjami językowymi.Content-Location
: Wskazuje alternatywną lokalizację dla zwracanych danych.
Z punktu widzenia pentest ten zestaw informacji zwykle jest "bezużyteczny", ale jeśli zasób jest chroniony przez 401 lub 403 i potrafisz znaleźć jakiś sposób aby uzyskać te info, to może być to interesujące.
Na przykład kombinacja Range
i Etag
w żądaniu HEAD może is leaking zawartość strony przez żądania HEAD:
- Żądanie z nagłówkiem
Range: bytes=20-20
i z odpowiedzią zawierającąETag: W/"1-eoGvPlkaxxP4HqHv6T3PNhV9g3Y"
is leaking, że SHA1 bajtu 20 toETag: eoGvPlkaxxP4HqHv6T3PNhV9g3Y
Server Info
Server: Apache/2.4.1 (Unix)
X-Powered-By: PHP/5.3.3
Controls
Allow
: Ten nagłówek służy do komunikowania metod HTTP, które zasób może obsłużyć. Na przykład może być określony jakoAllow: GET, POST, HEAD
, wskazując, że zasób obsługuje te metody.Expect
: Używany przez klienta do przekazania oczekiwań, które serwer musi spełnić, aby żądanie zostało poprawnie przetworzone. Powszechnym zastosowaniem jest nagłówekExpect: 100-continue
, który sygnalizuje, że klient zamierza wysłać dużą ilość danych. Klient oczekuje odpowiedzi100 (Continue)
przed kontynuacją transmisji. Mechanizm ten pomaga optymalizować wykorzystanie sieci przez oczekiwanie na potwierdzenie serwera.
Downloads
- Nagłówek
Content-Disposition
w odpowiedziach HTTP określa, czy plik powinien być wyświetlony inline (w obrębie strony) czy traktowany jako attachment (do pobrania). Na przykład:
Content-Disposition: attachment; filename="filename.jpg"
To oznacza, że plik o nazwie "filename.jpg" ma zostać pobrany i zapisany.
Nagłówki bezpieczeństwa
Content Security Policy (CSP)
Content Security Policy (CSP) Bypass
Trusted Types
Wymuszając Trusted Types za pomocą CSP, aplikacje mogą być chronione przed atakami DOM XSS. Trusted Types zapewniają, że tylko specjalnie przygotowane obiekty, zgodne z ustalonymi zasadami bezpieczeństwa, mogą być używane w niebezpiecznych web API calls, co w efekcie domyślnie zabezpiecza kod JavaScript.
// Feature detection
if (window.trustedTypes && trustedTypes.createPolicy) {
// Name and create a policy
const policy = trustedTypes.createPolicy('escapePolicy', {
createHTML: str => str.replace(/\</g, '<').replace(/>/g, '>');
});
}
// Assignment of raw strings is blocked, ensuring safety.
el.innerHTML = "some string" // Throws an exception.
const escaped = policy.createHTML("<img src=x onerror=alert(1)>")
el.innerHTML = escaped // Results in safe assignment.
X-Content-Type-Options
Ten nagłówek zapobiega MIME type sniffing, praktyce, która może prowadzić do podatności XSS. Zapewnia, że przeglądarki respektują typy MIME określone przez serwer.
X-Content-Type-Options: nosniff
X-Frame-Options
Aby przeciwdziałać clickjackingowi, ten nagłówek ogranicza sposób, w jaki dokumenty mogą być osadzane w tagach <frame>
, <iframe>
, <embed>
, lub <object>
, zalecając, aby wszystkie dokumenty wyraźnie określały swoje uprawnienia dotyczące osadzania.
X-Frame-Options: DENY
Cross-Origin Resource Policy (CORP) i Cross-Origin Resource Sharing (CORS)
CORP jest kluczowy dla określania, które zasoby mogą być ładowane przez strony internetowe, co pomaga ograniczyć cross-site leaks. Z kolei CORS pozwala na bardziej elastyczny mechanizm udostępniania zasobów cross-origin, poluzowując same-origin policy w określonych warunkach.
Cross-Origin-Resource-Policy: same-origin
Access-Control-Allow-Origin: https://example.com
Access-Control-Allow-Credentials: true
Cross-Origin Embedder Policy (COEP) and Cross-Origin Opener Policy (COOP)
COEP i COOP są niezbędne do umożliwienia izolacji cross-origin, co znacząco zmniejsza ryzyko ataków podobnych do Spectre. Kontrolują one odpowiednio ładowanie zasobów cross-origin oraz interakcję z oknami cross-origin.
Cross-Origin-Embedder-Policy: require-corp
Cross-Origin-Opener-Policy: same-origin-allow-popups
HTTP Strict Transport Security (HSTS)
Na koniec, HSTS to funkcja bezpieczeństwa, która zmusza przeglądarki do komunikowania się z serwerami wyłącznie przez bezpieczne połączenia HTTPS, w ten sposób zwiększając prywatność i bezpieczeństwo.
Strict-Transport-Security: max-age=3153600
Header Name Casing Bypass
HTTP/1.1 definiuje nazwy pól nagłówka jako niezależne od wielkości liter (RFC 9110 §5.1). Mimo to bardzo często można natrafić na niestandardowe middleware, filtry bezpieczeństwa lub logikę biznesową, które porównują literalną nazwę nagłówka bez uprzedniego znormalizowania wielkości liter (np. header.equals("CamelExecCommandExecutable")
). Jeśli te sprawdzenia są wykonywane z rozróżnieniem wielkości liter, atakujący może je obejść, wysyłając ten sam nagłówek z inną kapitalizacją.
Typowe sytuacje, w których pojawia się ten błąd:
- Niestandardowe allow/deny lists, które próbują zablokować „niebezpieczne” nagłówki wewnętrzne zanim żądanie trafi do wrażliwego komponentu.
- Wewnętrzne implementacje pseudo-nagłówków reverse-proxy (np. sanitizacja
X-Forwarded-For
). - Frameworki, które udostępniają punkty końcowe zarządzania / debug i polegają na nazwach nagłówków przy uwierzytelnianiu lub wyborze polecenia.
Abusing the bypass
- Zidentyfikuj nagłówek, który jest filtrowany lub walidowany po stronie serwera (np. przez analizę kodu źródłowego, dokumentacji lub komunikatów o błędach).
- Wyślij ten sam nagłówek z inną kapitalizacją (wielkość liter mieszana lub wielkie litery). Ponieważ stosy HTTP zwykle kanonizują nagłówki dopiero po wykonaniu kodu użytkownika, podatne sprawdzenie można pominąć.
- Jeśli komponent downstream traktuje nagłówki bez rozróżniania wielkości liter (większość tak robi), zaakceptuje wartość kontrolowaną przez atakującego.
Example: Apache Camel exec
RCE (CVE-2025-27636)
W podatnych wersjach Apache Camel trasy Command Center próbują zablokować nieufne żądania przez usunięcie nagłówków CamelExecCommandExecutable
i CamelExecCommandArgs
. Porównanie było wykonywane za pomocą equals()
, więc usuwane były tylko nagłówki o dokładnie takim zapisie (z uwzględnieniem wielkości liter).
# Bypass the filter by using mixed-case header names and execute `ls /` on the host
curl "http://<IP>/command-center" \
-H "CAmelExecCommandExecutable: ls" \
-H "CAmelExecCommandArgs: /"
Nagłówki trafiają do komponentu exec
bez filtrowania, co skutkuje remote command execution z uprawnieniami procesu Camel.
Wykrywanie i łagodzenie
- Znormalizuj wszystkie nazwy nagłówków do jednego zapisu (zwykle małe litery) przed przeprowadzeniem porównań allow/deny.
- Odrzuć podejrzane duplikaty: jeśli obecne są zarówno
Header:
, jak iHeAdEr:
, potraktuj to jako anomalię. - Użyj pozytywnej allow-listy egzekwowanej po canonicalisation.
- Chroń endpointy zarządzania za pomocą uwierzytelniania i segmentacji sieci.
References
- CVE-2025-27636 – RCE in Apache Camel via header casing bypass (OffSec blog)
- https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Disposition
- https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers
- https://web.dev/security-headers/
- https://web.dev/articles/security-headers
tip
Ucz się i ćwicz Hacking AWS:HackTricks Training AWS Red Team Expert (ARTE)
Ucz się i ćwicz Hacking GCP: HackTricks Training GCP Red Team Expert (GRTE)
Ucz się i ćwicz Hacking Azure:
HackTricks Training Azure Red Team Expert (AzRTE)
Wsparcie dla HackTricks
- Sprawdź plany subskrypcyjne!
- Dołącz do 💬 grupy Discord lub grupy telegramowej lub śledź nas na Twitterze 🐦 @hacktricks_live.
- Dziel się trikami hackingowymi, przesyłając PR-y do HackTricks i HackTricks Cloud repozytoriów na githubie.