
Detector de CVE-2026-87902. Clase LFI de get_page_template de WordPress. Solo detección. Laboratorio autorizado.
Detector de CVE-2026-87902 para WordPress Core.
get_page_template() puede ser dirigido de modo que la resolución de plantillas de página incluya un archivo .php local legible fuera del tema activo. WPSniper identifica el sitio, elige un page_id publicado, sondea la clase de inclusión y solo imprime VULN cuando un banner PEAR fuerte es exclusivo del cuerpo de la sonda.
Solo detección. Sin webshell. Sin pearcmd config-create. Sin ejecución de comandos del sistema operativo.
python3 WPSniper.py -u https://lab.wordpress.local --shell
Pipeline:
subfinder -d lab.example -silent | httpx -silent | python3 WPSniper.py -t 8
Alcance escrito. Laboratorio propio. Esa es toda la licencia para ejecutarlo.
WordPress construye el nombre de la plantilla de página a partir de la variable de consulta pagename derivada de la URL y decodificada:
page-{$pagename}.php
locate_template() luego incluye ese archivo. En las compilaciones afectadas, la ruta resuelta no se fuerza a permanecer dentro de un directorio de tema permitido. Un recorrido de doble codificación en pagename sobrevive a sanitize_title lo suficiente para que get_page_template() lo decodifique una vez y salga del árbol del tema.
Dos precondiciones se sitúan frente a una inclusión cerrada:
page- (WordPress documenta page-templates/ — Twenty Twelve, Twenty Fourteen, Neve, Hestia, Sydney y otros)..php legible para la cuenta del servidor web. El detector utiliza banners estándar de PEAR CLI como oráculo de inclusión. No escribe uno.RCE es un efecto posterior posible cuando esas condiciones más una línea de gadget escribible/ejecutable se alinean. Ese efecto posterior no está en este repositorio.
Crédito del descubridor en el CVE: Robert (ressl) vía WordPress HackerOne. Aviso: GHSA-7hp8-65ch-5whp.
La tabla de versiones está integrada. 4.7.0–7.1.1 son la ventana afectada. Puntos parcheados: 7.1.2, 7.0.6, 6.9.9, 6.8.10 … hasta 4.7.37.
Una página de marketing que dice "pearcmd" en una entrada de blog no es un hallazgo.
VULN solo cuando todo esto es verdadero:
?page_id=PEAR Version:, Usage: pear, PEAR_Config, Commands for pear, config-create, DEPRECATED: PEAR commands, pear.php)pearcmd / PEAR por sí solo se descarta, especialmente si ya estaba en el HTML de la línea baseINFO = versión afectada y/o directorio page-templates, inclusión no cerrada. No reporte crítico sobre INFO.
SAFE = rama parcheada, o inclusión idéntica a la línea base.
SKIP = no es WordPress, URL incorrecta.
/etc/passwd es el oráculo equivocado para este CVE. locate_template() añade .php. El comando interactivo passwd existe para que puedas verlo por ti mismo. La aparición de una estrofa root:x:0:0: es inusual y debe verificarse a mano.
python3 -m pip install -r requirements.txt
python3 WPSniper.py -u https://lab.wordpress.local
Requiere requests.
--shell se ignora en un pipeline. Eso es intencional.
python3 WPSniper.py -u https://lab.wordpress.local --shell
[email protected] ▶
1 fp version / theme / patched?
2 pages REST published pages
3 theme page-templates directory
4 probe PEAR include + baseline diff (no write)
5 diff same, print Δ + tokens
6 passwd try …/etc/passwd (this class includes *.php)
7 include P include a .php path without suffix
8 save last body → /tmp/wpsniper-probe.html
9 help
0 exit
Cada sonda imprime la URL completa y un curl listo para copiar y pegar. Úselo en el informe. No invente una segunda solicitud.
7 include es para un archivo de laboratorio autorizado que ya haya colocado. El nombre de ejemplo en el texto de ayuda es un marcador testigo, no un dropper.
WPSniper v1.3 CVE-2026-87902 get_page_template LFI
[radar] target https://lab.wordpress.local
[radar] generator=6.8.3 theme=twentytwelve status=affected
[radar] page_id=2
[radar] theme dir /wp-content/themes/twentytwelve/page-templates/ → 403
VULN lab.wordpress.local unique=['PEAR Version:','Usage: pear'] Δlen=+18420
patched 7.1.2 · 7.0.6 · 6.8.10 · backports to 4.7.37
El host en esta página es una etiqueta de laboratorio. Los nombres de host de clientes reales no pertenecen a una captura pública.
Actualice a 7.1.2 o al backport para su rama:
7.0.6 · 6.9.9 · 6.8.10 · 6.7.9 · 6.6.9 · 6.5.12 · 6.4.12 · 6.3.12 · 6.2.13 · 6.1.14 · 6.0.16 · 5.9.18 … hasta 4.7.37.
7.1.2 también requiere que la ruta de plantilla resuelta permanezca dentro de un directorio de tema permitido. Esa es la corrección real, no una regla de WAF.
pearcmd config-create, sin envoltorio de system()/etc/passwd en bruto como confirmación principalSi necesita un hallazgo: adjunte el curl que WPSniper ya imprimió, los tokens fuertes únicos y la discrepancia del digest de la línea base.
Solo pruebas de seguridad autorizadas. Ejecutar esto contra un host que no posee o que no tiene por escrito es su problema, no el de la herramienta.
mitsec · Yunus Emre Öztaş
| Paso | Acción | Señal |
|---|
| 1 | Home + generator + /feed/ | ¿WordPress? ¿versión? ¿slug del tema? |
| 2 | REST /wp-json/wp/v2/pages o page_id= en el HTML | Una página publicada para que la ruta de plantilla realmente se ejecute |
| 3 | GET /wp-content/themes/{slug}/page-templates/ | 200 / 401 / 403 = el directorio existe |
| 4 | Línea base ?page_id=N vs sonda pagename= | Digest del cuerpo + tokens PEAR fuertes únicos |
| Opción | Significado |
|---|
-u URL | Objetivo único |
-l file | Lista de URLs |
| stdin | subfinder | httpx | WPSniper |
-t N | Hilos en una lista (por defecto 6) |
-q | Filas silenciosas + resumen |
--shell | Sonda interactiva en un único -u |
--timeout | Segundos (por defecto 14) |