背景
COMポート名ではなくvid(ベンダーID)とpid(プロダクトID)を指定してシリアルポートを開きたい場面があったので、参照方法を調べて実現しました。備忘録として記事を残します。
使ったもの
- USBポートがあるPC
今回はUbuntu 22.04をインストールしたノートPCを利用しました - python3
Ubuntuの場合は下記コマンドでインストールできますsudo apt install -y python3-pip
- USBシリアルポート対応機器
この記事はESP32S3を接続対象として解説します。
ライブラリインストール: pyserial
pyserialを使ってvidとpidの参照とシリアルポートの接続を行います。pipコマンドでインストールできます。
python -m pip install pyserial
lsusbでpid vidを確認
linuxならlsusbコマンドでpidとvidを確認できます。lsusb
Bus 002 Device 041: ID 303a:1001 Espressif USB JTAG/serial debug unit
コロン「:」で繋がっている数字の左がvid、右がpidです。
書き方
serial.toolのlist_portsを使ってvidとpidでポートを絞り込めます。コード全体を共有後に要所を解説します。
from serial.tools import list_ports
import serial
target_vid = 0x303a
target_pid = 0x1001
path_to_open = None
bps_to_open = 115200
opened_stream = None
for comport in list_ports.comports():
print(comport)
print(comport.hwid)
if comport.vid is not None and comport.vid == target_vid and comport.pid == target_pid:
path_to_open = comport.device
if path_to_open is not None:
try:
opened_stream = serial.Serial(path_to_open, bps_to_open)
print("opened stream")
except serial.serialUtil.SerialException as e:
print("failed to open serial port")
print(e)
else:
print("cannot find target serial port")
serial.toolsはimportしたserial経由では呼べないので、from serial.toolsで中身(list_ports)を呼びます。
from serial.tools import list_ports
import serial
lsusbで取得したvidとpidを持つポートを探します。
target_vid = 0x303a
target_pid = 0x1001
comports関数で認識しているポートの一覧が取得できるので、それのvidとpidを参照します。
hwidでvid pid serial_numberなどを表示します。
serial_numberを参照してvidとpidが同じでも個体識別可能な装置が基本だと思いますが、serial_numberが同じで識別不能な装置もあるので、serial_numberを使う場合は確認が必要です。
comportのパスはdeviceで取得できます。
for comport in list_ports.comports():
print(comport)
print(comport.hwid)
if comport.vid is not None and comport.vid == target_vid and comport.pid == target_pid:
path_to_open = comport.device
comport.deviceで取得したパスがあれば開きます。
パスを取得したものの開けない場合は「serial.serialutil.SerialException」でエラーが発生するので、開けない場合もプログラムを終えずにループを繰り返したい場合はそれをexceptして処理を続けます。
if path_to_open is not None:
try:
opened_stream = serial.Serial(path_to_open, bps_to_open)
print("opened stream")
except serial.serialutil.SerialException as e:
print("failed to open serial port")
print(e)
else:
print("cannot find target serial port")
ESP32S3の内蔵jtagポートに対して上記のプログラムを実施した場合、下記のようなログが表示されます。
/dev/ttyACM0 - USB JTAG/serial debug unit
USB VID:PID=303A:1001 SER=F4:12:FA:84:14:24 LOCATION=2-1:1.0
opened stream
おわり
pythonでUSBのvidとpidを指定してシリアルポートを開けました。他に良い方法や書き方があれば、コメントなどで教えていただけると嬉しいです。
参考
Is it possible to refer to a serial device by vendor and device ID in pySerial?serial.tools.list_ports
0 件のコメント :
コメントを投稿