| # ExecuTorch Scanner Bypass PoC | |
| ## Vulnerability Summary | |
| **Format:** ExecuTorch (`.pte`) | |
| **Scanner Bypass:** modelscan 0.8.7 + picklescan 1.0.1 (DUAL BYPASS) | |
| **Impact:** Arbitrary Code Execution via malicious model file | |
| **Bounty Target:** [ExecuTorch MFV](https://huntr.com/bounties/disclose/models?target=executorch) | |
| ## Technical Details | |
| This PoC demonstrates a dual scanner bypass for `.pte` model files: | |
| 1. **modelscan bypass:** The `.pte` extension is not in modelscan's supported file extensions list. | |
| modelscan skips scanning entirely, returning "No issues found." | |
| 2. **picklescan bypass:** The malicious payload uses joblib's numpy byte interleaving technique. | |
| Even when scanned directly, `pickletools.genops()` crashes on raw numpy bytes embedded in the | |
| joblib pickle format before reaching the malicious `__reduce__` call. | |
| 3. **ACE vector:** The file loads successfully with `joblib.load()`, executing arbitrary code. | |
| In ML pipelines, model files are commonly loaded with joblib/pickle regardless of extension. | |
| ## Reproduction | |
| ```bash | |
| # Scan with modelscan - reports no issues | |
| modelscan -p malicious_model.pte | |
| # Scan with picklescan - reports no issues | |
| picklescan -p malicious_model.pte | |
| # Load with joblib - executes arbitrary code | |
| python3 -c "import joblib; joblib.load('malicious_model.pte')" | |
| ``` | |
| ## Files | |
| - `malicious_model.pte` - Malicious model file (1,471 bytes) | |
| - `README.md` - This file | |
| ## Scanner Results | |
| ``` | |
| modelscan 0.8.7: No issues found (BYPASS) | |
| picklescan 1.0.1: No issues found (BYPASS) | |
| joblib.load(): Executes eval('1+1') = 2 (ACE CONFIRMED) | |
| ``` | |