Skip to content

USB CAT: readable serial port picker, VID+PID device match, diagnostics hint (#817) - #820

Merged
patrickrb merged 3 commits into
devfrom
fix/usb-port-picker-817
Sep 17, 2026
Merged

patrickrb merged 3 commits into
devfrom
fix/usb-port-picker-817

Conversation

@patrickrb

Copy link
Copy Markdown
Owner

Partial implementation of #817, scoped to the parts that hold for every rig.

Why not the rest of #817

The issue proposed auto-selecting the CAT interface from a VID:PID table and auto-probing interfaces × baud rates when CAT is silent. Both were checked against vendor docs and deliberately not implemented:

  • On the very same chip (Silicon Labs CP2105, 10C4:EA70) Yaesu (FT-891, FT-991A, FTDX10, FT-710) carries CAT on the Enhanced interface (0) and keying on Standard, while Kenwood's TS-890S manual says to use the Standard port for PC control (menu 7-01 "Baud Rate (Virtual Standard COM Port)"). Icom's IC-9700/IC-7610 also expose two ports (A = CI-V). A table keyed on the chip is wrong for someone; keying on the selected instruction set is not reliable either.
  • Baud-walking on the frame-less 5-byte Yaesu protocol (FT-817/857/897) can decode garbage as an opcode, including 0x08 = PTT on. FT-710 cable mode and the Hamlib backend never answer a read, so the probe would "fail" there by design. It would also have to coexist with the auto-reconnect loop and the CAT liveness watchdog (Fix CAT chip turning red while CAT still works (#781) #818).

The app now states the facts and leaves the choice to the operator. USB auto-connect still opens the first enumerated port (interface 0 = Enhanced, right for Yaesu) and a manual pick is still not persisted, so a wrong pick self-heals on restart.

What changes

  • Readable picker rowsSilicon Labs CP2105 · Port 1 of 2 · Enhanced / … Port 2 of 2 · Standard instead of \0x03E9\0x10C4\0xEA70\0x1. New pure SerialPortLabel (chip name from the driver class + PID; the role is only ever the chip's own interface name, never "CAT"/"PTT"). Same label feeds the legacy picker and the web log page through SerialPort.information().
  • Dual-port hint in the picker when a CP2105 is listed: Yaesu uses Enhanced for CAT, Kenwood TS-890S/TS-990S uses Standard, the other port carries RTS/DTR keying.
  • Device match by VID+PIDCableSerialPort.prepare() / isDevicePresent() matched on vendor id only and kept the last device the map iterated, so an FT-891 (CP2105) plus a Digirig (CP2102, same vendor) could open the wrong chip. Now: same deviceId+VID+PID, else first VID+PID, else (unknown PID, legacy) first vendor match. The match is logged to debug.log (serial.prepare: matched …).
  • CDC-class devices are listed when no prober claims them (prepare() already fell back to CdcAcmSerialDriver, so they could connect but never appeared in the picker), gated on an actual Communications-class interface so the rig's audio codec is not offered as a port.
  • USB Diagnostics: new "CAT Port" row (Port 2 of 2 · Standard · 4800 bd) and a hint under the card when the port is open but CAT is silent — the Enhanced/Standard note on a dual-port chip, a baud/model note otherwise. In FT-710 cable mode (read loop intentionally off) CAT Response is now an informational row with an explanation instead of a permanent red.

The off-by-one bounds bug listed in #817 was already fixed on dev (isValidPortIndex).

Tests

  • SerialPortLabelTest (17): chip names, Enhanced/Standard for CP2105 only, never hex, never a CAT/PTT role, template fallback.
  • CableSerialPortDeviceMatchTest (9): two Silicon Labs chips in either order, re-plug (new deviceId), recycled deviceId on another product, legacy vendor-only, CDC gate, FT-710 mode.
  • SerialPortPickerHintTest (3).
  • UsbDiagnosticsLogicTest (+14): row order, CAT Port value/template, INFO-not-FAIL for FT-710, hint selection.

Full unit suite: 3892 tests, 0 failures. Debug APK built and smoke-run on the Pixel_8 emulator (USB Diagnostics page renders the new row, no crash). Not verified on hardware — no phone was attached; a real CP2105 rig (FT-891/FT-991A) is needed to see the populated rows and the picker labels.

Closes #817 for the parts above; the auto-select and auto-probe proposals are declined with the reasoning here.

🤖 Generated with Claude Code

…by VID+PID (#817)

A Discord user with an FT-891 (Silicon Labs CP2105 dual UART) could not get
CAT working: every row of "Select Serial Port" printed raw hex
(\0x03E9\0x10C4\0xEA70\0x1) so nothing told them which of the two identical
rows was the CAT interface, and when they picked the wrong one the USB
Diagnostics page only said "CAT Response: fail".

The issue proposed auto-selecting the CAT interface from a VID:PID table and
auto-probing ports x baud rates when CAT is silent. Both are deliberately NOT
implemented: on the same 10C4:EA70 chip Yaesu carries CAT on the Enhanced
interface (0) while Kenwood's TS-890S manual says to use the Standard one (1),
so any table keyed on the chip is wrong for someone; and walking baud rates on
the frame-less 5-byte Yaesu protocol can decode garbage as an opcode (0x08 =
PTT on). The app states facts and leaves the choice to the operator.

What changes:

- Picker rows now read "Silicon Labs CP2105 · Port 1 of 2 · Enhanced" /
  "... Port 2 of 2 · Standard" (SerialPortLabel, pure + unit-tested). The
  role is only ever the chip's own interface name, never "CAT"/"PTT". The same
  label feeds the legacy picker and the web log page via information().
- The picker shows a one-line note when a dual-port chip is listed: Yaesu
  uses Enhanced for CAT, Kenwood TS-890S/TS-990S uses Standard.
- CableSerialPort.prepare() and isDevicePresent() match the picked device by
  deviceId+VID+PID, then VID+PID, instead of "last device with this vendor
  id" — an FT-891 plus a Digirig (both Silicon Labs) could open the wrong
  chip depending on HashMap order. The match is logged to debug.log.
- listSerialPorts() lists CDC-class devices that no prober claims (prepare()
  already fell back to CdcAcmSerialDriver for them, so they could connect but
  never appeared) — gated on an actual Communications-class interface so the
  rig's audio codec is not offered as a serial port.
- USB Diagnostics gains a "CAT Port" row ("Port 2 of 2 · Standard · 4800 bd")
  and a hint under the card when the port is open but CAT is silent: the
  Enhanced/Standard note on a dual-port chip, a baud/model note otherwise. In
  FT-710 cable mode (read loop intentionally off) CAT Response is now an
  informational row with a note instead of a permanent red.

Not changed: USB auto-connect still opens the first enumerated port, and a
manual pick is still not persisted (a wrong pick self-heals on restart).

Tests: SerialPortLabelTest, CableSerialPortDeviceMatchTest,
SerialPortPickerHintTest, UsbDiagnosticsLogicTest (+14 cases).

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
@codecov

codecov Bot commented Sep 17, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 56.97674% with 37 lines in your changes missing coverage. Please review.
✅ Project coverage is 42.04%. Comparing base (fd4db16) to head (aec7c96).

Files with missing lines Patch % Lines
...o/ks3ckc/ft8af/ui/settings/UsbDiagnosticsScreen.kt 62.33% 28 Missing and 1 partial ⚠️
...dio/ks3ckc/ft8af/ui/settings/RadioAudioSettings.kt 11.11% 8 Missing ⚠️
Additional details and impacted files

Impacted file tree graph

@@             Coverage Diff              @@
##                dev     #820      +/-   ##
============================================
+ Coverage     42.00%   42.04%   +0.04%     
  Complexity      239      239              
============================================
  Files           276      276              
  Lines         33097    33177      +80     
  Branches       3850     3871      +21     
============================================
+ Hits          13902    13949      +47     
- Misses        18913    18945      +32     
- Partials        282      283       +1     
Flag Coverage Δ
android 17.53% <56.97%> (+0.17%) ⬆️
native 9.93% <ø> (ø)

Flags with carried forward coverage won't be shown. Click here to find out more.

Files with missing lines Coverage Δ
...dio/ks3ckc/ft8af/ui/settings/RadioAudioSettings.kt 0.26% <11.11%> (+0.13%) ⬆️
...o/ks3ckc/ft8af/ui/settings/UsbDiagnosticsScreen.kt 55.75% <62.33%> (+4.13%) ⬆️
🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🟡 Changes recommended

Release obfuscation breaks chip labels, while diagnostics can misidentify or misclassify connected devices.

Get a fresh assessment by requesting another Copilot review.

Pull request overview

Improves USB CAT port selection, labeling, and diagnostics for multi-port and CDC devices.

Changes:

  • Matches USB devices by device ID, VID, and PID.
  • Adds readable serial-port labels and dual-port guidance.
  • Expands USB diagnostics and unit coverage.
File summaries
File Description
UsbDiagnosticsLogicTest.kt Tests CAT-port diagnostics and hints.
SerialPortPickerHintTest.kt Tests dual-port hint visibility.
SerialPortLabelTest.java Tests readable port labels.
CableSerialPortDeviceMatchTest.java Tests device matching and CDC detection.
strings_compose.xml Adds diagnostics and picker text.
UsbDiagnosticsScreen.kt Displays CAT port details and guidance.
RadioAudioSettings.kt Uses readable picker labels.
MainViewModel.java Exposes connected USB-port state.
SerialPortLabel.java Generates human-readable labels.
CableSerialPort.java Adds VID/PID matching and CDC fallback.
CableConnector.java Retains selected-port metadata.
Review details
  • Files reviewed: 11/11 changed files
  • Comments generated: 5
  • Review effort level: Balanced

💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Comment thread ft8af/app/src/main/java/com/k1af/ft8af/connector/CableSerialPort.java Outdated
Comment thread ft8af/app/src/main/kotlin/radio/ks3ckc/ft8af/ui/settings/UsbDiagnosticsScreen.kt Outdated
Comment thread ft8af/app/src/main/res/values/strings_compose.xml Outdated
patrickrb and others added 2 commits September 17, 2026 07:24
Resolves the strings_compose.xml conflict: the PR commit had rewritten the
file with CRLF line endings (whole-file conflict). Restored LF and took both
sides' string changes (#817 USB diag/picker strings + #819 share-logs).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
- Chip names no longer depend on getSimpleName(): R8 renames the driver
  classes in release, so map class literals to stable family keys.
- USB Diagnostics counts a CDC-ACM fallback device (Communications control
  interface) as a serial device, the same rule the picker uses.
- VID/PID/permission rows describe the connected CAT port's device
  (deviceId+VID+PID, then VID+PID after a replug) before the generic ranking.
- CAT hints are suppressed without a USB port or once CAT answered, then pick
  the FT-710 / dual-port / generic explanation.
- FT-710 hint text matches the informational (not red) row.
- UsbDiagnosticsLogicTest back to LF line endings.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@patrickrb
patrickrb merged commit 886a50e into dev Sep 17, 2026
19 checks passed
@patrickrb
patrickrb deleted the fix/usb-port-picker-817 branch September 17, 2026 12:40
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants