PyPI · motioneye
motionEye: LFI → pass‑the‑hash admin → unsafe restore → unauth action exec (RCE)
A multi‑stage chain in motionEye leads to remote code execution. The chain combines:
CONF_PATH./action/<id>/<action>.If the normal user password is unset, the chain becomes unauthenticated RCE. If a normal password exists, a normal user can still achieve admin escalation and RCE.
picture/<id>/downloadFiles:
motioneye/motioneye/handlers/picture.py → download() (local motion camera branch)motioneye/motioneye/mediafiles.py → get_media_content()Issue: get_media_content() only blocks .. and then joins target_dir with path. Absolute paths (e.g. /etc/hosts) bypass the join and are read directly.
File: motioneye/motioneye/handlers/base.py → get_current_user()
Issue: The signature check allows signatures computed using the admin password hash (SHA1) as the key. If the hash is leaked (via LFI), admin access can be obtained without the plaintext password.
File: motioneye/motioneye/config.py → restore()
Issue: tar zxC CONF_PATH is used on user‑supplied data without sanitizing entries. A crafted tar can drop executable files into CONF_PATH.
File: motioneye/motioneye/handlers/action.py → post()
Issue: No authentication decorator is present. It executes <action>_<camera_id> found in CONF_PATH with subprocess.Popen.
/picture/<id>/download/<absolute_path>/picture/1/download/%2Fetc%2Fhosts/etc/motioneye/motion.conf:@admin_password <SHA1_HASH>./config/restore?_username=admin using the hash as key.lock_<id> (or any action) as an executable.CONF_PATH by restore./action/<id>/lockIn local testing, the injected action created a marker file:
/tmp/meye_rce_ok
Verification command:
docker exec -it motioneye ls -la /tmp | grep meye_rce_ok
Example output:
-rw-r--r-- 1 root root 0 ... /tmp/meye_rce_ok
netcam_url, videodevice).picture/<id>/download is reachable:@normal_password is empty (default in some installs).get_media_content() and get_media_path()..., symlinks, non‑regular files.ActionHandler (admin‑only).Is your project exposed to this? Stateward checks every dependency on every pull request and flags it only if your code actually reaches it.
Check my repoSources: CISA KEV (public domain), OSV.dev & GitHub Advisory Database (CC-BY-4.0), FIRST EPSS, NVD/CWE (public domain). Served live from the Stateward advisory database.