【问题标题】:automatic renaming and numbering of nics using udev使用 udev 自动重命名和编号 nic
【发布时间】:2009-10-29 16:01:39
【问题描述】:

我正在编写一个 udev 规则,以自动重命名和编号具有特定 MAC 地址的 NIC。

生成的规则应该与75-persistent-net-generator.rules 几乎相同(匹配卡的 MAC 地址的前 3 个字节,将其命名为“mycard*”,具体取决于安装了该供应商的卡数量,将重命名规则写入70-persistent-net.rules)。

到目前为止,我已经走了多远:

# udev rules to name rename cards to mycard

ACTION!="add", GOTO="persistent_mycard_generator_end"
SUBSYSTEM!="net", GOTO="persistent_mycard_generator_end"

# ignore the interface if a name has already been set
NAME=="mycard*", GOTO="persistent_mycard_generator_end"

# device name whitelist
KERNEL!="eth*", GOTO="persistent_mycard_generator_end"

# read MAC address
ENV{MATCHADDR}="$attr{address}"

# match interface type
ENV{MATCHIFTYPE}="$attr{type}"

# ignore non mycard MAC addresses
ENV{MATCHADDR}!="00:11:22:*", GOTO="persistent_mycard_generator_end"

# default comment
ENV{COMMENT}=="", ENV{COMMENT}="mycard connected through ($attr{driver})"

#### THIS IS THE PART I DON'T GET ####

# write rule
DRIVERS=="?*", IMPORT{program}="write_net_rules"

# rename interface if needed
ENV{INTERFACE_NEW}=="?*", NAME="mycard*"

#### THIS IS THE END OF THE PART I DON'T GET ####

LABEL="persistent_mycard_generator_end

“我没有得到的部分”应该做的任务是将卡(假设它是 eth3)重命名为 mycard0,或者如果它是系统中具有匹配 MAC 地址 mycard1 的第二张卡,依此类推。

提前致谢, 植物群

【问题讨论】:

    标签: linux networking udev


    【解决方案1】:

    如果您在调用 write_net_rules 之前将 ENV{INTERFACE} 设置为“mycard0”,它将为您找到第一个未使用的 mycardN,为其写出规则,并返回 ENV{INTERFACE_NEW} 中的名称。

    【讨论】:

    • 差不多了。留下一个问题:写的规则有KERNEL==mycard* 而不是KERNEL==eth*,所以它没有被应用。我今天早上写了一个完整的解决方案,我回家后会发布。
    【解决方案2】:

    好的,这是我的解决方案(我已经使用 Debian 5.0 和 Ubuntu 9.04 对其进行了测试,所以我不确定它是否适用于其他发行版的 udev 实现):

    1. 75-persistent-mycard-generator.rules

      ACTION!="add", GOTO="persistent_mycard_generator_end"
      SUBSYSTEM!="net", GOTO="persistent_mycard_generator_end"
      
      # ignore the interface if a name has already been set
      NAME=="?*", GOTO="persistent_mycard_generator_end"
      
      # device name whitelist
      KERNEL!="eth*", GOTO="persistent_mycard_generator_end"
      
      # by default match on the MAC address and interface type
      ENV{MATCHADDR}="$attr{address}"
      ENV{MATCHIFTYPE}="$attr{type}"
      
      # match interface dev_id
      ATTR{dev_id}=="?*", ENV{MATCHDEVID}="$attr{dev_id}"
      
      # by default match on the MAC address and interface type
      ENV{MATCHADDR}="$attr{address}"
      ENV{MATCHIFTYPE}="$attr{type}"
      
      # match interface dev_id
      ATTR{dev_id}=="?*", ENV{MATCHDEVID}="$attr{dev_id}"
      
      # terminate processing if card is not a mycard
      ENV{MATCHADDR}!="AA:BB:CC:*", GOTO="persistent_mycard_generator_end"
      
      # provide nice comments for the generated rules
      SUBSYSTEMS=="pci", ENV{COMMENT}="PCI device $attr{vendor}:$attr{device}"
      SUBSYSTEMS=="pcmcia", ENV{COMMENT}="PCMCIA device $attr{card_id}:$attr{manf_id}"
      SUBSYSTEMS=="usb", ENV{COMMENT}="USB device 0x$attr{idVendor}:0x$attr{idProduct}"
      ENV{COMMENT}=="", ENV{COMMENT}="Unknown $env{SUBSYSTEM} device($env{DEVPATH})"
      ATTRS{driver}=="?*", ENV{COMMENT}="$env{COMMENT} ($attr{driver})"
      
      # add mycard to comment
      ENV{COMMENT}="$env{COMMENT} (mycard)"
      
      # set interface name to mycard0 (initially)
      ENV{INTERFACE}="mycard0"
      
      # generate and write the rule
      DRIVERS=="?*", IMPORT{program}="write_mycard_rules"
      
      # rename the interface if requested
      ENV{INTERFACE_NEW}=="?*",NAME="$env{INTERFACE_NEW}"
      
      LABEL="persistent_mycard_generator_end"
      
    2. write_mycard_rules

      RULES_FILE='/etc/udev/rules.d/70-persistent-net.rules'
      
      . /lib/udev/hotplug.functions
      
      interface_name_taken() {
          local value="$(find_all_rules 'NAME=' $INTERFACE)"
          if [ "$value" ]; then
              return 0
          fi
          return 1
      
      }
      
      find_next_available() {
          raw_find_next_available "$(find_all_rules 'NAME=' "$1")"
      }
      
      write_rule() {
          local match="$1"
          local name="$2"
          local comment="$3"
      
          {
          if [ "$PRINT_HEADER" ]; then
              PRINT_HEADER=
              echo "# This file was automatically generated by the $0"
              echo "# program run by the persistent-mycard-generator.rules rules file."
              echo "#"
              echo "# You can modify it, as long as you keep each rule on a single line."
          fi
      
          echo ""
          [ "$comment" ] && echo "# $comment"
          echo "SUBSYSTEM==\"net\", ACTION==\"add\"$match, NAME=\"$name\""
          } >> $RULES_FILE
      }
      
      if [ -z "$INTERFACE" ]; then
          echo "missing \$INTERFACE" >&2
          exit 1
      fi
      
      # Prevent concurrent processes from modifying the file at the same time.
      lock_rules_file
      
      # Check if the rules file is writeable.
      choose_rules_file
      
      # the DRIVERS key is needed to not match bridges and VLAN sub-interfaces
      if [ "$MATCHADDR" ]; then
          match="$match, DRIVERS==\"?*\", ATTR{address}==\"$MATCHADDR\""
      fi
      
      
      if [ "$MATCHDRV" ]; then
          match="$match, DRIVERS==\"$MATCHDRV\""
      fi
      
      if [ "$MATCHDEVID" ]; then
          match="$match, ATTR{dev_id}==\"$MATCHDEVID\""
      fi
      
      
      if [ "$MATCHID" ]; then
          match="$match, KERNELS==\"$MATCHID\""
      fi        
      
      if [ "$MATCHIFTYPE" ]; then
          match="$match, ATTR{type}==\"$MATCHIFTYPE\""
      fi
      
      
      if [ -z "$match" ]; then
          echo "missing valid match" >&2
          unlock_rules_file
          exit 1
      fi
      
      basename=${INTERFACE%%[0-9]*}
      match="$match, KERNEL==\"eth*\""
      if [ "$INTERFACE_NAME" ]; then
          # external tools may request a custom name
          COMMENT="$COMMENT (custom name provided by external tool)"
      
          if [ "$INTERFACE_NAME" != "$INTERFACE" ]; then
              INTERFACE=$INTERFACE_NAME;
              echo "INTERFACE_NEW=$INTERFACE"
          fi
      else
          # if a rule using the current name already exists, find a new name
          if interface_name_taken; then
              INTERFACE="$basename$(find_next_available "$basename[0-9]*")"
              echo "INTERFACE_NEW=$INTERFACE"
          fi
      fi
      
      write_rule "$match" "$INTERFACE" "$COMMENT"
      unlock_rules_file
      exit 0
      

    最重要的更改是 75-persistent-mycard-generator.rules 中的 ENV{INTERFACE}="mycard0" 设置卡片应获取的名称,以及 write_mycard_rules 中的 match="$match, KERNEL==\"eth*\"" 强制 udev 不使用新名称覆盖使用的内核子系统。

    【讨论】:

      猜你喜欢
      • 2021-04-27
      • 2013-04-11
      • 2015-12-18
      • 2017-09-22
      • 2019-06-19
      • 1970-01-01
      • 1970-01-01
      • 2015-10-22
      • 1970-01-01
      相关资源
      最近更新 更多