Savoir, par un script non interactif, si une interface est wireless
Le
Francois Lafont

Bonjour à tous,
En fait, j'ai 2 questions.
1. Je me demandais si on pouvait savoir, par un script non interactif
et de manière _fiable_ (ou de la manière la plus fiable possible), si
une interface (au sens interface réseau du noyau) correspond à une
carte réseau Wifi ou non (et dans ce cas je considère que c'est une
carte réseau filaire). Le script prendrait en argument le nom d'une
des interfaces retournées par la commande "ip link" (par exemple) :
is_wireless.sh "eth1" && echo OK
is_wireless.sh "wlan0" && echo OK
Là, ce serait en shell mais n'importe quel langage de script mon
conviendrait (bon j'avoue j'aurais une préférence pour le shell mais
bon ;)).
Évidemment, si vous me dites qu'il suffit juste de tester que le nom
de l'interface commence par « wlan » et que c'est un test 100% fiable
alors Ok. Mais je constate qu'on peut tomber sur des noms bizarres
parfois. Par exemple, récemment suite à une installation « out-of-the-box »
d'une Ubuntu Xenial, je me suis retrouvé avec une interface nommée
enp0s3 au lieu du bon vieux eth0. Alors ok, là c'était de la carte
réseau filaire Ethernet mais du coup, le nom de l'interface est-il
vraiment une information fiable ?
J'aimerais que ce script soit compatible Debian Jessie et Ubuntu
Xenial si possible.
2. Par ailleurs, savez-vous s'il y a une option qui m'aurait échappée
pour parser facilement (typiquement parser dans un script) la sortie
des commandes « ip ». Par exemple, avec la commande « ip addr » j'ai
la liste de mes interfaces avec leur IP etc. Si je veux récupérer l'IP
de l'interface eth0 dans la sortie de « ip addr », évidemment je peux
le faire à coup de grep, awk etc. mais je trouve cela fragile. Par
exemple, il serait plus robuste de pouvoir parser une sortie json ou
je ne sais quoi. Je suis surpris de ne pas avoir trouvé d'option pour
ça. Mais j'ai peut-être mal cherché.
Merci d'avance pour votre aide.
--
François Lafont
En fait, j'ai 2 questions.
1. Je me demandais si on pouvait savoir, par un script non interactif
et de manière _fiable_ (ou de la manière la plus fiable possible), si
une interface (au sens interface réseau du noyau) correspond à une
carte réseau Wifi ou non (et dans ce cas je considère que c'est une
carte réseau filaire). Le script prendrait en argument le nom d'une
des interfaces retournées par la commande "ip link" (par exemple) :
is_wireless.sh "eth1" && echo OK
is_wireless.sh "wlan0" && echo OK
Là, ce serait en shell mais n'importe quel langage de script mon
conviendrait (bon j'avoue j'aurais une préférence pour le shell mais
bon ;)).
Évidemment, si vous me dites qu'il suffit juste de tester que le nom
de l'interface commence par « wlan » et que c'est un test 100% fiable
alors Ok. Mais je constate qu'on peut tomber sur des noms bizarres
parfois. Par exemple, récemment suite à une installation « out-of-the-box »
d'une Ubuntu Xenial, je me suis retrouvé avec une interface nommée
enp0s3 au lieu du bon vieux eth0. Alors ok, là c'était de la carte
réseau filaire Ethernet mais du coup, le nom de l'interface est-il
vraiment une information fiable ?
J'aimerais que ce script soit compatible Debian Jessie et Ubuntu
Xenial si possible.
2. Par ailleurs, savez-vous s'il y a une option qui m'aurait échappée
pour parser facilement (typiquement parser dans un script) la sortie
des commandes « ip ». Par exemple, avec la commande « ip addr » j'ai
la liste de mes interfaces avec leur IP etc. Si je veux récupérer l'IP
de l'interface eth0 dans la sortie de « ip addr », évidemment je peux
le faire à coup de grep, awk etc. mais je trouve cela fragile. Par
exemple, il serait plus robuste de pouvoir parser une sortie json ou
je ne sais quoi. Je suis surpris de ne pas avoir trouvé d'option pour
ça. Mais j'ai peut-être mal cherché.
Merci d'avance pour votre aide.
--
François Lafont
$ iwconfig lo 2>&1 | grep -q wireless
$ echo $?
0
$ iwconfig wlan0 2>&1 | grep -q wireless
$ echo $?
1
Parser:
Certaines options de substitution d'expressions régulières de sed peuvent
rendre des services occasionnels.
On peut tout faire avec Lex & Yacc, mais il y a un investissement initial
non négligeable.
http://dinosaur.compilertools.net/
Sinon avec des bouts de manipulations de chaines de caractères en python,
tout est possible et assez facile.
$ iwconfig eth0 1> /dev/null 2>&1
Le code retour $? est 0 si l'interface est un wlan, 161 s'il n'en est
pas, 237 si l'interface n'existe pas.
Sous Debian Stretch
grep <interface> /proc/net/wireless
fait le truc.
--
JJ R.
Ok, merci pour l'idée de la commande iwconfig. L'utilisation de l'exit code
comme tu le proposes dans ton message suivant est parfaite. ;)
Ok, pas de souci avec tout ça. Mais donc tu me confirmes que je ne suis pas
passé à côté d'une option --json ou je ne sais quoi au niveau de la commande
« ip » ? Car il n'est pas rare que les commandes proposent une mise en forme
de la sortie pour faciliter la récupération de données dans un script et je
suis surpris que ce ne soit pas le cas pour « ip ».
--
François Lafont
J'ai aussi de fichier sous ma Debian Wheezy. Mais en revanche, il semble que l'interface doit être up et configurée pour qu'elle y apparaisse. Merci pour l'info.
À+
--
François Lafont
Le 08/05/2016 à 02:53, Francois Lafont a écrit dans le message
Peut-être en regardant la présence de /sys/class/net/<ifn>/phy80211 ?
for ifname in /sys/class/net/*; do
printf '%10s is ' "${ifname##*/}"
test -L "$ifname/phy80211" || printf 'not '
printf 'IEEE 802.11n'
done
Ce lien devrait t'intéresser :
Quelle est la finalité ?
--
Benoit Izac
On 09/05/2016 22:36, Benoit Izac wrote:
Ah merci Benoît. Ce que j'aime bien avec cette manière, c'est que ça ne
nécessite a priori aucun paquet d'installé (on peut peut-être supposer
que ça va marcher sur tous les Linux).
Oui et non. ;)
En fait, justement, j'avais lu ce lien avant et justement ça me saoule
un peu de me retrouver avec des noms d'interfaces du genre enp0s3 à la
place d'un bon vieux eth0. Du coup, je cherchais à renommer les interfaces
(ça, ça va je sais faire) mais je voulais avoir un moyen fiable de savoir
si une interface correspond à une carte wifi (auquel cas, je choisis un
nom en wlan<i>) ou non (auquel cas, dans mon écosystème à moi, ça veut
dire que c'est une carte réseau filaire avec comme nom eth<i>).
Et bien il n'est pas rare que je doive récupérer par script par exemple
l'adresse MAC ou l'adresse IP d'une interface. Et je trouve que faire
cela avec la commande ip n'est pas très aisé. On y arrive avec du grep,
du awk etc. mais je trouve cela fragile, d'où ma question.
--
François Lafont
Je n'ai peut-être pas bien répondu à ta question en fait.
Le « contexte » c'est que, dans mon temps de loisir, j'essaye de participer
au projet SambaEdu (https://github.com/SambaEdu) qui est une sorte de solution
pour établissement scolaire de serveur "contrôleur de domaine Windows" mais
via la technologie Samba (et pas Active Directory bien sûr).
Plus précisément, on essaye de mettre en place un système de serveur PXE pour
que les utilisateurs puissent installer des machines "clientes" Ubuntu ou Debian
et les intégrer au domaine Samba, le tout 100% automatiquement. Et typiquement,
après l'installation du système de base sous un nom d'hôte générique ("poste"),
la machine est censée rechercher son adresse MAC dans l'annuaire du serveur Samba
(consultable en lecture via le réseau) et récupérer son nom d'hôte associé à
cette adresse MAC. Donc tu imagines que dans l'histoire il y a du script shell
dans lequel par exemple je dois récupérer l'adresse MAC de l'unique interface
réseau qui a été configurée via le DHCP du réseau local. Etc. Voilà le genre
de tambouille. ;)
--
François Lafont
Le 10/05/2016 à 02:05, Francois Lafont a écrit dans le message
Si c'est juste l'adresse MAC :
MAC=$(cat /sys/class/net/<ifname>/address)
Tu peux regarder également /sys/class/net/<ifname>/operstate pour savoir
si l'interface est up ou down ; voir
pour d'autres informations disponibles.
Pour l'IP, il faut bricoler :
Soit, par exemple, si tu n'as pas besoin de la longueur du préfixe :
ip addr | awk '/scope global/{split($2, a, "/"); print a[1]}'
--
Benoit Izac
On 10/05/2016 18:51, Benoit Izac wrote:
Ok merci. Ce sont des manières de faire que je ne connaissais pas.
Personnellement je faisais ça :
mac=$(ip link show eth0 | awk '/link/ether/ {print $2}')
Mais du coup, est-ce que c'est mieux de passer par l'arborescence /sys/ ?
Par exemple, est-ce que je n'ai pas intérêt à rester sur du « haut » niveau
avec la commande "ip" plutôt que d'utiliser l'arbo /sys/ qui, peut-être,
pourra changer avec l'évolution du noyau Linux ? Je ne dis pas que c'est
le cas bien sûr, je me pose la question. Après la sortie de "ip" sera-t-elle
plus stable que l'arbo /sys/ pas sûr non plus...
Ok, au passage je découvre la fonction split() de awk.
Comme tu dis, faut bricoler un peu. Une option --json (ou n'importe quoi qui
puisse se parser facilement je me moque que ce soit du json en particulier)
aurait été commode je trouve. Et je constate que de telle option sont quand
même souvent présentes mais pas là.
--
François Lafont