次の問題があります。 fifoデバイスファイルを生成するスクリプトを作成していますが、ファイルがすでに存在していてもtrueを返したいと思います。次のコードスニペット||
とでFIFOを生成しようとします/bin/true
。mkfifo
cmdの最後のパラメータが何であるかをどうやって知ることができますかX
?
$ /usr/bin/mkfifo /dev/fifofile || /bin/true
システムサービスで実行します。
ExecStartPre=/usr/bin/mkfifo /dev/fifofile || /bin/true
Apr 29 08:39:40 mkfifo[27275]: /usr/bin/mkfifo: cannot create fifo '/dev/fifofile': File exists
Apr 29 08:39:40 mkfifo[27275]: /usr/bin/mkfifo: cannot create fifo '||': File exists
Apr 29 08:39:40 mkfifo[27275]: /usr/bin/mkfifo: cannot create fifo '/bin/true': File exists
ExecStartPre
に変更しようとすると、ExecStartPre=(/usr/bin/mkfifo /dev/fifofile) || /bin/true
次のエラーが発生します。
Executable path is not absolute: (/usr/bin/mkfifo /dev/gpsfifo) || /bin/true
ベストアンサー1
ExecStartPre=/usr/bin/mkfifo /dev/fifofile || /bin/true
シェルのコマンドラインでは問題ありませんが、systemdはシェルを介してExecStartPre
コマンドなどを実行しません。 (mkfifo
そしてパスが必要かどうかはわかりません。)true
これ文書によるとそれ:
systemd.syntax(5) の「引用」セクションで説明されている規則を使用して、各コマンドラインの引用を解放します。最初の項目は実行するコマンドになり、次の項目はパラメーターになります。
構文はシェル構文に触発されましたが、次の段落で説明するメタ文字と拡張のみを理解し、変数は異なる方法で拡張されます。特に、およびを使用してリダイレクトし、パイプを
<
使用して、バックグラウンドでプログラムを実行します。<<
>
>>
|
&
シェル構文の他の要素はサポートされていません。。
ただし、引用符が機能する必要があるため、次のコマンドを使用して明示的にシェルを実行できます。
ExecStartPre=sh -c 'mkfifo /dev/fifofile || true'.
しかし、systemdにはエラーを無視する特別な構文があるため、これは必要ありません。
実行可能ファイルパスに接頭辞が付けられている場合、通常は
-
失敗(たとえば、ゼロ以外の終了状態またはシグナルによる異常終了)と見なされるコマンドの終了コードが記録されますが、もはや効果がなく、次のように見なされます。成功。
だから
ExecStartPre=-mkfifo /dev/fifofile
すべきこと。
しかし、リダイレクトの説明には>
、代わりに2>
。ただし、最初にファイルを削除してから再作成することもできます。
ExecStartPre=-rm -f /dev/fifofile
ExecStartPre=-mkfifo /dev/fifofile
もちろん、これは同じ名前を持つ他のファイルもすべて削除します。
これを防ぐには、次の手順を実行します。
ExecStartPre=sh -c '[ -p /dev/fifofile ] || mkfifo /dev/fifofile'
パイプがすでに存在する場合は自動的に終了する必要がありますが、mkfifo
ファイルが存在し、まだパイプではない場合はエラーが発生します。
fifoファイルを置くためのより「正しい」場所があるかもしれません。