CVE-2026-32397

Filter & Grids <= 3.5.1 - Missing Authorization

mediumMissing Authorization
5.3
CVSS Score
5.3
CVSS Score
medium
Severity
3.5.2
Patched in
55d
Time to patch

Description

The Filter & Grids plugin for WordPress is vulnerable to unauthorized access due to a missing capability check on a function in versions up to, and including, 3.5.1. This makes it possible for unauthenticated attackers to perform an unauthorized action.

CVSS Vector Breakdown

CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:L/A:N
Attack Vector
Network
Attack Complexity
Low
Privileges Required
None
User Interaction
None
Scope
Unchanged
None
Confidentiality
Low
Integrity
None
Availability

Technical Details

Affected versions<=3.5.1
PublishedFebruary 20, 2026
Last updatedApril 15, 2026
Affected pluginymc-smart-filter

What Changed in the Fix

Changes introduced in v3.5.2

Loading patch diff...

Source Code

WordPress.org SVN
Research Plan
Unverified

# Exploitation Research Plan - CVE-2026-32397 ## 1. Vulnerability Summary The **Filter & Grids** plugin (version <= 3.5.1) contains a **Missing Authorization** vulnerability. The plugin supports two operational modes: **Legacy Mode** (v2.x) and **New Mode** (v3.x). An administrative "Upgrade to v3.…

Show full research plan

Exploitation Research Plan - CVE-2026-32397

1. Vulnerability Summary

The Filter & Grids plugin (version <= 3.5.1) contains a Missing Authorization vulnerability. The plugin supports two operational modes: Legacy Mode (v2.x) and New Mode (v3.x). An administrative "Upgrade to v3.x" feature exists to migrate settings and switch the plugin's core engine. However, the AJAX handler responsible for this transition fails to implement proper authorization checks (e.g., current_user_can( 'manage_options' )). This allows unauthenticated attackers to remotely trigger the upgrade process, which is not backward compatible and disrupts the site's layout and grid functionality.

2. Attack Vector Analysis

  • Endpoint: /wp-admin/admin-ajax.php
  • Method: POST
  • Action: ymc_update_plugin (inferred from js-confirm-update-plugin class in includes/core/admin/admin-header/tmpl-admin-header.php)
  • Authentication: None (Unauthenticated via wp_ajax_nopriv_ymc_update_plugin)
  • Preconditions: The plugin must be in "Legacy Mode" (ymc_plugin_legacy_is option set to yes).

3. Code Flow

  1. Frontend Trigger: The administrator UI in includes/core/admin/admin-header/tmpl-admin-header.php renders a modal (#ymc-update-modal) with a confirmation button (.js-confirm-update-plugin).
  2. AJAX Registration: The plugin likely registers the AJAX handler in its main class or an admin utility:
    add_action('wp_ajax_ymc_update_plugin', 'ymc_update_plugin_callback');
    add_action('wp_ajax_nopriv_ymc_update_plugin', 'ymc_update_plugin_callback');
    
  3. Vulnerable Handler: The callback function (likely in includes/Plugin.php or ymc2/YMC_Filter_Grids.php) executes the migration:
    function ymc_update_plugin_callback() {
        // MISSING: current_user_can('manage_options') check
        // MISSING: check_ajax_referer('ymc_nonce', 'nonce') check
        update_option('ymc_plugin_legacy_is', 'no'); 
        // ... other migration logic ...
        wp_send_json_success();
    }
    
  4. Impact: ymc-smart-filters.php checks is_legacy() and switches the entire plugin logic to the v3.x engine, which is incompatible with legacy grid data.

4. Nonce Acquisition Strategy

Based on the "Missing Authorization" severity and unauthenticated vector, the endpoint likely lacks a nonce check entirely. If a nonce is required, it is often leaked via a localized script.

  1. Identify Script: Search for wp_localize_script calls that define AJAX parameters.
  2. Potential Variable: ymc_smart_filter_params or ymc_admin_ajax.
  3. Extraction:
    • Navigate to the homepage or a page containing a grid.
    • Execute: browser_eval("window.ymc_smart_filter_params?.nonce") or browser_eval("window.ymc_ajax?.nonce").
  4. Bypass: If wp_ajax_nopriv is registered, the developer often skips the check_ajax_referer call, meaning no nonce is needed.

5. Exploitation Strategy

The goal is to trigger the plugin upgrade unauthenticated.

Step 1: Trigger the Upgrade

Send a POST request to the AJAX endpoint.

HTTP Request:

  • URL: http://vulnerable-wp.local/wp-admin/admin-ajax.php
  • Method: POST
  • Headers: Content-Type: application/x-www-form-urlencoded
  • Body:
    action=ymc_update_plugin
    

Step 2: Alternative Action (If above fails)

If the action name differs, try:

  • action=ymc_migrate_to_v3
  • action=ymc_switch_to_v3

6. Test Data Setup

  1. Install Plugin: Install version 3.4.1 or 3.5.1 of ymc-smart-filter.
  2. Enable Legacy Mode:
    wp option update ymc_plugin_legacy_is "yes" --allow-root
    
  3. Create Legacy Content: Create at least one grid using the legacy shortcode to establish a baseline state.

7. Expected Results

  • Response: The server should return a JSON success message: {"success": true} or {"success": true, "data": "..."}.
  • State Change: The plugin option ymc_plugin_legacy_is will change from yes to no.
  • Side Effect: Legacy grids on the site will stop functioning or display errors because the v3.x logic is now active.

8. Verification Steps

After sending the HTTP request, verify the state change using WP-CLI:

wp option get ymc_plugin_legacy_is --allow-root
# Expected Output: no

9. Alternative Approaches

If the upgrade action is protected, check the Taxonomy Settings Apply functionality seen in includes/core/util/taxonomy.php:

  • Trigger: .btn-tax-apply
  • Action: ymc_save_tax_options or ymc_tax_settings_apply
  • Payload: action=ymc_save_tax_options&ymc-tax-bg=#ff0000&ymc-tax-custom-name=PWNED
  • Goal: Unauthorized modification of taxonomy display settings.

Another target is the Debug Code settings mentioned in uninstall.php (ymc_debug_code). If an unauthorized action allows saving settings, an attacker could enable debug mode to leak information.

Research Findings
Static analysis — not yet PoC-verified

Summary

The Filter & Grids plugin for WordPress is vulnerable to unauthorized access because it fails to perform capability and nonce checks on the AJAX action responsible for upgrading the plugin to version 3.x. This allows unauthenticated attackers to remotely trigger an upgrade that changes the core engine mode, potentially breaking existing legacy grids and disrupting the site's layout.

Vulnerable Code

/* includes/core/admin/admin-header/tmpl-admin-header.php line 32 */
<button class="button button-primary js-confirm-update-plugin"><?php esc_html_e('Yes, update now', 'ymc-smart-filter'); ?></button>

---

/* ymc-smart-filters.php lines 83-102 */
	if ( 'no' === YMC_Filter_Grids::is_legacy() ) {
		YMC_Filter_Grids::instance();

		/**
		 * Returns the main instance of FG.
		 *
		 * @since  3.0.0
		 * @return YMC_Filter_Grids
		 */
		function YMC() {
			return YMC_Filter_Grids::instance();
		}

	} else {
		/**
		 * Include legacy plugin
		 */
		if ( file_exists( YMC_SMART_FILTER_DIR . 'includes/Plugin.php' ) ) {
			require_once YMC_SMART_FILTER_DIR . 'includes/Plugin.php';
		} else {
			wp_die( 'Filter & Grids: Legacy version file not found.' );
		}
	}

Security Fix

diff -ru /home/deploy/wp-safety.org/data/plugin-versions/ymc-smart-filter/3.4.1/includes/core/admin/admin-header/tmpl-admin-header.php /home/deploy/wp-safety.org/data/plugin-versions/ymc-smart-filter/3.5.2/includes/core/admin/admin-header/tmpl-admin-header.php
--- /home/deploy/wp-safety.org/data/plugin-versions/ymc-smart-filter/3.4.1/includes/core/admin/admin-header/tmpl-admin-header.php	2026-01-25 17:16:52.000000000 +0000
+++ /home/deploy/wp-safety.org/data/plugin-versions/ymc-smart-filter/3.5.2/includes/core/admin/admin-header/tmpl-admin-header.php	2026-02-18 21:38:00.000000000 +0000
@@ -1,3 +1,6 @@
+<?php defined( 'ABSPATH' ) || exit; ?>
+
+
 <div class='ymc-admin-toolbar'>
     <div class="admin-toolbar-inner">
         <div class='logo'>
diff -ru /home/deploy/wp-safety.org/data/plugin-versions/ymc-smart-filter/3.4.1/readme.txt /home/deploy/wp-safety.org/data/plugin-versions/ymc-smart-filter/3.5.2/readme.txt
--- /home/deploy/wp-safety.org/data/plugin-versions/ymc-smart-filter/3.4.1/readme.txt	2026-01-25 17:16:52.000000000 +0000
+++ /home/deploy/wp-safety.org/data/plugin-versions/ymc-smart-filter/3.5.2/readme.txt	2026-02-18 21:38:00.000000000 +0000
@@ -1,8 +1,8 @@
 ===  Filter & Grids ===
 Plugin Name: Filter & Grids
 Contributors: YMC, Roman
-Version: 3.4.1
-Donate link: https://github.com/YMC-22/Filter-Grids
+Version: 3.5.2
+Donate link: https://www.paypal.com/webapps/shoppingcart?flowlogging_id=f650927e62f93&mfid=1771341447878_f650927e62f93#/checkout/openButton
 Tags: filter, grid, ajax, search, sort, masonry, wordpress
 Requires at least: 5.5
 Tested up to: 6.9
@@ -76,6 +76,10 @@
 
 == Changelog ==
 
+= 3.5.2 =
+Fixed query security bugs.
+= 3.5.0 =
+Added Usage tab for filters, allowing administrators to see a list of pages and posts where each filter is used.
 = 3.4.1 =
 Improved recursive sanitization function to safely handle both arrays and strings.
 = 3.4.0 =

Exploit Outline

An unauthenticated attacker can perform a POST request to the WordPress AJAX endpoint (/wp-admin/admin-ajax.php) with the 'action' parameter set to 'ymc_update_plugin'. Because the backend handler for this action fails to check for user capabilities or a valid security nonce, the request is processed immediately. This triggers a change in the 'ymc_plugin_legacy_is' database option from 'yes' to 'no', forcing the plugin to switch from its legacy 2.x engine to the incompatible 3.x engine, effectively breaking any content relying on legacy configurations.

Check if your site is affected.

Run a free security audit to detect vulnerable plugins, outdated versions, and misconfigurations.