← CodeClarityLab Home
Browse by Category
+ added · updated 7d
← Back to glossary

realpath()

php PHP 5.0+ Intermediate

Also Known As

realpath() PHP canonical path resolve symlinks

TL;DR

Resolves a path to its canonical absolute form, collapsing ../ sequences — used to prevent path traversal.

Explanation

realpath($path) resolves all symbolic links, /../ and /./ sequences, and redundant separators to produce the canonical absolute path. It returns false if the file doesn't exist. The standard path traversal guard is: $real = realpath($base . '/' . $userInput); if ($real === false || strpos($real, $base) !== 0) { deny; }. This ensures the resolved path starts with the intended base directory, regardless of what the user submitted.

Common Misconception

realpath() is safe to use on any user-supplied path. realpath() resolves the canonical path including symlinks — it returns false for non-existent paths, which must be checked. Always verify the resolved path starts with the expected base directory before using it.

Why It Matters

realpath() resolves symlinks, . and .. components, and returns the canonical absolute path — it is the essential step before comparing user-supplied paths to allowed base directories.

Common Mistakes

  • Checking path prefix before calling realpath() — traversal sequences pass the check but resolve differently.
  • Not handling realpath() returning false for non-existent paths — the comparison silently fails.
  • Using realpath() without checking that the result starts with the intended base directory.
  • Trusting that realpath() sanitises the path for security without the subsequent base-directory check.

Code Examples

✗ Vulnerable
// Check before realpath — bypassable:
$path = '/var/www/uploads/' . $_GET['file'];
if (str_starts_with($path, '/var/www/uploads/')) {
    readfile($path); // ../../etc/passwd passes the check!
}

// Correct:
$real = realpath('/var/www/uploads/' . $_GET['file']);
if ($real === false || !str_starts_with($real, '/var/www/uploads/')) die('Denied');
readfile($real);
✓ Fixed
// realpath() resolves ../, ./, symlinks to canonical absolute path
// Returns false if path doesn't exist
\$base = realpath('/var/www/uploads');
\$path = realpath(\$base . '/' . \$_GET['file']);

if (\$path === false) abort(404);  // file doesn't exist
if (!str_starts_with(\$path, \$base . DIRECTORY_SEPARATOR)) abort(403); // path traversal

readfile(\$path);

// basename() strips directory components:
basename('../../../etc/passwd'); // 'passwd'
\$safe = '/var/www/uploads/' . basename(\$_GET['file']); // still need realpath() too

Added 15 Mar 2026
Edited 22 Mar 2026
Views 28
Rate this term
No ratings yet
🤖 AI Guestbook educational data only
| |
Last 30 days
0 pings W 0 pings T 0 pings F 0 pings S 0 pings S 0 pings M 0 pings T 0 pings W 0 pings T 0 pings F 0 pings S 1 ping S 1 ping M 0 pings T 1 ping W 0 pings T 1 ping F 0 pings S 0 pings S 0 pings M 1 ping T 0 pings W 0 pings T 2 pings F 0 pings S 1 ping S 0 pings M 0 pings T 0 pings W 1 ping T
No pings yesterday
Amazonbot 7 Perplexity 5 Ahrefs 4 Unknown AI 3 SEMrush 3 Google 2
crawler 22 crawler_json 1 pre-tracking 1
DEV INTEL Tools & Severity
🟠 High ⚙ Fix effort: Low
⚡ Quick Fix
Always use realpath() to resolve the canonical absolute path before file operations on user-supplied paths — then verify the resolved path starts with your allowed base directory with str_starts_with()
📦 Applies To
PHP 5.0+ web cli
🔗 Prerequisites
🔍 Detection Hints
File operations with user-supplied path without realpath() validation; path traversal ../ not checked; file existence checked by different path than used
Auto-detectable: ✓ Yes semgrep psalm
⚠ Related Problems
🤖 AI Agent
Confidence: High False Positives: Medium ✓ Auto-fixable Fix: Low Context: Function
CWE-22 CWE-73

✓ schema.org compliant