ENVIRONNEMENT UNIX/LINUX
Travaux pratiques : TP5
Professeur : Asmae EL KASSIRI
Filière : GINF 1ère Année
Année Universitaire : 2024-2025
TP PROGRAMMATION SHELL – PARTIE 1
1 Script shell
Un script shell permet d'automatiser une série d'opérations. Il se présente sous la forme d'un fichier contenant
une ou plusieurs commandes qui seront exécutées de manière séquentielle. Tandis que le shell est un interpréteur
de commandes. Il en existe plusieurs versions dont en cite :
- dash : shell par défaut utilisé pour exécuter les scripts sur Ubuntu ;
- bash (Bourne Again SHell) : conçu par le projet GNU, shell linux ; le shell par défaut sur Ubuntu ;
- rbash : un shell restreint basé sur bash. Il existe de nombreuses variantes de bash ;
- csh, tcsh : shells C, créés par Bill Joy de Berkeley ;
- zsh, shell C écrit par Paul Falstad ;
- ksh (ksh88 sur Solaris et equivaut a ksh93 sur les autres UNIX/Linux) shells korn écrits par David Korn, pdksh
(Public Domain Korn Shell ⇔ ksh88) ;
- rc : shell C, lui aussi conçu par le projet GNU ;
- tclsh : shell utilisant Tcl ;
- wish : shell utilisant Tk ;
La commande sh est en fait un lien symbolique vers l'interpréteur de commandes par défaut : /bin/dash.
Soit le fichier suivant
#!/bin/bash
echo "Entrez votre nom "
read nom
echo "vous vous appelez $nom."
Ce fichier qui contient des commandes du shell, écrites dans un ordre précis, est un shell script. On pourra
l'invoquer de la façon suivante : bash NomDuFichierScript
Autre solution, on rend le fichier exécutable, et lors de son invocation, il s'exécutera avec l'interpréteur indiqué
en première ligne
chmod +x LeFichierScript (rend exécutable)
./LeFichierScript
Remarquez les commandes :
- echo pour afficher, qui offre des options (man echo)
- read qui permet d'affecter à une variable (non typée, non déclarée) la saisie de l'utilisateur.
1.1 Les variables locales
Comme tout langage de programmation, le Shell permet de gérer des variables. Il y a :
- Les variables d'environnement sont des variables que l'on peut utiliser dans n'importe quel programme. On
parle aussi parfois de variables globales. Vous pouvez afficher toutes celles que vous avez actuellement en
mémoire avec la commande env
ENVIRONNEMENT UNIX/LINUX |Asmae EL KASSIRI 1
o lorsqu’on tape une commande, le shell va consulter la variable $PATH pour identifier les emplacements
où il doit chercher le code de la commande.
o Pour voir son contenu : echo $PATH
o Pour en modifier le contenu :
export PATH= nouveau contenu
exemple : export PATH=$PATH:$HOME/scripts. C’est intéressant si on souhaite mettre tous nos
scripts dans le répertoire scripts de notre dossier personnel, ça nous permettra par la suite
d’exécuter le script en tant que commande. Pour rendre cette modification permanente vous devez
ajouter la commande export PATH=… au ficher caché .bashrc de votre répertoire personnel et/ou
du dossier root.
- Les variables spéciales du shell : en général, créées par le programme shell lui-même, elles sont en lecture
seule. Par exemple $0, $# ou $?
- Les variables de l'utilisateur, c'est à dire le programmeur, dites Variables locales. Une variable n'a pas de type,
et n'est pas déclarée. On s'en sert directement, en général par une affectation. Une variable locale définie
pour le script A ne sera pas utilisable dans le script B.
o Par exemple : x=5 nom="Sylvain Cherrier"
o ATTENTION : var est la variable, et $var est le contenu de la variable. Parfois, on utilisera ${var} pour
indiquer son nom (notamment dans les substitutions ou les concaténations)
o Problème du non déclaré et non typé : Possibilité d'erreur très importante (mauvais nom sans alerte,
confusion) Pb du type : que vaut x=3 puis y=$x+2 La solution : y=$(($x+2))
1.2 Les arguments
Comme toutes les commandes, vos scripts bash peuvent eux aussi accepter des paramètres. Ainsi, on pourrait
appeler notre script comme ceci :
./[Link] param1 param2 param3
En effet, des variables sont automatiquement créées :
- $# : contient le nombre de paramètres ;
- $* : liste tous les arguments ;
- $?: contient le code de retour de la dernière commande exécutée ;
- $0 : contient le nom du script exécuté (ici ./[Link]) ;
- $1 : contient le premier paramètre ;
- $2 : contient le second paramètre ;
- $9 : contient le 9e paramètre.
On peut « décaler » les paramètres dans les variables $1, $2, etc. à l’aide de la commande shift.
1.3 Les quottes
Il est possible d'utiliser des quottes pour délimiter un paramètre contenant des espaces. Il existe trois types de
quottes :
- les apostrophes ' ' (simples quottes):
o exemple
ENVIRONNEMENT UNIX/LINUX |Asmae EL KASSIRI 2
message='Bonjour tout le monde'
echo 'Le message est : $message'
Le message est : $message
o Avec de simples quottes, la variable n'est pas analysée et le $ est affiché tel quel.
- les guillemets " " (doubles quottes):
o exemple:
echo "Le message est : $message"
Le message est : Bonjour tout le monde
o En fait, les doubles quottes demandent à bash d'analyser le contenu du message. S'il trouve des symboles
spéciaux (comme des variables), il les interprète.
- Les accents graves ` ` (back quottes), qui s'insèrent avec Alt Gr + 7 sur un clavier AZERTY français:
o exemple:
message=`pwd`
echo "Vous êtes dans le dossier $message"
Vous êtes dans le dossier /home/mateo21/bin
o La commande pwd a été exécutée et son contenu inséré dans la variable message
o Les accents graves permettent d’interpréter un sous shell, c’est la commande backquotée, et de
récupérer son résultat, qui devient alors l'argument de la commande en cours
1.4 Les structures de contrôle
1.4.1 La structure if
Syntaxe :
if commande1
then ........
elif …
else …
fi
If permet de récupérer la valeur de retour de commande1 (pas son stdout, mais sa valeur de retour) afin de
prendre une décision... Ainsi, il est possible de tester le bon fonctionnement d'une majorité de commandes.
Exemple:
if ps -u asmae|grep gedit
then
echo "l’editeur gedit est lancé par asmae"
else
echo "l’editeur gedit n’est pas lancé par asmae"
fi
1.4.2 La commande test
La commande test existe sous tous les Unix, elle permet de faire un test et de renvoyer 0 si tout s'est bien passé
ou 1 en cas d'erreur. On peut la raccourcir par un crochet. On utilise pour tester trois catégories d’opérateurs :
- Opérateurs de test :
ENVIRONNEMENT UNIX/LINUX |Asmae EL KASSIRI 3
Syntaxe
Fonction réalisée
-e fichier renvoie 0 si fichier/répertoire existe.
-d fichier renvoie 0 si fichier existe et est un répertoire.
-f fichier renvoie 0 si fichier existe et est un fichier 'normal'.
-w fichier renvoie 0 si fichier existe et est en écriture.
-x fichier renvoie 0 si fichier existe et est exécutable.
f1 -nt f2 renvoie 0 si f1 est plus récent que f2.
f1 -ot f2 renvoie 0 si f1 est plus vieux que f2.
- Opérateurs de comparaison numériques :
Syntaxe
Fonction réalisée
$A -lt 5 renvoie 0 si $A est strictement inférieur à 5
$A -le 5 renvoie 0 si $A est inférieur ou égal à 5
$A -gt 5 renvoie 0 si $A est strictement supérieur à 5
$A -ge 5 renvoie 0 si $A est supérieur ou égal à 5
$A -eq 5 renvoie 0 si $A est égal à 5
$A -ne 5 renvoie 0 si $A est différent de 5
- Opérateurs de comparaison logiques :
o le et logique : -a
o le ou logique : -o
o le non logique : !
Exemples :
- test expr1 -lt expr2 <= => [expr1 -lt expr2]
- [-f /etc/passwd]
Exemple avec if :
if [ -e "$file" ]
then
echo "Le fichier existe!"
else
echo "Le fichier n'existe pas, du moins n'est pas dans le répertoire d'exécution du script"
fi
1.4.3 La structure case
Syntaxe :
case variable in
modèle [ | modèle] ...) instructions;;
modèle [ | modèle] ...) instructions;;
...
esac
Exemple
#!/bin/sh
echo -n "Etes-vous fatigué ? "
ENVIRONNEMENT UNIX/LINUX |Asmae EL KASSIRI 4
read on
case "$on" in
oui | o | O | Oui | OUI ) echo "Allez faire du café !";;
non | n | N | Non | NON ) echo "Programmez !";;
* ) echo "Ah bon ?";;
esac
exit 0
1.5 Les boucles
1.5.1 while
while programme
do
instructions...
done
On boucle tant que le programme renvoie vrai.
Exemple qui permet de parcourir les lignes d’un fichier :
while read line
do
echo -e "$line\n"
done < [Link]
un autre exemple de lecture d’un fichier en considérant le séparateur ‘ ;’ comme séparateur de mots:
while IFS=';' read champ1 champ2 toutLeReste
do
line="$champ1 $champ2 $toutLeReste"
echo "$line"
done < [Link]
1.5.2 Until
until programme
do
instructions...
done
Là on boucle jusqu’à ce que le programme renvoie vrai
1.5.3 Saut : break et continue
Break : cette commande est utilisée pour arrêter l'exécution d'une boucle prématurément dès qu'une certaine
condition est vérifiée.
continue: cette commande est utilisée pour refaire un tour de boucle en repartant du do.
until programme
do
instructions...
if cond1
then
ENVIRONNEMENT UNIX/LINUX |Asmae EL KASSIRI 5
continue
else
if cond2
break
fi
fi
done
1.5.4 for
Le for du shell est simpliste, il sert à se prendre les valeurs d'une liste. Cette liste est souvent générée par une
commande. Or, on conçoit souvent le for comme étant paramétré par une borne de début et de fin, avec un pas.
Souvent on utilise la substitution du shell (*, ? et autres caractères) qui nous renvoie la liste des fichiers
correspondant
for i in /etc/*
do
if [ -f $i ]
then
echo "$i is a file"
elif [ -d $i ]
echo "$i is a directory"
fi
done
Ou encore, on récupère le résultat d'un sous shell
for i in ` who`
do
...
done
2 Exercices
2.1 Exercice 1
Créez un répertoire scripts, dans lequel vous rangerez vos scripts
1. Créez un script [Link] qui vous demande votre nom et votre prénom, et vous affiche : 'vous êtes prénom
nom'
2. Créez un script [Link] qui vous demande votre nom et prénom (en une seule variable), puis votre mois
de naissance et enfin votre année de naissance. Il affiche ensuite "Nom : xxxxx, né(e) en xx xxxx" suivi du
calendrier de ce mois
3. Écrire un script non interactif [Link] qui crée un fichier /tmp/bilan, qui contient la date, le nom de la
machine (uname -a), la liste des utilisateurs connectés, et la liste des processus. Vérifiez le bon
fonctionnement de votre script.
4. Écrire un script non interactif [Link] qui affiche :
Nb users connectés : xx
Nb de processus : xxx
ENVIRONNEMENT UNIX/LINUX |Asmae EL KASSIRI 6
5. Ecrire un script [Link] qui vous demande un nom d'utilisateur, puis affiche les processus qui lui
appartiennent
6. Ecrire un script [Link] qui crée dans /tmp un fichier qui contient le lastlog du jour.
La commande lastlog permet d’afficher les dernières connexions :
- -u : permet de spécifier un utilisateur pour lequel on souhaite afficher les connexions
- -b day : permet d’afficher les connexions qui datent avant day
- -t day : permet d’afficher les connexions qui datent aptès day
7. Améliorez le script précédent en faisant en sorte que le nom du fichier soit SAV-AA-MM-JJ (SAV suivi de
la date du jour, calculée automatiquement)
2.2 Exercice 2
1. Écrire un script qui liste son nom et ses arguments (grâce à echo), et affiche le total d'arguments
2. Écrire un script qui rend exécutable le fichier dont le nom est passé en argument (pratique pour les scripts,
justement)
3. Améliorez le script précédent, afin qu'il vérifie si le fichier existe bien. Il doit aussi indiquer si celui-ci était
déjà exécutable.
4. Améliorez encore le programme précédent afin qu'il vérifie si l'argument qu'on lui passe est bien un script
shell.
5. Écrire une commande qui vérifie si le processus qu'on lui donne en argument est présent en mémoire.
Testez ce programme.
6. Ecrire une commande qui vérifie si le user dont on lui passe le nom en argument est bien connecté, et
affiche aussi son nom complet (dans /etc/passwd, 5ème champ)
2.3 Exercice 3
1. Ecrire un programme qui ping toutes les machines de [Link] à [Link].
2. Écrivez un programme qui prend en paramètre le nom d’un répertoire. Il vérifie d’abord si le répertoire
existe, sinon il doit demander un autre nom en boucle jusqu’à avoir un répertoire valide. Le programme
doit ensuite parcourir la liste des entrées de ce répertoire dont le nom se termine par '.c' et applique à
chacune la commande wc -l s’il s’agit d’un fichier.
3. Écrivez un programme qui parcourt les lignes du ficher /etc/passwd et qui affiche :
root si la ligne concerne root
le shell par défaut est sh si la ligne se termine par /bin/sh
le shell par défaut est bash si la ligne se termine par /bin/bash
compte verrouillé si la ligne se termine par /bin/nologin
accès au shell interdite si la ligne se termine par /bin/false
inconu dans tous les autres cas
4. Créer un script shell réalisant la création d'un répertoire "Exo3" contenant 10 fichiers nommés "Un" à
"Dix". Chaque fichier contient une seule ligne:
"Un" contient "Première ligne"
"Deux" contient "Deuxième ligne"
...
"Dix" contient "Dixième ligne"
ENVIRONNEMENT UNIX/LINUX |Asmae EL KASSIRI 7
Vérifier que le répertoire à créer n'existe pas pour qu’il ne serait pas recréé.
5. Ecrire un script qui prend deux arguments, et teste si les deux arguments sont des entiers, si oui il doit en
calculer la somme, la moyenne et la multiplication, sinon il doit afficher un message d’information du
problème.
Pensez à utiliser les expressions régulières avec la commande test.
ENVIRONNEMENT UNIX/LINUX |Asmae EL KASSIRI 8