サーバーには複数の NIC がありますが、そのうちの 1 つにのみケーブルが接続されています。
特定のポートethX
が接続されているかどうかをテストするにはどうすればよいでしょうか?
似たようなものがたくさん見つかりました質問、しかし、どちらも私には機能しませethtool
んcat /sys/class/net/eth1/carrier
。
私の場合、ケーブルは実際には に接続されていますeth2
が、ethtool
それでも表示されますLink detected: no
Settings for eth2:
Supported ports: [ FIBRE ]
Supported link modes: 10000baseT/Full
Supported pause frame use: Symmetric
Supports auto-negotiation: No
Advertised link modes: 10000baseT/Full
Advertised pause frame use: Symmetric
Advertised auto-negotiation: No
Speed: Unknown!
Duplex: Unknown! (255)
Port: Direct Attach Copper
PHYAD: 0
Transceiver: internal
Auto-negotiation: off
Supports Wake-on: d
Wake-on: d
Current message level: 0x00000007 (7)
drv probe link
Link detected: no
にはケーブルが接続されていませんeth3
が、ethtool
出力はほぼ同じに見えます。
diff <(ethtool eth2) <(ethtool eth3)
1c1
< Settings for eth2:
---
> Settings for eth3:
11c11
< Port: Direct Attach Copper
---
> Port: Other
最初にインターフェイスを起動するとeth2
、ethtool
が表示されますLink detected: yes
。その後、インターフェイスをダウンしても、ethtool
はリンクを として報告します。yes
つまり、ethtool
インターフェースがアップグレードされる前は、最初は機能しないようです。
特定のインターフェースにケーブルが接続されているかどうかを確実にテストするにはどうすればよいでしょうか?
答え1
ソケットにケーブルが差し込まれた物理的な状態ではなく、NIC のリンク状態を調べたいのだと思います (調べるのは不可能かもしれません)。
ちょっと検索してみると、すでに答えが見つかるのではないかと思います。インターフェースを起動し、リンクが見つかるまで待ちます。リンクがあれば (数秒かかる場合があります)、 、ethtool
またはcarrier
および/または のoperstate
出力を確認します/sys/class/net/$NIC/
。
ifconfig somenic up
次の 2 つの呼び出しを行うようですioctl
:
ioctl(4, SIOCGIFFLAGS, {ifr_name="somenic", ifr_flags=IFF_BROADCAST|IFF_MULTICAST}) = 0
ioctl(4, SIOCSIFFLAGS, {ifr_name="somenic", ifr_flags=IFF_UP|IFF_BROADCAST|IFF_RUNNING|IFF_MULTICAST}) = 0
つまり、 を設定しますIFF_UP
。ここ実際にデバイスを初期化する設定は次のとおりです。
次に、 (ソケット I/O 制御インターフェイス フラグの設定)を使用して
IFF_UP
ビットを設定し、インターフェイスをオンにします。dev->flag
ioctl(SIOCSIFFLAGS)
ただし、後者のコマンド (
ioctl(SIOCSIFFLAGS)
) は、デバイスの open メソッドを呼び出します。実際のコードに関する限り、ドライバーは char ドライバーや block ドライバーと同じタスクの多くを実行する必要があります。open は必要なシステム リソースを要求し、インターフェイスを起動するように指示します。
同様のコメントはe1000e
ドライバーソース:
/**
* e1000e_open - Called when a network interface is made active
* @netdev: network interface device structure
*
* Returns 0 on success, negative value on failure
* * The open entry point is called when a network interface is made
* active by the system (IFF_UP). At this point all resources needed
* for transmit and receive operations are allocated, the interrupt
* handler is registered with the OS, the watchdog timer is started,
* and the stack is notified that the interface is ready.
**/
int e1000e_open(struct net_device *netdev)
つまり、NICのリンク状態を意味のある方法で見つける方法はないということです。上ハードウェアが初期化されないためです。
もちろん、一部のドライバーが異なる動作をして、誰かが設定する前にハードウェアを初期化することは少なくとも理論的には可能ですがIFF_UP
、それでも一般的なケースでは役に立ちません。
1 台のマシン ( e1000e
Cisco スイッチに接続) でインターフェイスをプルダウンすると、スイッチもリンクがダウンしたことを認識します。
別のマシン (Realtek NIC が組み込まれている) では、アップからダウンへの変更により、リモート スイッチが短時間切断されますが、スイッチはリンクを認識し、その後再びアップになります。 (ethtool
ただし、PC 側では「リンクなし」と表示されます。) これは、Wake-on-LAN などの準備と関係があるかどうかはわかりませんが、まったくわかりません。
答え2
ifplugstatus
パッケージからコマンドを試すifplugd
$ ifplugstatus net0
net0: unplugged
$ ifplugstatus wlnet0
wlnet0: link beat detected
画面出力以外にも、コマンドの終了ステータスからも確認できます。
(manページより)
戻り値
0 Success 1 Failure 2 Link beat detected (only available when an interface is specified) 3 Unplugged (same here)
答え3
ethertoolsのソースコードを確認しましたが、リンク状態が記述されている箇所が見つかりませんでした。
その後、これが SO の質問とまったく同じであることがわかりました。https://stackoverflow.com/questions/808560/how-to-detect-the-physical-connected-state-of-a-network-cable-connector
そこにリストされている回答のほとんど (mii-tools、ethertool、cat the carrier または operstate、dmesg) を試しましたが、ifconfig がダウンしているときにリンク上で正しく機能するものはありませんでした。
SOの質問は6年以上前のものなので、可能答えはすでにそこにあります。
私の意見としては、標準の Linux ツールでは、キャリアを起動してみるまでキャリアをチェックできないということです。その後は、mii-tools
リンク検出は正常に機能し、一貫した回答が得られるようです。
私はrtnetlinkと、検出を扱う他の回答を試しませんでした。変更リンク状態ですが、これはおそらくあなたが望んでいたものではないと思います。