web-dev-qa-db-ja.com

同一のUSBシリアルデバイスに既知のシンボリックリンクを割り当てるためのudevルール

私は2つの(そしておそらく将来的にはもっと)USBシリアルデバイスを持っています(残念ながらシリアル番号まで)-それらは実際にはBTCマイナーです。現在、それらはttyUSBXとして終わります。ここで、Xは0、1、または2です。関係のない別のUSBシリアルデバイスもあるためです(ここで心配する必要はありません)。

/devのように/dev/miner0のように予測可能な名前を割り当てるudevルールを書きたいと思います。ここで、ゼロは増加する整数です。どちらが最終的にどちらになるかは気にしませんが、変化しない予測可能な範囲内にある必要があります。

現在私はこれを持っています:

SUBSYSTEM=="tty", ATTRS{idVendor}=="10c4", ATTRS{idProduct}=="ea60", SYMLINK+="miner%n"

私が望むような名前になってしまうので、これはかなり近いです。唯一の問題は、鉱山労働者と3番目のデバイスがランダムな順序で表示されることがあるので、miner0miner1miner2の2つになってしまう可能性がありますが、どちらかはわかりません2つ(手動で探す必要なし)。マイナー以外のUSBシリアルデバイスを追加すると(可能性があります)、問題が悪化します。

%eへの参照が見つかりましたが、それは私が望んでいたとおりのことをしたように見えましたが、それは もう存在していないようです です。

これらのデバイスに予測可能な名前を付けるにはどうすればよいですか?できれば、USBバス上の場所にも接続しないようにしたいと思います。


詳細情報/背景

デバイスが別のUSBソケットに接続されても、名前がわかっていて変わらないというだけで、名前が気にならないことに言及する価値があります。私は単にudev全体を忘れて/dev/serial/by-idのエントリを使用しますが、それらは同じシリアル番号を持っているため、そこには1つしかありません!

また、これを行う理由は、マイニングソフトウェアに、プローブおよび検出するデバイスのリストを通知する必要があることです。私はそれをすべて行うことができます(基本的にはttyUSB*範囲内のすべての有効なマイナーを見つけるだけです)が、それは非マイナーデバイスを困らせます。それで、それらだけを使用するように構成できるように、事前にわかっている鉱夫の名前が必要です。悲しいことに、それはワイルドカードを受け入れません(そのため、/dev/miner*を使用するように指示するだけでは問題外と思われます)、したがってこの問題です。

8
Mark Embling

これは組み合わせでテストされていません:

鉱夫のためにIMPORT{program}="/usr/local/sbin/unique-num /run/miner-counter 0 MINER_NUM"にudevルールを追加します。

次に、次のようなある程度テストされたプログラムのような単純なシェルスクリプトを使用できます。

#!/bin/sh

if [ $# -ne 3 ]; then
    echo "Usage: $0 data-file initial var-name" >&2
    exit 1
fi

datfile="$1"
lockfile="$1.lck"
initial=$2
key="$3"

(
    flock -x 9
    num=$initial
    if [ -e "$datfile" ]; then
        read -r num < "$datfile"
    fi

    next=`expr $num + 1`;
    echo $next > "$datfile"

    echo "$key=$num"
) 9> "$lockfile"

次に、そのudev環境変数を使用してマイナーに名前を付けることができます。

4
derobert

質問にはすでに受け入れられた回答がありますが、私は derobert によって提供される solution のバリエーションを共有することにしました。

私の要件は少し異なりました-新しいデバイスに「増加する」インデックス番号を提供することに加えて、システムから削除されたデバイスによって与えられたインデックス番号を再取得したいと思っていました。

環境変数を設定するためのudevルールは次のようになります。

IMPORT{program}="/usr/local/sbin/unique-num /dev miner MINER_NUM"

私の解決策では、インデックスを追跡するためにファイルを使用せず、既存の symlink をループして、利用可能な最初のインデックスを見つけるだけです。

/usr/local/sbin/unique-num 脚本:

#!/bin/bash

if [ $# -ne 3 ]; then
    echo "Usage: $0 location prefix var-name" >&2
    exit 1
fi

location="$1"
prefix="$2"
key="$3"

needindex=1
index=0

while [ $needindex -eq 1 ]
do
        if [ ! -e $location/$prefix$index ]; then
                needindex=0
                echo "$key=$index"
        else
                (( index++ ))
        fi
done

もちろん、これは、たとえば次の symlink がすでに存在する場合、最初に使用可能なインデックスを含むvar-nameを出力します。

miner0
miner1
miner2

その後 miner1はシステムから切り離されています-残っています:

miner0
miner2

スクリプトを実行すると戻ります。

MINER_NUM=1

...これは現在最初に使用可能なインデックスであるため。

2
dtmland