Linux fa un ottimo lavoro riconoscendo, caricando ed esponendo automaticamente i dispositivi hardware collegati di innumerevoli fornitori. In effetti, è stata questa caratteristica che, molti anni fa, mi ha convinto a insistere affinché il mio datore di lavoro convertisse l'intera infrastruttura a Linux. Il punto dolente è stato il modo in cui una certa azienda di Redmond non poteva caricare i driver per la scheda di rete integrata sui nostri desktop Compaq mentre Linux lo faceva senza sforzo.
Da allora, la libreria Linux di dispositivi riconosciuti è cresciuta enormemente insieme alla sofisticazione del processo. E la star di quello spettacolo è udev. Il compito di Udev è ascoltare gli eventi dal kernel Linux che coinvolgono modifiche allo stato di un dispositivo. Potrebbe trattarsi di un nuovo dispositivo USB collegato o scollegato, oppure potrebbe essere un mouse wireless offline perché affogato nel caffè versato.
Il compito di Udev è gestire tutti i cambiamenti di stato, ad esempio, assegnando i nomi o le autorizzazioni attraverso i quali si accede ai dispositivi. È possibile accedere a un record di tali modifiche tramite dmesg. Poiché dmesg in genere emette migliaia di voci, è intelligente filtrare i risultati. L'esempio seguente mostra come Linux identifica la mia interfaccia Wi-Fi. Mostra il chipset utilizzato dal mio dispositivo wireless (ath9k ), il nome originale assegnato all'inizio del processo (wlan0 ) e il nome permanente grosso e brutto che sta attualmente utilizzando (wlxec086b1ef0b3 ):
$ dmesg | grep wlan
[ 5.396874] ath9k_htc 1-3:1.0 wlxec086b1ef0b3: renamed from wlan0
In questo articolo, discuterò perché qualcuno potrebbe voler usare un nome del genere. Lungo la strada, esplorerò l'anatomia dei file di configurazione di udev e poi mostrerò come apportare modifiche alle impostazioni di udev, incluso come modificare il modo in cui il sistema nomina i dispositivi. Questo articolo è basato su un modulo del mio nuovo corso, Ottimizzazione del sistema Linux.
Capire il sistema di configurazione udev
Sulle macchine systemd, le operazioni di udev sono gestite da systemd-udevd demone. Puoi controllare lo stato del demone udev nel modo normale systemd usando systemctl status systemd-udevd .
Più risorse Linux
- Comandi Linux cheat sheet
- Cheat sheet sui comandi avanzati di Linux
- Corso online gratuito:Panoramica tecnica RHEL
- Cheat sheet della rete Linux
- Cheat sheet di SELinux
- Cheat sheet dei comandi comuni di Linux
- Cosa sono i container Linux?
- I nostri ultimi articoli su Linux
Tecnicamente, udev funziona cercando di far corrispondere ogni evento di sistema ricevuto con insiemi di regole che si trovano in /lib/udev/rules.d/ o /etc/udev/rules.d/ directory. I file delle regole includono chiavi di corrispondenza e chiavi di assegnazione. L'insieme delle chiavi di corrispondenza disponibili include azione , nome e sottosistema . Ciò significa che se viene rilevato un dispositivo con un nome specificato che fa parte di un sottosistema specifico, gli verrà assegnata una configurazione preimpostata.
Quindi, le coppie chiave/valore "assegnazione" vengono utilizzate per applicare la configurazione desiderata. È possibile, ad esempio, assegnare un nuovo nome al dispositivo, associarlo a un collegamento simbolico del filesystem o limitare l'accesso a un particolare proprietario o gruppo. Ecco un estratto di tale regola dalla mia workstation:
$ cat /lib/udev/rules.d/73-usb-net-by-mac.rules
# Use MAC based names for network interfaces which are directly or indirectly
# on USB and have an universally administered (stable) MAC address (second bit
# is 0). Don't do this when ifnames is disabled via kernel command line or
# customizing/disabling 99-default.link (or previously 80-net-setup-link.rules).
IMPORT{cmdline}="net.ifnames"
ENV{net.ifnames}=="0", GOTO="usb_net_by_mac_end"
ACTION=="add", SUBSYSTEM=="net", SUBSYSTEMS=="usb", NAME=="", \
ATTR{address}=="?[014589cd]:*", \
TEST!="/etc/udev/rules.d/80-net-setup-link.rules", \
TEST!="/etc/systemd/network/99-default.link", \
IMPORT{builtin}="net_id", NAME="$env{ID_NET_NAME_MAC}"
Il aggiungi action dice a udev di attivarsi ogni volta che viene collegato un nuovo dispositivo che fa parte del sottosistema di rete e è un dispositivo USB. Inoltre, se ho capito bene, la regola si applica solo quando il dispositivo ha un indirizzo MAC composto da caratteri all'interno di un determinato intervallo e, inoltre, solo se il 80-net-setup-link.rules e 99-default.link i file non esistono.
Supponendo che tutte queste condizioni siano soddisfatte, l'ID interfaccia verrà modificato in modo che corrisponda all'indirizzo MAC del dispositivo. Ricorda la voce dmesg precedente che mostra come è stato cambiato il nome della mia interfaccia da wlan0 a quel brutto wlxec086b1ef0b3 nome? Questo è stato il risultato dell'esecuzione di questa regola. Come lo so? Perché ec:08:6b:1e:f0:b3 è l'indirizzo MAC del dispositivo (meno i due punti):
$ ifconfig -a
wlxec086b1ef0b3: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
inet 192.168.0.103 netmask 255.255.255.0 broadcast 192.168.0.255
inet6 fe80::7484:3120:c6a3:e3d1 prefixlen 64 scopeid 0x20<link>
ether ec:08:6b:1e:f0:b3 txqueuelen 1000 (Ethernet)
RX packets 682098 bytes 714517869 (714.5 MB)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 472448 bytes 201773965 (201.7 MB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
Questa regola udev esiste per impostazione predefinita in Linux. Non ho dovuto scriverlo da solo. Ma perché preoccuparsi, soprattutto visto quanto sia difficile lavorare con una tale designazione di interfaccia? Dai una seconda occhiata ai commenti inclusi nella regola:
# Use MAC based names for network interfaces which are directly or indirectly
# on USB and have an universally administered (stable) MAC address (second bit
# is 0). Don't do this when ifnames is disabled via kernel command line or
# customizing/disabling 99-default.link (or previously 80-net-setup-link.rules).
Nota come questa regola è progettata specificamente per le interfacce di rete basate su USB. A differenza delle schede di interfaccia di rete (NIC) PCI, è probabile che i dispositivi USB vengano rimossi e sostituiti di tanto in tanto. Ciò significa che non vi è alcuna garanzia che il loro ID non cambierà. Potrebbero essere wlan0 un giorno e wlan3 il prossimo. Per evitare di confondere le applicazioni, assegna ID assoluti ai dispositivi, come quello fornito alla mia interfaccia USB.
Manipolazione delle impostazioni udev
Per il mio prossimo trucco, prenderò l'indirizzo MAC e l'ID corrente per l'interfaccia di rete Ethernet su una macchina virtuale VirtualBox e quindi utilizzerò tali informazioni per creare una nuova regola udev che cambierà l'ID dell'interfaccia. Come mai? Bene, forse ho intenzione di lavorare con il dispositivo dalla riga di comando e dover digitare quel nome lungo può essere fastidioso. Ecco come funzionerà.
Prima di poter modificare il mio ID, dovrò disabilitare la configurazione di rete corrente di Netplan. Ciò costringerà Linux a prestare attenzione alla nuova configurazione. Ecco il mio attuale file di configurazione dell'interfaccia di rete in /etc/netplan/ directory:
$ less /etc/netplan/50-cloud-init.yaml
# This file is generated from information provided by
# the datasource. Changes to it will not persist across an instance.
# To disable cloud-init's network configuration capabilities, write a file
# /etc/cloud/cloud.cfg.d/99-disable-network-config.cfg with the following:
# network: {config: disabled}
network:
ethernets:
enp0s3:
addresses: []
dhcp4: true
version: 2
Il 50-cloud-init.yaml contiene una definizione di interfaccia molto semplice. Ma include anche alcune informazioni importanti sulla disabilitazione della configurazione nei commenti. Per farlo, passerò a /etc/cloud/cloud.cfg.d directory e crea un nuovo file chiamato 99-disable-network-config.cfg e aggiungi la rete:{config:disabled} stringa.
Anche se non ho testato questo metodo su distribuzioni diverse da Ubuntu, dovrebbe funzionare su qualsiasi versione di Linux con systemd (che è quasi tutte). Qualunque cosa tu stia usando, darai una buona occhiata alla scrittura dei file di configurazione udev e al loro test.
Successivamente, ho bisogno di raccogliere alcune informazioni di sistema. Esecuzione dell'ip comando segnala che la mia interfaccia Ethernet si chiama enp0s3 e il suo indirizzo MAC è 08:00:27:1d:28:10 :
$ ip a
2: enp0s3: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc fq_codel state UP group default qlen 1000
link/ether 08:00:27:1d:28:10 brd ff:ff:ff:ff:ff:ff
inet 192.168.0.115/24 brd 192.168.0.255 scope global dynamic enp0s3
Ora creerò un nuovo file chiamato peristent-net.rules in /etc/udev/rules.d directory. Assegnerò al file un nome che inizia con un numero basso, 10:
$ cat /etc/udev/rules.d/10-persistent-network.rules
ACTION=="add", SUBSYSTEM=="net",ATTR{address}=="08:00:27:1d:28:10",NAME="eth3"
Più basso è il numero, prima Linux eseguirà il file e voglio che questo vada presto. Il file contiene il codice che darà il nome eth3 a un dispositivo di rete quando viene aggiunto, purché il suo indirizzo corrisponda a 08:00:27:1d:28:10 , che è l'indirizzo MAC della mia interfaccia.
Dopo aver salvato il file e riavviato la macchina, il mio nuovo nome di interfaccia dovrebbe essere in riproduzione. Potrebbe essere necessario accedere direttamente alla mia macchina virtuale e utilizzare dhclient per far sì che Linux richieda manualmente un indirizzo IP su questa rete appena denominata. L'apertura di sessioni SSH potrebbe essere impossibile senza prima farlo:
$ sudo dhclient eth3
Fatto. Quindi ora puoi forzare udev a fare in modo che il tuo computer faccia riferimento a una scheda di rete nel modo desiderato. Ma soprattutto, hai gli strumenti per capire come gestire qualsiasi dispositivo che si comporta male.