2015-10-12 103 views
0

我已經編寫了一個守護程序,它管理一個或多個RS232設備(通常爲FT232R usb2serial)上的多種通信協議。 一旦的/ dev/ttyUSB *設備出現時,如果檢測到某些屬性, systemd被告知通過的udev啓動一個進程:systemctl服務啓動後執行udev的RUN語句

ENV{SYSTEMD_WANTS}="%s{manufacturer}.service" 

一旦守護進程已經開始,它需要被告知要打開哪個設備,這是我通過udev的事:

RUN="/usr/bin/sercomc open %E{sd_name} %E{sd_proto} %N" 

所以完整的udev規則讀起來像是:

ACTION=="add", SUBSYSTEM=="tty", ATTRS{idVendor}=="0403", ATTRS{idProduct}=="6001", ATTRS{manufacturer}=="sercomd", ENV{SYSTEMD_WANTS}="%s{manufacturer}.service", ENV{sd_proto}="%s{product}", ENV{sd_name}="%s{serial}", RUN="/usr/bin/sercomc open %E{sd_name} %E{sd_proto} %N" 

現在的問題是運行時befor執行E中的守護進程啓動,使 這個命令顯然沒有任何效果:

systemd-udevd[1638]: starting '/usr/bin/sercomc open ctl-vk1 ctserial /dev/ttyUSB0' 
systemd-udevd[1632]: '/usr/bin/sercomc open ctl-vk1 ctserial /dev/ttyUSB0'(err) 'Couldn't connect to server: Connect failed: Connection refused' 
[...] 
sercomctl[1639]: [2015-10-12 03:05:39:291634] Serial communication daemon ver. 0.5 starting up 

是否有解決這一點,即運行命令一旦systemd啓動完成業務觸發一個推薦的方式?

回答

0

如果您偶然發現了類似問題並閱讀了該問題,請不要讓自己被我正在使用的軟件的名稱所迷惑。讓我們趕快說「sercomd」是管理串行連接的守護進程的名稱,「sercomc」是一個客戶端程序,告訴sercomd使用某種協議打開該設備。此外,我操縱了FTDI usb2串行芯片的EEPROM,使產品,製造商和串行字符串顯示用戶定義的值,我可以使用它來「串連適配器的即插即用」自動識別。

我正在做的是爲每個出現的設備使用單元文件的實例化服務 /lib/systemd/system/[email protected]

的udev規則現規定:

SUBSYSTEM=="tty", ATTRS{idVendor}=="0403", ATTRS{idProduct}=="6001", ATTRS{manufacturer}=="sercomd", ACTION=="add", SYMLINK="tty%s{serial}", PROGRAM="/bin/systemd-escape %s{serial}", ENV{SYSTEMD_WANTS}="[email protected]%c.service", ENV{sd_proto}="%s{product}", ENV{sd_dev}="%N" 

此規則設置一些環境變量sd_proto和sd_dev,並且然後可以從sercomd @。服務文件中提取的第三個參數sd_dev:

ExecStart=/bin/bash -c "eval $$(udevadm info --query=env --export /dev/tty%I); sercomc open %I $$sd_proto $$sd_dev" 

ExecStop =的/ usr /斌/ sercomc -l%I關閉

因此,每一個設備被添加或從USB集線器移除時間,相應的客戶端命令從s運行ystemd。 通過添加

Requires=sercomd.service 
    After=sercomd.service 

到單位的文件,它也將確保在客戶端進行之前,實際上管理這些接口,我的守護進程啓動。

+0

如果您認爲您的問題很混亂,請編輯您的問題以解釋。 –