Radix 16 (live-verified), universal reply splitter, golden capture vectors, host_probe6

This commit is contained in:
kfj001 committed 2026-10-16 02:50:23 +00:00
1 parent 0cd6b34a2e
commit 62e0fd649b
10 files changed
+418 -82

No files matched your search

+16 -8
View File
@@ -125,16 +125,18 @@ def get_battery(
sn: str,
host: str = "10.100.1.1",
ports: Tuple[int, ...] = SOCKET_PORT_CANDIDATES,
key_radix: int = 32,
key_radix: int = 16,
timeout: float = 5.0,
) -> Dict[str, Any]:
"""Query the aggregate charge percentage over the local TCP socket.
Mirrors the app's ``queryAPowerData`` first (``DEVICE_APOWER_INFO`` with
``data={"update": 2}``), then ``BMS`` and ``EMS`` as fallbacks, probing
each candidate port. Returns the ``extract_soc`` dict plus
``cmd``/``port``/``reply`` context. Raises the last socket error if no
port answers.
``data={"opt": 0, "update": 2}``), then ``BMS`` and ``EMS`` as fallbacks,
probing each candidate port. Like the app's direct-connect flow, a
discovery query (``QUERY_DEVICE_INFO``, empty serial) opens each port's
sequence — its reply also confirms two-way crypto before the battery
read. Returns the ``extract_soc`` dict plus ``cmd``/``port``/``reply``
context. Raises the last socket error if no port answers.
"""
last_err: Optional[Exception] = None
for port in ports:
@@ -142,6 +144,12 @@ def get_battery(
sn=sn, host=host, socket_port=port,
key_radix=key_radix, timeout=timeout,
)
try:
client.send_rpc(CommunicationCmd.QUERY_DEVICE_INFO,
equip_no="",
data={"minProtocolVer": "V1.00.00"})
except Exception as exc: # discovery is best-effort; keep going
log.debug("port %d discovery failed: %s", port, exc)
for cmd, data in (
(CommunicationCmd.DEVICE_APOWER_INFO, {"update": 2}),
(CommunicationCmd.BMS, None),
@@ -182,7 +190,7 @@ def probe_device(
sn: str,
host: str = "10.100.1.1",
ports: Tuple[int, ...] = SOCKET_PORT_CANDIDATES,
key_radix: int = 32,
key_radix: int = 16,
timeout: float = 5.0,
) -> List[Dict[str, Any]]:
"""Send every :data:`PROBE_VARIANTS` envelope; return exact TX/RX bytes."""
@@ -251,7 +259,7 @@ def probe_transport(
sn: str,
host: str = "10.100.1.1",
ports: Tuple[int, ...] = (9000,),
key_radix: int = 32,
key_radix: int = 16,
timeout: float = 5.0,
) -> List[Dict[str, Any]]:
"""Transport-level probes against one service port.
@@ -323,7 +331,7 @@ def main(argv: Optional[List[str]] = None) -> int:
"--ports", default=",".join(map(str, SOCKET_PORT_CANDIDATES)),
help="comma-separated socket ports to probe",
)
parser.add_argument("--key-radix", type=int, default=32, choices=(16, 32))
parser.add_argument("--key-radix", type=int, default=16, choices=(16, 32))
parser.add_argument("--timeout", type=float, default=5.0)
parser.add_argument("--show-hotspot", action="store_true",
help="print derived AP SSID/password and exit")