Как определить логический тип сетевого устройства Linux

Вопрос или проблема

Под логическим я имею в виду все легальные в команде
ip link, как в, например:

ip link add link dum0 name dum0.200 type vlan protocol 802.1Q id 200

где логический тип будет «vlan». Все допустимые типы, чтобы процитировать страницу man:

vlan | veth | vcan | dummy | ifb | macvlan | macvtap | can | bridge | ipoib | ip6tnl | ipip | sit | vxlan | gre | gretap | ip6gre | ip6gretap | vti

Обратите внимание, что это явно не физический тип устройства (например, ethernet, wifi, ppp и т.д.), как спрашивалось в вопросе, который содержит жемчужину ссылки на физический тип, который заставил меня протестировать это:

find /sys/class/net ! -type d | xargs --max-args=1 realpath | 
  while read d; do 
    b=$(basename $d) ; n=$(find $d -name type) ; echo -n $b' ' ; cat $n;
 done
dum0.200 1
dum0.201 1
dum1.300 1
dum1.301 1
dummy0 1
ens36 1
ens33 1
lo 772
dum0 1
dum1 1
wlan0 1

Но, похоже, что находит как dummy, так и vlan, и wlan устройства типа ARPHRD_ETHER.

Кто-нибудь знает больше? Спасибо заранее.

====

Пересматривая это в 2023 году.

Это из системы с двумя настоящими ethernet-интерфейсами, одним wifi, установленным docker, но неактивным, libvirt с двумя сетями и двумя виртуальными машинами и соединением wireguard. jq из stedolan.github.io/jq, обычно устанавливается с помощью хорошего менеджера пакетов.

$ ip -details -j l | jq -r '.[]|"\(.ifname), \(.link_type), \(.linkinfo.info_data.type), \(.linkinfo.info_kind), \(.linkinfo.info_slave_kind)"' | column -t -s ','
lo                loopback   null   null        null
enp43s0           ether      null   null        null
enx00e04c680049   ether      null   null        null
wlp0s20f3         ether      null   null        null
virbr2            ether      null   bridge      null
virbr1            ether      null   bridge      null
docker0           ether      null   bridge      null
vnet0             ether      tap    tun         bridge
vnet1             ether      tap    tun         bridge
vnet2             ether      tap    tun         bridge
vnet3             ether      tap    tun         bridge
wg0               none       null   wireguard   null
$

Проще решение:

ip -details link show

Для виртуальных устройств тип устройства отображается на третьей строке.

Есть способ перебрать все доступные типы и показать все интерфейсы по типу (используя ip link show type <type>). Из этого можно собрать интерфейсы для всех типов и затем обработать для интерфейса, о котором хотите узнать. Это не элегантно, но работает:

Используя bash:

#!/bin/bash

# Аргументы: $1: Интерфейс ('grep'-регулярное выражение).

# Статический список типов (из `ip link help`). ПРИМЕЧАНИЕ: на моей машине не все типы там перечислены, например, тип `tun`. И список типов может со временем изменяться. Поэтому не полагайтесь в конечном итоге на этот список здесь!:
TYPES=(bareudp bond bond_slave bridge can dummy erspan geneve gre gretap hsr ifb ip6erspan ip6gre ip6gretap ip6tnl ipip ipoib ipvlan ipvtap lowpan macsec macvlan macvtap netdevsim nlmon rmnet sit tap tun vcan veth vlan vrf vti vxcan vxlan xfrm)

iface="$1"

for type in "${TYPES[@]}"; do
  ip link show type "${type}" | grep -E '^[0-9]+:' | cut -d ':' -f 2 | sed 's|^[[:space:]]*||' | while read _if; do
    echo "${_if}:${type}"
  done | grep "^${iface}"
done

Сохраните это в файл, сделайте его исполняемым и запустите с вашим интерфейсом, о котором хотите узнать, в качестве аргумента.

Для примера dum0.200, который является типом vlan через соединение eth0 (созданный с помощью ip link add link eth0 name dum0.200 type vlan protocol 802.1Q id 200), вывод будет dum0.200@eth0:vlan, указывая, что он типа vlan. Обратите внимание, что @eth0 происходит из ip link show и может быть удалено, если это необходимо.

Поскольку аргумент к этому скрипту интерпретируется как grep-регулярное выражение, указание ничего приведет к тому, что будут перечислены все, что выводится ip link show type <type>, или указание только префикса перечислит некоторые и т.д.

Примечание: (добавлено 2021-05-12): «Обычные» ethernet-устройства и также устройство обратной связи, похоже, не имеют никакого типа. Поэтому скрипт не будет их перечислять. Если необходимо также перечислить устройства без типа, его необходимо расширить или переписать.

Это из системы с двумя настоящими ethernet-интерфейсами, одним wifi, установленным docker, но неактивным, libvirt с двумя сетями и двумя виртуальными машинами и соединением wireguard. jq из stedolan.github.io/jq, обычно устанавливается с помощью хорошего менеджера пакетов.

$ ip -details -j l | jq -r '.[]|"\(.ifname), \(.link_type), \(.linkinfo.info_data.type), \(.linkinfo.info_kind), \(.linkinfo.info_slave_kind)"' | column -t -s ','
lo                loopback   null   null        null
enp43s0           ether      null   null        null
enx00e04c680049   ether      null   null        null
wlp0s20f3         ether      null   null        null
virbr2            ether      null   bridge      null
virbr1            ether      null   bridge      null
docker0           ether      null   bridge      null
vnet0             ether      tap    tun         bridge
vnet1             ether      tap    tun         bridge
vnet2             ether      tap    tun         bridge
vnet3             ether      tap    tun         bridge
wg0               none       null   wireguard   null
$

Ответ или решение

Определение логического типа сетевого устройства в Linux

Определение логического типа сетевого устройства в Linux — это важная задача для системных администраторов и сетевых инженеров. Логический тип устройства включает такие технологии, как vlan, bridge, dummy и другие, которые могут не совпадать с физическим типом устройства (например, Ethernet или Wi-Fi). В этом руководстве мы обсудим несколько эффективных способов определения логического типа сетевого устройства с использованием командной строки Linux.

Подходы к определению логического типа сетевого устройства

  1. Использование команды ip link:

    Наиболее распространенным способом является использование команды ip link, которая позволяет получить отображение всех сетевых интерфейсов в системе. Вы можете использовать следующую команду для получения подробной информации о каждом интерфейсе:

    ip -details link show

    При выполнении этой команды, логический тип сетевого устройства будет отображен на третьей строке (если применимо). Для виртуальных интерфейсов это особенно полезно.

  2. Использование JSON-вывода с jq:

    Если вам нужен более структурированный вывод, вы можете сделать следующее:

    ip -details -j link | jq -r '.[]|"\(.ifname), \(.link_type), \(.linkinfo.info_data.type), \(.linkinfo.info_kind), \(.linkinfo.info_slave_kind)"' | column -t -s ','

    Этот подход позволяет получить информацию о каждом интерфейсе в читаемом виде и может помочь в быстром анализе.

  3. Скрипт для определения типа устройства:

    Если у вас есть конкретное устройство, для которого вы хотите узнать логический тип, можно использовать следующий bash-скрипт. Этот скрипт перебирает известные типы устройств и отображает интерфейсы, соответствующие каждому типу:

    #!/bin/bash
    
    # Аргументы: $1: Интерфейс ('grep'-регулярное выражение).
    TYPES=(vlan bridge dummy veth ...)  # добавьте остальные типы по мере необходимости
    
    iface="$1"
    
    for type in "${TYPES[@]}"; do
     ip link show type "${type}" | grep -E '^[0-9]+:' | cut -d ':' -f 2 | sed 's|^[[:space:]]*||' | while read _if; do
       echo "${_if}:${type}"
     done | grep "^${iface}"
    done

    Сохраните этот скрипт в файл, сделайте его исполняемым и передайте имя интерфейса в качестве аргумента, чтобы получить вывод, указывающий логический тип устройства.

  4. Проверка файловой системы /sys/class/net:

    Еще один способ определить тип устройства — это проверить виртуальные файлы в каталоге /sys/class/net. Например, можно использовать следующую команду:

    find /sys/class/net ! -type d | xargs --max-args=1 realpath | while read d; do b=$(basename $d) ; n=$(find $d -name type) ; echo -n $b' ' ; cat $n; done

    Этот подход также дает информацию о физическом типе устройств, но может не быть полностью надежным для определения логического типа.

Заключение

Определение логического типа сетевого устройства в Linux можно выполнить различными способами в зависимости от ваших потребностей. Используя команды ip link, структурированный вывод с jq, или кастомные скрипты, вы можете эффективно получать информацию о типах сетевых интерфейсов. Важно помнить, что для успешного администрирования сетевой инфраструктуры необходимо понимать различия между физическими и логическими типами устройств, что позволит вам более эффективно управлять соединениями и конфигурациями сети.

Оцените материал
Добавить комментарий

Капча загружается...