Skip to content
KitploitKITPLOIT
ToolsExploitsBlog
Log in
Submit
ToolsExploitsBlog
Submit

Hacking, PenTest, and Cybersecurity Tools for Your Security Arsenal!

Kitploit is a directory of hacking, cybersecurity, and pentesting tools. Discover the latest project updates to find vulnerabilities, analyze systems, automate testing, and strengthen your security.

FeedsContactPrivacy© 2026 Kitploit

Tool Directory

Categories

View all categories
Loading categories
EXPLOIT-CVE-2026-87902 — Lab vulnerável (Docker) + PoC Python para a CVE-2026-87902 — path traversal não autenticado no WordPress Core (page-template -> LFI -> RCE condicional). Uso educacional/autorizado. | Kitploit
Tools/GitHubGitHub/joaovicdev/exploit-cve-2026-87902
Container SecurityVulnerability AnalysisExploitationWeb Application ExploitationWeb SecurityPenetration TestingLearning & EducationPayload DevelopmentLabs & Practice

Most Popular

View all →

Discover the most used tools by our community.

Explore all tools

Browse our collection of tools

View all tools →
Share
GitHubjoaovicdev/exploit-cve-2026-87902

EXPLOIT-CVE-2026-87902

Lab vulnerável (Docker) + PoC Python para a CVE-2026-87902 — path traversal não autenticado no WordPress Core (page-template -> LFI -> RCE condicional). Uso educacional/autorizado.

View Repository
3321 days agoNot yet reviewed

Lab + Exploit — CVE-2026-87902

Lab deliberately vulnerable + Python PoC for CVE-2026-87902: unauthenticated path traversal in the page template resolution of WordPress Core, leading to Local File Inclusion (LFI) and conditional RCE.

FieldValue
ProductWordPress Core
Affected versions4.7.0 → 7.1.1
Fix7.1.2 (backported up to 4.7.37)
TypePath Traversal (CWE-22) → LFI → Conditional RCE
AuthenticationNone (unauthenticated)
CVSS 4.09.2 (Critical)
Publication Date2026-09-23

⚠️ Legal / Ethical Notice. All material here is for study in a local and authorized environment. The lab is an intentionally insecure Docker image — do not expose it to the internet. The exploit.py defaults to http://localhost:8091 on purpose. Running the PoC against any system without explicit written authorization is illegal. You are solely responsible for its use.


Structure

EXPLOIT-CVE-2026-87902/
├── README.md                # este arquivo
├── docker-compose.yml       # sobe o lab em localhost:8091
├── lab/
│   ├── Dockerfile           # php:8.2-apache + PEAR + register_argc_argv=On
│   ├── config/zz-lab.ini    # pré-condições ambientais de RCE
│   └── src/                 # "WordPress mini" que reproduz o trecho vulnerável
│       ├── index.php        # front controller (≈ template-loader.php)
│       ├── wp-mini.php      # get_page_template()/locate_template()/... vulneráveis
│       ├── private/
│       │   └── secret-config.php   # alvo .php fora do tema (prova de LFI)
│       └── wp-content/themes/twentytwelve-mini/
│           ├── style.css
│           ├── index.php
│           └── page-templates/     # diretório "page-*" exigido p/ a travessia
│               └── full-width.php
└── exploit/
    ├── exploit.py           # PoC (pt-BR): LFI + cadeia RCE via pearcmd
    └── requirements.txt

How to Run

Prerequisites: Docker + Docker Compose and Python 3 with requests.

# 1) Suba o lab (fica em http://localhost:8091)
docker compose up --build

# 2) Em outro terminal, instale a dependência do PoC e rode
cd exploit
pip install -r requirements.txt
python3 exploit.py            # roda LFI + RCE contra o lab local

# Opções úteis
python3 exploit.py --mode lfi              # só a prova de LFI
python3 exploit.py --mode rce --cmd 'uname -a'
python3 exploit.py --target http://localhost:8091

# 3) Derrube o lab
docker compose down

Expected output (summary):

[LFI] Sucesso! Arquivo externo incluído -> SEGREDO_DO_LAB{lfi_via_page_template_traversal}
[RCE] Comando executado no servidor:
------------------------------------------------------------
uid=33(www-data) gid=33(www-data) groups=33(www-data)
FLAG{cve_2026_87902_rce_no_wordpress_mini}
------------------------------------------------------------

Vulnerability Anatomy

1. Vulnerable Code Path

In get_page_template() the value of the public query variable pagename is used to construct the template name. The core validates the raw value with validate_file() (which blocks literal ..), but then decodes the value once and uses the result as a template candidate without revalidating (faithful reproduction in wp-mini.php):

if ($pagename !== '' && 0 === validate_file($pagename)) {
    $templates[] = "page-{$pagename}.php";          // valor cru (ainda encodado)

    $pagename_decoded = urldecode($pagename);        // <-- 2ª decodificação
    if ($pagename_decoded !== $pagename) {
        $templates[] = "page-{$pagename_decoded}.php"; // travessia reintroduzida
    }
}

The locator then concatenates theme + "/" + template and includes the first existing file, without realpath() or verification that the result remains inside the theme directory.

2. Double Encoding Bypass

The attacker sends doubly encoded pagename:

Valor no fio (POST body):   templates%252f%252e%252e%252f...%252fpearcmd
1ª decodificação (HTTP):    templates%2f%2e%2e%2f...%2fpearcmd     <- sem '..' literal => passa por validate_file()
2ª decodificação (core):    templates/../../.../pearcmd            <- travessia real

Since the locator prefixes page-, the path becomes page-templates/../../.../pearcmd.php. This resolves outside the theme.

3. Prerequisites for RCE (all present in the lab)

  • Theme with a top-level directory starting with page- (here, page-templates/). This is the actual starting point for the traversal: on Linux each path component must exist for ../ to resolve. Legacy themes (Twenty Twelve/Fourteen) and popular ones (Neve, Hestia, Sydney) meet this.
  • register_argc_argv = On in PHP → $_SERVER['argv'] is populated from the query string.
  • Readable pearcmd.php on the server (the official php:8.2-apache image already includes it at /usr/local/lib/php/pearcmd.php, in the default include_path).

Since the locator appends .php, LFI only reaches .php files. Therefore, the practical RCE route chains with pearcmd.php:

  • Stage 1 — include pearcmd.php by passing, via the query string (=argv), config-create to write a .php webshell to /tmp.
  • Stage 2 — include that /tmp/<webshell>.php via a new traversal → the attacker's PHP executes.

4. How 7.1.2 Fixes It

The patch handles the pagename value consistently: it validates after any decoding (or rejects input containing encoded traversal sequences) and begins enforcing the directory boundary during template resolution (the final path must remain within the theme). Result: the doubly encoded value no longer survives to the include.

Mitigations: upgrade to ≥ 7.1.2; and, as defense in depth, set register_argc_argv = Off, remove/restrict pearcmd.php, and deploy a WAF that detects encoded ../ (%2e%2e%2f, %252e...) in requests.


Detection (for the defense team)

  • Front-end requests containing encoded/double-encoded ../ (%2e%2e%2f, %252e%252e%252f) in parameters.
  • Attempts to manipulate page template resolution (suspicious values in pagename), especially combined with query strings containing config-create / references to pearcmd.
  • Unexpected creation of .php files in /tmp followed by inclusion.

Sources

  • NVD — CVE-2026-87902
  • VulDB — CVE-2026-87902
  • Help Net Security — WordPress 7.1.2 Fixes CVE-2026-87902
  • SOC Prime — Critical WordPress Core RCE Flaw
  • Hadrian — Working PoC for WordPress's Critical Path Traversal
  • Security Affairs
Download Tool