web-dev-qa-db-ja.com

systemdテンプレートのudevルールパラメータ

背景:usb-uartデバイスが接続したときにログスクリプトを開始したいと思います。

私の/etc/udev/rules.d/10-local.rules

SUBSYSTEM=="tty", ATTRS{idVendor}=="1366", ATTRS{idProduct}=="1015", ATTRS{serial}=="000621000000", SYMLINK+="ttymkw", TAG+="systemd", ENV{SYSTEMD_USER_WANTS}+="offnet-uart-log@$env{ID_SERIAL_SHORT}.service"

私の~/.config/systemd/user/[email protected]

[Unit]
Description=Start log of UART

[Service]
ExecStart=sh -c "echo %I >> /tmp/systemd.test"

これでは、ID_SERIAL_SHORTの期待値は得られません。代わりに、長いsysパスを取得します。

sys/devices/pci0000:00/0000:00:1c.0/0000:01:00.0/0000:02:02.0/0000:39:00.0/usb3/3-1/3-1.7/3-1.7.2/3-1.7.2:1.0/tty/ttyACM0

このパスのプロパティを取得しようとすると(先頭のsysを削除する必要があります)、ID_SERIAL_SHORTが表示されます。

$ udevadm info --query=property --path /devices/pci0000:00/0000:00:1c.0/0000:01:00.0/0000:02:02.0/0000:39:00.0/usb3/3-1/3-1.7/3-1.7.2/3-1.7.2:1.0/tty/ttyACM0DEVPATH=//devices/pci0000:00/0000:00:1c.0/0000:01:00.0/0000:02:02.0/0000:39:00.0/usb3/3-1/3-1.7/3-1.7.2/3-1.7.2:1.0/tty/ttyACM0
DEVNAME=/dev/ttyACM0
MAJOR=166
MINOR=0
SUBSYSTEM=tty
USEC_INITIALIZED=1633350773062
[email protected]
ID_BUS=usb
ID_VENDOR_ID=1366
ID_MODEL_ID=1015
ID_PCI_CLASS_FROM_DATABASE=Serial bus controller
ID_PCI_SUBCLASS_FROM_DATABASE=USB controller
ID_PCI_INTERFACE_FROM_DATABASE=XHCI
ID_VENDOR_FROM_DATABASE=SEGGER
ID_MODEL_FROM_DATABASE=DSL6340 USB 3.1 Controller [Alpine Ridge]
ID_VENDOR=SEGGER
ID_VENDOR_ENC=SEGGER
ID_MODEL=J-Link
ID_MODEL_ENC=J-Link
ID_REVISION=0100
ID_SERIAL=SEGGER_J-Link_000621000000
ID_SERIAL_SHORT=000621000000                 ### <--- here
ID_TYPE=generic
ID_USB_INTERFACES=:020201:0a0000:ffffff:080650:
ID_USB_INTERFACE_NUM=00
ID_USB_DRIVER=cdc_acm
ID_USB_CLASS_FROM_DATABASE=Miscellaneous Device
ID_USB_PROTOCOL_FROM_DATABASE=Interface Association
ID_PATH=pci-0000:39:00.0-usb-0:1.7.2:1.0
ID_PATH_TAG=pci-0000_39_00_0-usb-0_1_7_2_1_0
ID_MM_CANDIDATE=1
DEVLINKS=/dev/ttymkw /dev/serial/by-id/usb-SEGGER_J-Link_000621000000-if00 /dev/serial/by-path/pci-0000:39:00.0-usb-0:1.7.2:1.0
TAGS=:systemd:

udevルールの$env{ID_SERIAL_SHORT}が、プロパティの値に置き換えられていないようです。

Udevのmanページによると、$env{key}置換はNAME、SYMLINK、PROGRAM、OWNER、GROUP、MODE、SECLABEL、およびRUNフィールドでのみ使用できます。

ただし、ENV{SYSTEMD_USER_WANTS}それを使用する人々の例 を見てきました。どうやら、私にはうまくいきません。

デバイスのシリアル番号をsystemdテンプレートに渡すにはどうすればよいですか?


編集: this も試しましたが、いいえ:

SUBSYSTEM=="tty", ATTRS{idVendor}=="1366", ATTRS{idProduct}=="1015", ATTRS{serial}=="000621000000", SYMLINK+="ttymkw", PROGRAM="/bin/systemd-escape -p [email protected] $env{ID_SERIAL_SHORT}", ENV{SYSTEMD_WANTS}+="%c"
3
Gauthier

私が探しているパラメータは$attr{serial}です。他のソリューションが他のソリューションで機能したのになぜ機能しなかったのかはわかりませんが、時代遅れだと思います(編集:10で始まる私のルールファイルが、環境変数ID_SERIALを作成するルールファイルの前に読み込まれるためと考えられます、60から始まる)。これは機能しています:

udevルール:

SUBSYSTEM=="tty", ATTRS{idVendor}=="1366", SYMLINK+="ttymkw", ENV{SYSTEMD_WANTS}+="offnet-uart-log@$attr{serial}"

Systemdテンプレート:

[Unit]
Description=Start log of UART for a Offnet unit

[Service]
ExecStart=/bin/sh -c "/bin/echo %i >> /tmp/asdf.log"

どうやらTAGは必要なく、$attrではなく$envを使用する必要があります。

systemdのバージョンは241です。

Q/A 助けてくれました。


編集:$envが機能しない理由は、ファイルがID_SERIAL_SHORTであるのに、10-local.rulesがレベル60のルールで作成されている可能性があります。 ありがとう @yuwata。 (検証されていない。)

2
Gauthier

別の回避策として、systemdサービスがExecStartステートメントでスクリプトを呼び出している場合、質問に示されている同じudevadm呼び出しをそのスクリプトに含めることができますgrepを介してID_SERIAL_SHORTを抽出します。

1
AdminBee

回避策として、udevルールで独自の環境変数を作成できます。

SUBSYSTEM=="tty", ATTRS{idVendor}=="1366", ATTRS{idProduct}=="1015", \
ATTRS{serial}=="000621000000", SYMLINK+="ttymkw", TAG+="systemd", \ 
ENV{MY_ID}="000621000000", \
ENV{SYSTEMD_USER_WANTS}+="offnet-uart-log@$env{MY_ID}.service"

(読みやすくするためにバックスラッシュを使用します。これは1行に入力する必要があります。)

または、実際には、@の直後に文字列を書き込むだけです。

ただし、これらは必要ありません。

0
Gauthier