mirror of
https://github.com/ZoneMinder/zoneminder.git
synced 2026-10-02 15:35:09 -04:00
zmfilter.pl rebuilds SQL from the JSON the web tier stores verbatim in Filters.Query_json, so a saved filter's attribute, operator and value all arrive at the statement exactly as they were written. None of the three were checked here, while web/includes/FilterTerm.php checks all three: values were wrapped in quotes by hand, which a value containing one closes; the final attribute branch concatenated 'E.'.$attr; and the generic operator branch emitted the operator as written. Any account that can save a filter could therefore have the daemon run SQL of their choosing with its own credentials, against a table set that includes Users. The daemon also deletes and moves events, so this is not only a read. Confirmed against the module before the change, building SQL from stored terms and checking whether the payload landed outside a string literal: val = "x' OR 1=1 -- " -> outside, injected attr = "Id=1 OR 1=1 -- " -> outside, injected op = "= 1 OR 1=1 -- " -> outside, injected Attributes now have to match what the PHP accepts, operators have to be one of the sixteen the UI can produce, and a filter carrying anything else is refused rather than run. Values go through DBI's quote(). Numbers are left unquoted so the statements the existing filters produce are unchanged: a bare number cannot carry SQL, and quoting it would have altered every numeric comparison in the file for no gain. Verified by generating the SQL for seven representative filters before and after -- purge-when-full, delete-after-a-day, LIKE on a name, IN on monitors, a monitor name, a score range and an IS NULL -- and diffing: identical apart from the timestamp a relative date resolves to. After the change the three payloads above are contained in a literal, or the filter is refused. See GHSA-p8h3-4x5c-cv7p. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01WBHBB95RBX7D9p8ge2WDZb (cherry picked from commit bc11642fea844bc86bac0080da42e4514d5a4d76)