
# Laboratorio Docker che dimostra il path traversal CVE-2026-12243 in NLTK precedente alla 3.10.0, confrontando il comportamento vulnerabile e quello corretto con un segreto sintetico in un ambiente isolato e offline.
Un piccolo laboratorio Docker riproducibile che confronta il comportamento di path traversal con codifica percentuale in NLTK 3.9.4 con il comportamento corretto in NLTK 3.10.0.
La versione vulnerabile valida il nome della risorsa prima della decodifica URL. Il payload fisso %2e%2e/%2e%2e/outside/lab-secret.txt supera il controllo, viene successivamente decodificato in ../../outside/lab-secret.txt ed esce sia dalla directory dati NLTK configurata sia dalla directory di lavoro del processo. La versione corretta rifiuta lo stesso input.
[!CAUTION] Questo repository è destinato esclusivamente a formazione difensiva e test autorizzati. Il laboratorio utilizza un segreto sintetico fisso all'interno di un contenitore isolato. Non adattarlo per accedere a sistemi o dati che non possiedi o per i quali non hai esplicita autorizzazione al test.
| Contenitore | Versione NLTK | Risultato atteso |
|---|---|---|
vulnerable | 3.9.4 | Legge il marcatore sintetico fuori da /lab/nltk_data |
patched |
Non vengono utilizzati download di corpora, server, porte, bind mount o connessione internet a runtime.
docker compose)run.shgit clone https://github.com/morzelowski/CVE-2026-12243-NLTK-PoC.git
cd CVE-2026-12243-NLTK-PoC
docker compose build
./run.sh
Risultato atteso:
=== Vulnerable image: NLTK 3.9.4 ===
NLTK version : 3.9.4
Working directory : /app
Configured data dir: /lab/nltk_data
Encoded resource : %2e%2e/%2e%2e/outside/lab-secret.txt
Decoded resource : ../../outside/lab-secret.txt
Resolved candidate : /outside/lab-secret.txt
NLTK warning : Security Violation [pathsec.open]: Unauthorized path /outside/lab-secret.txt
NLTK result : read 36 bytes
Synthetic marker : CVE-2026-12243-SYNTHETIC-LAB-MARKER
[PASS] Traversal escaped the configured NLTK data directory.
=== Patched image: NLTK 3.10.0 ===
NLTK version : 3.10.0
NLTK result : blocked (ValueError: Unsafe resource path: '...')
[PASS] Patched version rejected the same encoded traversal.
Lab completed: traversal reproduced and patched rejection verified.
L'immagine vulnerabile segnala che /outside/lab-secret.txt non è autorizzato ma ne restituisce comunque il contenuto perché NLTK 3.9.4 utilizza una sicurezza dei percorsi basata solo su avvisi (warning) per impostazione predefinita. Il testo di eccezioni e avvisi può variare leggermente; run.sh utilizza lo stato di uscita del processo, non una corrispondenza testuale fragile, per determinare se la dimostrazione è riuscita.
Ogni immagine contiene questo layout deliberatamente separato:
/
├── app/
│ └── poc.py # process CWD is /app
├── lab/
│ └── nltk_data/ # configured NLTK search root
└── outside/
└── lab-secret.txt # public synthetic marker
poc.py sostituisce nltk.data.path con /lab/nltk_data e passa il nome della risorsa fisso %2e%2e/%2e%2e/outside/lab-secret.txt a nltk.data.load(..., format="raw"). Nella versione vulnerabile, la decodifica avviene troppo tardi nel flusso di validazione:
/lab/nltk_data
↓ ../../outside/lab-secret.txt
/outside/lab-secret.txt
Poiché la directory di lavoro è /app, il canarino si trova fuori da entrambe le posizioni rilevanti per la dimostrazione: /app e /lab/nltk_data.
Lo script ha due asserzioni esplicite:
Qualsiasi altro risultato termina con codice di uscita non zero, quindi i controlli automatizzati non possono riportare un falso successo.
La configurazione Compose limita intenzionalmente il laboratorio:
network_mode: none disabilita la rete durante l'esecuzione di entrambe le dimostrazioni.no-new-privileges abilitato.noexec è scrivibile.fixtures/lab-secret.txt, un marcatore di test pubblico copiato nell'immagine durante la build.La build dell'immagine richiede accesso agli indici dei pacchetti per installare le due versioni NLTK bloccate. L'esecuzione a runtime è offline.
nltk.data.load() o nltk.data.find()Il laboratorio blocca la 3.9.4 perché è la versione concreta citata nel report originale e la 3.10.0 perché è la prima versione corretta registrata dall'avviso del manutentore.
Aggiorna NLTK e mantienilo aggiornato:
python -m pip install "nltk>=3.10.0"
Evita inoltre di passare nomi di risorse non attendibili alle API di caricamento da filesystem. Dove è richiesta la selezione da parte dell'utente, mappa gli identificatori visibili all'utente su una lista consentita di risorse di proprietà dell'applicazione invece di accettare direttamente percorsi o URL.
Esegui ciascun lato in modo indipendente:
docker compose run --rm vulnerable
docker compose run --rm patched
Ispeziona la configurazione Compose completamente risolta:
docker compose config
Rimuovi le immagini di laboratorio costruite localmente:
docker compose down --rmi local
permission denied: ./run.sh — esegui chmod +x run.sh una volta.docker: command not found — installa Docker Desktop o Docker Engine.docker compose build --no-cache.aec4fceRilasciato sotto Licenza MIT.
3.10.0| Blocca la traversal codificata |