Hacktoberfest 2026: le issue che i maintainer hanno segnato per ottobre, aperte e adatte ai principianti. Sfoglia le issue Hacktoberfest

Arbitrary code execution via eval() of a third-party model pack's train.log field in the WebUI

Aperta Adatta ai principianti
#2,866 0 commenti 0 reazioni 0 assegnatari Vedi su GitHub

Nessuno ha ancora preso questa issue.

Valutazione

Difficoltà
2/5
Tempo stimato
1-3 ore
Idoneità per principianti
78/100
Tipo di issue
Bug
Chiarezza
Specificata chiaramente
Stato di attività
Attiva
Stack tecnologico
python
Ambito
security

Direzione di ricerca

Leggi webui.py:1719-1726 in change_info_ e il collegamento di ckpt_path2.change in webui.py:2820-2822. Esegui le riproduzioni di train.log malevolo e del controllo negativo dell’issue, quindi verifica che il parsing rifiuti le espressioni eseguibili mentre i dati validi di model-info continuano ad aggiornare i selettori senza creare il file canary.

Scritto dal modello di indicizzazione a partire dal testo della issue.

Descrizione

1. Summary

RVC WebUI wires the change event of the model-path textbox to change_info_ (webui.py:2821). change_info_ reads the sidecar file train.log shipped next to the selected model, takes the last tab-separated field of the first line, and passes it straight to eval() (webui.py:1719-1726). Model packs usually come from third-party sharing (cloud drives, model sites), so this train.log is attacker-controlled untrusted input: with a completely benign .pth, a single line of log text is enough to execute arbitrary Python code with WebUI process privileges on the victim's machine.

2. Affected version / environment

Repository: RVC-Project/Retrieval-based-Voice-Conversion-WebUI; verification anchor: commit 81eed5e (webui.py:1715-1731 change_info_; webui.py:2821 .change wiring); latest release: tag 2.3.260718 and the current main branch (checked 2026-09-30) still contain the same code; history: tag 2.2.231006 (2023-10) already had the same eval in infer-web.py:754-761, so the flaw is at least ~2 years old; PoC environment: Docker official python:3.11-slim image (Python 3.11.16) with the project's own CPU dependency list requirments_cpu_py312.txt (gradio 3.14.0; torch 2.4.1+cpu); the WebUI listens on 0.0.0.0:7897 by default.

3. Steps to reproduce

  1. Build a model pack evil_model/ containing two files: G_23333.pth is a normal, benign small checkpoint (generated with torch.save, byte-identical to the negative control); the first line of train.log follows the project's own log format "%(asctime)s\t%(name)s\t%(levelname)s\t%(message)s" with the last field (the message slot) replaced by the Python expression (import('pathlib').Path('/out/pwned_by_rvc_train_log_eval').write_text('MBE2E-CANARY-rvc-train-log-eval-v1\n', encoding='utf-8'), {'sample_rate': '48k', 'if_f0': 1, 'version': 'v2'})[1], which first writes a canary file and then returns the model-info dict, so the UI update completes normally without any error.
  2. Start the WebUI: python webui.py --pycmd python3 --port 7897
  3. Fire the same event a real user triggers: put the path evil_model/G_23333.pth into the "Path to Model" textbox of the checkpoint-extraction section (the .change event invokes change_info_); in the PoC the project's own Gradio queue API is used (/queue/join WebSocket, same protocol as the product frontend), submitting that path with fn_index pointing at the .change listener.
  4. Observe the server filesystem: /out/pwned_by_rvc_train_log_eval now exists with content "MBE2E-CANARY-rvc-train-log-eval-v1", while the UI shows no anomaly at all.
  5. Negative control: same directory layout and byte-identical .pth, but with the last train.log field replaced by the plain dict literal {'sample_rate': '48k', 'if_f0': 1, 'version': 'v2'}; repeat step 3 — it returns 48k/1/v2 and produces no file.

4. Expected behavior / Actual behavior

Expected: train.log is untrusted data carried inside a third-party model pack; parsing its field to prefill the sample-rate/if_f0/version selectors must never execute any code from it.
Actual: the field content is evaluated by eval(); the attacker's expression runs with WebUI process privileges, and because the payload returns a legitimate info dict the UI updates silently — no error, no warning.

5. Impact

  • Full arbitrary code execution with WebUI process privileges: file read/exfiltration, persistence, weight replacement, all possible.
  • The payload hides in "log text" while the .pth stays clean, so weight-based scanning and user intuition (people only look at the weights) both miss it; the expression returns a normal dict, so nothing is surfaced to the UI.
  • The trigger (selecting/pasting a model path in the WebUI) is the unavoidable step of loading community models; no training, no GPU, no extra interaction required.

6. Suggested fix

Replace the eval() at webui.py:1719 with a constrained parser: prefer ast.literal_eval(info_str), which accepts literals only and rejects any call or name lookup; treat parse failures as "no train.log info" (fall back to the UI defaults) instead of swallowing them into a traceback; the cleaner long-term option is a JSON convention (json.dumps on the writer side), fully dropping Python literal evaluation. Also consider warning the user when a model path with a sidecar train.log is loaded for the first time.

7. Additional context

  • Vulnerable code (webui.py:1719-1726, commit 81eed5e):
info = eval(
    read_text(
        ckpt_path.replace(os.path.basename(ckpt_path), "train.log")
    )
    .strip("\n")
    .split("\n")[0]
    .split("\t")[-1]
)
sr, f0 = info["sample_rate"], info["if_f0"]
  • Event wiring (webui.py:2820-2822):
ckpt_path2.change(
    change_info_, [ckpt_path2], [sr__, if_f0__, version_1]
)

rvc-train-log-eval-poc.zip

link:

https://github.com/3em0/cve_repo/blob/main/2026/Retrieval-based-Voice-Conversion-WebUI_Arbitrary_Code_Execution_via_eval()_of_Sidecar_train.log_in_WebUI_change_info_.md

Lingua principale
Python
Stelle
38.8k
Fork
5.3k
Metriche di merge delle PR
Nessuna PR unita negli ultimi 30g

Preparare l'ambiente

Questo progetto non fornisce container di sviluppo, Dockerfile né guida per i contributori, quindi l'ambiente è a tuo carico: parti dal suo README e consulta la nostra guida al primo contributo per i passaggi generali.

Come iniziare

  1. Leggi tutta la issue e poi la guida ai contributi del progetto.
  2. Commenta sulla issue per dire che te ne occupi tu — evita che due persone facciano lo stesso lavoro.
  3. Fai un fork del repository e lavora su un branch.
  4. Apri una pull request che faccia riferimento al numero della issue.

Altre issue di RVC-Project/Retrieval-based-Voice-Conversion-WebUI

Tutte le issue di RVC-Project/Retrieval-based-Voice-Conversion-WebUI

Issue simili

Altre issue su Python

Ricevi le nuove issue nella tua casella

Un breve riepilogo di issue GitHub adatte ai principianti.