Path traversal (CWE-22) is a vulnerability class where an attacker manipulates file path input — typically by injecting sequences like ../ or their URL-encoded equivalents (%2e%2e%2f) — to make an application read, write, or execute files outside its intended directory. A request as simple as GET /images/../../../../etc/passwd can expose credentials, source code, or configuration secrets if the server doesn't normalize and validate the path before touching the filesystem. This isn't theoretical: CVE-2019-19781 in Citrix ADC/Gateway let unauthenticated attackers traverse to arbitrary files and plant malicious scripts, and CVE-2021-41773 in Apache HTTP Server 2.4.49 turned a path traversal bug into remote code execution within days of disclosure. Path traversal remains one of the most consistently exploited web application flaws because it's easy to introduce in file-handling code and easy for automated scanners to find — which also means it's one of the easiest classes to eliminate with the right controls.
How does a path traversal attack actually work?
A path traversal attack works by supplying relative path sequences that "walk" the filesystem outside a directory the application was designed to restrict access to. The canonical payload is ../ (dot-dot-slash), repeated enough times to climb from a web root like /var/www/html/images/ up to the filesystem root, then back down into sensitive files such as /etc/passwd, /etc/shadow, or application config files containing database credentials. Attackers rarely send the raw string, though, because naive filters often block literal ../. Instead they use encoding tricks: URL-encoding (%2e%2e%2f or %2e%2e/), double encoding (%252e%252e%252f), Unicode/overlong UTF-8 encoding, backslash variants on Windows (..\\), and null-byte injection (file.txt%00.jpg) to bypass extension checks on older platforms. In the Citrix ADC case (CVE-2019-19781, disclosed December 17, 2019), attackers combined traversal with the ability to write a Perl script into a reachable directory, escalating a file-read bug into unauthenticated remote code execution — CISA reported active exploitation against tens of thousands of exposed appliances within weeks.
What's the difference between path traversal, LFI, and directory listing?
Path traversal is the underlying technique; local file inclusion (LFI) and directory listing are two of the outcomes it enables. Path traversal describes manipulating a file path to escape a restricted directory — the mechanism. LFI happens when that escaped path is then passed into a function that includes or executes the file's contents (common in PHP apps using include($_GET['page'])), which can lead to code execution if an attacker can get PHP code onto the disk first, for example via log poisoning or file upload. Directory listing is a narrower, often lower-severity issue where a misconfigured server (e.g., Apache's Options +Indexes) reveals a full directory structure without requiring any traversal at all. Remote file inclusion (RFI) is the sibling of LFI where the included path points to an external URL instead of a local file. Security teams sometimes conflate these, but the distinction matters for remediation: fixing path traversal means canonicalizing and validating paths, while fixing LFI/RFI means also restricting what those paths can be used to do once resolved.
Which real-world breaches trace back to path traversal?
Several major incidents trace directly back to unpatched path traversal flaws, and the pattern repeats: a file-read bug becomes a full compromise once combined with a write primitive. CVE-2019-19781 (Citrix ADC/Gateway, CVSS 9.8) allowed traversal to arbitrary configuration files; within a month, security researchers documented active ransomware deployment on unpatched appliances, and Citrix confirmed exploitation was widespread enough to warrant emergency mitigations before a patch shipped. CVE-2021-41773, introduced in Apache HTTP Server 2.4.49 (released October 4, 2021), let attackers map URLs to files outside the document root; a follow-up bypass (CVE-2021-42013) turned it into RCE on servers with CGI enabled, and both were exploited in the wild before most organizations had patched. On the software-supply-chain side, the 2018 "Zip Slip" research from Snyk showed that dozens of popular Java, JavaScript, .NET, and Go archive-extraction libraries were vulnerable to path traversal via crafted filenames inside ZIP/TAR archives — meaning any application using an affected library to unzip user-supplied files inherited the flaw regardless of its own code quality.
How is path traversal classified and scored?
Path traversal is tracked as CWE-22 ("Improper Limitation of a Pathname to a Restricted Directory") in the MITRE CWE taxonomy, with related child weaknesses like CWE-23 (relative path traversal) and CWE-36 (absolute path traversal) covering specific variants. Under the OWASP Top 10 (2021 edition), it falls primarily under A01:2021 – Broken Access Control, the largest category in that release, covering 34 CWEs mapped to over 318,000 occurrences across the datasets OWASP analyzed. CVSS scores for path traversal vary widely by impact: a read-only information disclosure bug might score in the 5.3–7.5 range, while traversal that enables file write or chains into RCE — as with Citrix ADC and Apache HTTPD — routinely scores 9.0 or higher. CWE-22 has appeared in MITRE's annual "Top 25 Most Dangerous Software Weaknesses" list every year it has been published, consistently in the top 10, because it's both prevalent in scan data and severe in exploitability.
How can development teams actually prevent it?
The most reliable prevention is to never let user input construct a filesystem path directly — resolve the path first, then verify the result stays inside an allowed base directory. In practice: canonicalize the input path using the platform's own resolver (e.g., realpath() in PHP/C, Path.resolve() in Node, os.path.realpath() in Python) before any file operation, then confirm the resolved absolute path starts with the expected base directory string. Reject requests containing ../, ..\\, null bytes, or their encoded forms outright rather than trying to strip them (naive stripping is exactly what encoding-bypass techniques exploit). Where possible, avoid passing user input into file APIs at all — map user-facing identifiers to internal file references through a lookup table or database ID instead of a raw filename. For archive extraction specifically, validate that every extracted entry's resolved path stays within the target directory before writing it to disk, which is the direct fix for Zip Slip–class bugs. Finally, run web servers and application processes with least-privilege filesystem permissions so that even a successful traversal has a limited blast radius.
How Safeguard Helps
Safeguard's reachability analysis pinpoints which instances of CWE-22 in your codebase or dependencies are actually exploitable — for example, flagging a vulnerable archive-extraction library only when your code calls the unsafe extraction path with attacker-influenced input, rather than every package that merely bundles it. Griffin AI, Safeguard's agentic security engine, traces the full data flow from user-controlled input to filesystem sink to confirm exploitability and cuts through the noise scanners generate on path-handling code. Safeguard's SBOM generation and ingest capabilities give teams a live inventory of every archive, template, or file-serving library in use, so a disclosure like a new Zip Slip variant can be matched against your actual exposure in minutes instead of days. When a fix is available, Safeguard opens an auto-fix PR with the corrected path-validation logic or dependency bump already applied, so remediation ships as fast as detection.