Skip to content
Open
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 3 additions & 2 deletions mtkclient/Library/DA/mtk_da_handler.py
Original file line number Diff line number Diff line change
Expand Up @@ -120,14 +120,15 @@ def connect(self, mtk, directory:str = None):
step = self.mtk.step
mtk.preloader.dump_internal_flash(offset=offset,length=length,step=step,filename="internal_flash.bin")
else:
if mtk.serialportname is not None:

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is also critical, why remove it ?

mtk.preloader.init()
if directory:
self.mtk.config.hwparam_path = directory
if mtk.port.cdc.connected and os.path.exists(os.path.join(mtk.config.hwparam_path, ".state")):
mtk.daloader.reinit()
mtk.reinited = True
return mtk
else:
# Device found via USB but no DA state — likely BROM mode already connected
mtk.preloader.init(directory=directory)
if mtk.config.target_config is None:
self.info("Please disconnect, start mtkclient and reconnect.")
return None
Expand Down
53 changes: 28 additions & 25 deletions mtkclient/Library/Port.py
Original file line number Diff line number Diff line change
Expand Up @@ -73,8 +73,8 @@ def run_serial_handshake(self):
while i < length:
if ep_out(int.to_bytes(startcmd[i], 1, 'little')):
v = ep_in(1, timeout=20) # Do not wait 1 sec, bootloader is only active for 0.3 sec.
if len(v) == 1 and v[0] == ~(startcmd[i]) & 0xFF:
i += 1
if len(v) == 1 and (v[0] == ~(startcmd[i]) & 0xFF or v[0] == startcmd[i]):
i += 1 # complement (UART) or same-byte echo (USB command mode)
else:
i = 0
self.info("Device detected :)")
Expand Down Expand Up @@ -134,40 +134,43 @@ def run_handshake(self, retries=5):
self.cdc.setcontrollinestate(rts=True)

startcmd = b"\xa0\x0a\x50\x05"
expected_echo = bytes(~b & 0xFF for b in startcmd) # Precompute: b'\x5f\xf5\xaf\xfa'

brom_pids = [0x3, 0xF200, 0xD1E9, 0xD1E2, 0xD1EC, 0xD1DD]
if self.cdc.pid not in brom_pids:
ep_out(b"\xa0") # Send first byte separately if needed
ep_out(b"\xa0")

for attempt in range(retries):
received = b""
try:
for byte in startcmd:
written = ep_out(bytes([byte]), timeout=500) # Explicit timeout
if written != 1:
raise ValueError("Write failed")

# Read exactly 1 echo byte (fastest)
echo = ep_in(1, timeout=500)
if len(echo) != 1 or echo[0] != (~byte & 0xFF):
raise ValueError(f"Echo mismatch: got {echo!r}, expected {~byte & 0xFF:02x}")
# Flush any bytes BROM sent before we started
try:
ep_in(maxinsize, timeout=50)
except Exception:
pass

received += echo

if received == expected_echo:
success = True
for byte in startcmd:
ep_out(bytes([byte]), timeout=500)
got_echo = False
for _ in range(64):
try:
echo = ep_in(1, timeout=100)
if len(echo) == 1:
if echo[0] == (~byte & 0xFF) or echo[0] == byte:
got_echo = True # complement (UART) or same-byte (USB)
break
except Exception:
break
if not got_echo:
success = False
break

if success:
self.info("Device detected :)")
return True

except Exception as e: # Includes USBError, timeout, pipe error
except Exception as e:
self.debug(f"Handshake attempt {attempt + 1} failed: {e}")
time.sleep(0.01) # Short backoff

# Optional: flush input buffer before retry
try:
ep_in(maxinsize, timeout=50) # Discard any stale data
except:
pass
time.sleep(0.01)

self.info("Handshake failed after retries")
return False
Expand Down
6 changes: 4 additions & 2 deletions mtkclient/Library/exploit_handler.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
# (c) B.Kerler 2018-2025 GPLv3 License
import logging
import time
import traceback
from struct import pack, unpack

from mtkclient.Library.Hardware.hwcrypto import HwCrypto, CryptoSetup
Expand Down Expand Up @@ -91,8 +92,9 @@ def da_payload(self, payload, addr, forcekamakiri=True, exploittype=1):
self.info("Done sending payload...")
time.sleep(0.2)
return True
except Exception:
self.error("Error on sending payload.")
except Exception as _exploit_ex:
self.error(f"Error on sending payload: {_exploit_ex}")
traceback.print_exc()
return False
else:
self.info("Sending payload via insecure da.")
Expand Down
2 changes: 1 addition & 1 deletion mtkclient/config/usb_ids.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
default_ids = {
0x0E8D: {0x0003: -1, # MTK Brom
0x0E8D: {0x0003: 1, # MTK Brom - interface 1 has bulk endpoints (interface 0 is CDC comm/control only)

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This will break many devices :(

0x6000: 2, # MTK Preloader
0x2000: -1, # MTK Preloader
0x2001: -1, # MTK Preloader
Expand Down