Skip to content

Commit

Permalink
Fix macOS specific ports scanning issues
Browse files Browse the repository at this point in the history
Modify the `filtered_comports` function in `src/mpflash/mpflash/common.py` to exclude non-microcontroller ports based on descriptions and hardware ID patterns.

* Exclude ports with descriptions containing "debug-console" on MacOS / Darwin.
* Add trace logging with more Bluetooth hardware details during filtering of the ports.

Add tests for the changed functionality in `src/mpflash/tests/test_filtered_comports.py`.

* Add tests for MacOS ports filtering.
* Verify that non-microcontroller ports are correctly excluded.
  • Loading branch information
Josverl committed Dec 16, 2024
1 parent a2a55d1 commit 4724ffb
Show file tree
Hide file tree
Showing 2 changed files with 24 additions and 1 deletion.
4 changes: 3 additions & 1 deletion src/mpflash/mpflash/common.py
Original file line number Diff line number Diff line change
Expand Up @@ -77,7 +77,7 @@ class Params:
"""Common parameters for downloading and flashing firmware"""

ports: List[str] = field(default_factory=list)
boards: List[str] = field(default_factory=list)
boards: List[str] = field(default_factory.list)
versions: List[str] = field(default_factory=list)
fw_folder: Path = Path()
serial: List[str] = field(default_factory=list)
Expand Down Expand Up @@ -165,8 +165,10 @@ def filtered_comports(
# filter out bluetooth ports
comports = [p for p in comports if "bluetooth" not in p.description.lower()]
comports = [p for p in comports if "BTHENUM" not in p.hwid]
comports = [p for p in comports if "debug-console" not in p.description.lower()]
if sys.platform == "darwin":
comports = [p for p in comports if ".Bluetooth" not in p.device]
comports = [p for p in comports if not p.device.startswith("/dev/cu.")]
log.trace(f"no Bluetooth: {[p.device for p in comports]}")
log.debug(f"filtered_comports: {[p.device for p in comports]}")
# sort
Expand Down
21 changes: 21 additions & 0 deletions src/mpflash/tests/test_filtered_comports.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,9 @@
[{"description": "USB Serial Device (COM8)", "device": "COM8", "hwid": "USB VID:PID=F055:9802 SER=7A674ABB5336464E4E202020FF130722 LOCATION=1-5:x.0", "interface": null, "location": "1-5:x.0", "manufacturer": "Microsoft", "name": "COM8", "pid": 38914, "product": null, "serial_number": "7A674ABB5336464E4E202020FF130722", "vid": 61525}, {"description": "Standard Serial over Bluetooth link (COM15)", "device": "COM15", "hwid": "BTHENUM\\\\{00001101-0000-1000-8000-00805F9B34FB}_VID&00010067_PID&094E\\\\7&4CE5CE3&0&745C4B893934_C00000000", "interface": null, "location": null, "manufacturer": "Microsoft", "name": "COM15", "pid": null, "product": null, "serial_number": null, "vid": null}, {"description": "Standard Serial over Bluetooth link (COM13)", "device": "COM13", "hwid": "BTHENUM\\\\{00001101-0000-1000-8000-00805F9B34FB}_VID&00010067_PID&094E\\\\7&4CE5CE3&0&50C275017686_C00000000", "interface": null, "location": null, "manufacturer": "Microsoft", "name": "COM13", "pid": null, "product": null, "serial_number": null, "vid": null}, {"description": "Standard Serial over Bluetooth link (COM17)", "device": "COM17", "hwid": "BTHENUM\\\\{00001101-0000-1000-8000-00805F9B34FB}_LOCALMFG&0000\\\\7&4CE5CE3&0&000000000000_00000000", "interface": null, "location": null, "manufacturer": "Microsoft", "name": "COM17", "pid": null, "product": null, "serial_number": null, "vid": null}, {"description": "Standard Serial over Bluetooth link (COM5)", "device": "COM5", "hwid": "BTHENUM\\\\{00001101-0000-1000-8000-00805F9B34FB}_LOCALMFG&0000\\\\7&4CE5CE3&0&000000000000_00000001", "interface": null, "location": null, "manufacturer": "Microsoft", "name": "COM5", "pid": null, "product": null, "serial_number": null, "vid": null}, {"description": "USB Serial Device (COM9)", "device": "COM9", "hwid": "USB VID:PID=2341:025E SER=50159300709F8C1C LOCATION=1-6.2:x.0", "interface": null, "location": "1-6.2:x.0", "manufacturer": "Microsoft", "name": "COM9", "pid": 606, "product": null, "serial_number": "50159300709F8C1C", "vid": 9025}]
"""

macos_ports_json = """
[{"description": "Bluetooth-Incoming-Port", "device": "/dev/tty.Bluetooth-Incoming-Port", "hwid": "BTHENUM\\\\{00001101-0000-1000-8000-00805F9B34FB}_VID&00010067_PID&094E\\\\7&4CE5CE3&0&745C4B893934_C00000000", "interface": null, "location": null, "manufacturer": "Apple", "name": "Bluetooth-Incoming-Port", "pid": null, "product": null, "serial_number": null, "vid": null}, {"description": "debug-console", "device": "/dev/tty.debug-console", "hwid": "USB VID:PID=F055:9802 SER=7A674ABB5336464E4E202020FF130722 LOCATION=1-5:x.0", "interface": null, "location": "1-5:x.0", "manufacturer": "Apple", "name": "debug-console", "pid": 38914, "product": null, "serial_number": "7A674ABB5336464E4E202020FF130722", "vid": 61525}, {"description": "Hermes", "device": "/dev/tty.Hermes", "hwid": "BTHENUM\\\\{00001101-0000-1000-8000-00805F9B34FB}_VID&00010067_PID&094E\\\\7&4CE5CE3&0&50C275017686_C00000000", "interface": null, "location": null, "manufacturer": "Apple", "name": "Hermes", "pid": null, "product": null, "serial_number": null, "vid": null}, {"description": "usbmodem2101", "device": "/dev/tty.usbmodem2101", "hwid": "USB VID:PID=2341:025E SER=50159300709F8C1C LOCATION=1-6.2:x.0", "interface": null, "location": "1-6.2:x.0", "manufacturer": "Apple", "name": "usbmodem2101", "pid": 606, "product": null, "serial_number": "50159300709F8C1C", "vid": 9025}]
"""

@pytest.mark.parametrize(
"id, include, ignore, bluetooth, expected",
Expand Down Expand Up @@ -82,3 +85,21 @@ def platform_system():
result = filtered_comports(include=["*"], ignore=[], bluetooth=False)
devices = [port.device for port in result]
assert len(devices) == 1


@pytest.mark.parametrize(
"id, include, ignore, bluetooth, expected",
[
("00-default", ["*"], [], False, ["/dev/tty.usbmodem2101"]),
("10-ignore", ["*"], ["/dev/tty.usbmodem2101"], False, []),
("20-include", ["/dev/tty.usbmodem2101"], [], False, ["/dev/tty.usbmodem2101"]),
("30-include-over", ["/dev/tty.usbmodem2101"], ["/dev/tty*"], False, ["/dev/tty.usbmodem2101"]),
],
)
def test_filtered_comports_macos(id, include, ignore, bluetooth, expected, mocker):
macos_ports = jsons.loads(macos_ports_json, List[ListPortInfo])
mocker.patch("mpflash.common.list_ports.comports", return_value=macos_ports)
result = filtered_comports(include=include, ignore=ignore, bluetooth=bluetooth)
devices = [port.device for port in result]
assert all([(e in devices) for e in expected]), f"{expected} not in {devices}"
assert all([(d in expected) for d in devices]), f"{devices} not in {expected}"

0 comments on commit 4724ffb

Please sign in to comment.