Travaux Pratiques n°3

Instructions

Ces travaux pratiques sont à effectuer seul et un compte-rendu (réponses aux questions plus tout commentaire supplémentaire que vous jugerez utile) est à envoyer à serpaggi@emse.fr dès la fin de la séance de TP.

Pour faciliter la réception et le traitement, le message devra avoir un sujet (Sujet ou Objet selon le logiciel utilisé) formaté comme suit :
[MSGL Shell] TP3 Prénom Nom.

Écriture de scripts

Chacun des script que vous devez écrire doivent être le plus complet possible. Il devra donc tester si tous les arguments nécessaires sont présents et s'ils sont du bon type et/ou accessibles. Des messages d'erreurs pertinents devront être affichés si nécessaire.

Si le script attend un format particulier pour ses arguments, un message présentant ce format et respectant la syntaxe que l'on trouve en général dans les pages de manuel, devra être affiché en cas d'erreur à ce niveau.

Affichage des arguments

Écrire un script, aff_args, qui affiche les arguments qui lui sont passés sur la ligne de commande.

Exemple :

#> ./aff_args Hello World!
Hello
World!

Il existe au moins deux façons de faire cela, une utilisant une boucle for et l'autre utilisant la commande interne shift. Vous pouvez proposer les deux solutions et discuter des avantages de l'une et de l'autre.

Modifiez ce script pour qu'il ajoute devant chaque argument, sa position sur la ligne de commande.

Exemple :

#> ./aff_args Hello World!
1: Hello
2: World!

Modifiez votre script pour que l'affichage des arguments se fasse dans une fonction et non plus dans le script lui-même. Quel avantage cela peut-il avoir ?

Copie multiple

La commande cp permet de faire la copie d'un ou plusieurs fichiers dans un répertoire, mais ne permet pas de faire la copie d'un fichier dans plusieurs répertoires.

Nous vous demandons d'écrire un script, qui aura pour nom mcp, et qui réalisara cette tâche.

Sa syntaxe générale devra être de la forme :

Syntaxe

mcp FIC REP [REP]...

Le script devra être robuste et pour cela, il devra s'assurer de l'existence du fichier source et des répertoires destination.

Si au moins un des éléments n'est pas présent ou est du mauvais type, alors le script doit échouer.

En fonction de ce qu'il a été capable de faire ou ne pas faire, il devra retourner :

Taille d'un répertoire

Écrivez un script nommé dsz qui va calculer et afficher la somme de la taille de tous les fichiers présents dans les répertoires qui lui sont passés en paramètres.

S'il n'y a pas de paramètre, le script travaillera sur le répertoire courant.

Si l'option -r est donnée comme premier paramètre le script va ajouter au résultat la taille des fichiers dans les sous-répertoires de chaque paramètre.

Sa syntaxe générale devra être de la forme :

Syntaxe

dsz [-r] [REP]...

Vous pourriez avoir besoin de la commande expr(1) qui permet de faire la somme de deux termes.

Pour connaître la taille d'un fichier, un moyen est d'utiliser ls, cepedant nous avons vu qu'il n'est pas aisé de traiter sa sortie en format long avec cut. Pour vous aider, vous pourrez faire passer la sortie de ls au travers de la commande sed avec le traitement suivant :

#> ls -l | sed -e 's/ \{1,\}/ /g'

Cela signifie que pour chaque ligne de la sortie de ls, on va remplacer toute séquence de plus de un espace par un unique espace.

Attention tout de même, il se peut qu'à ce moment là, le ls soit un alias où même une fonction et produise un affichage qui différent de l'idée que vous vous en faites et que vous ne pourrez peut être pas traiter correctement avec vos filtres. Il serait donc prudent de préciser que c'est bien l'exécutable /bin/ls (par exemple) que vous voulez utilser.

Création de répertoires

Nous nous proposons d'écrire un script hdir, qui puisse créer automatiquement une hiérarchie de répertoires en une seule commande.

Ce script doit prendre en paramètre une liste de répertoires (1 à n répertoires) séparés par un / (slash) .

Sa syntaxe générale devra être de la forme :

Syntaxe

hdir REP[/REP]...

Si les p (p<n) premiers répertoires existent déjà, le script devra commencer la création de la hiérarchie au (p+1)ieme sans emmètre de message d'erreur.

La création de chaque répertoire sera faite par la commande prévue à cet effet : mkdir.

Le script retournera :

Vous pouvez, à ce niveau, donner plus de détails dans les codes d'erreur, si vous le jugez nécessaire.

Exemple d'utilisation :

#> hdir rep1/rep2/rep3
#> ls -R rep1
rep2/

rep1/rep2:
rep3/

rep1/rep2/rep3:

Version récursive de grep

La version de grep(1) que vous utilisez sur votre système n'est pas capable de faire ses recherche de manière récursive dans les éventuels sous-répertoires qu'elle rencontre.

Nous vous proposons d'écrire un script rgrep qui puisse agir comme grep mais avec cette fonctionnalité en plus.

Il y a au moins trois façons différentes d'écrire ce script. Deux en utilisant la commande find et une troisième, plus générique, en faisant un parcours récursif des répertoires et en utilisant la commande grep sur chaque fichier de ces sous-répertoires.

Cette dernière version, bien que plus difficile à coder permet de rendre récursive n'importe quelle commande qui ne l'est pas.

Vous risquez de rencontrer des difficultés pour traiter tous les cas possible, surtout en ce qui concerne le nom des fichiers/répertoires rencontrés mais également pour ce qui concerne la taille de la liste des sous-répertoires à traiter.

Notre script rgrep prendra deux types d'arguments :

  1. une liste d'options qui correspondent à certaines options de grep (i, l et n) ;
  2. une expression régulière correspondant à ce qu'il faut rechercher.

Le script aura toujours le répertoire courant comme point de départ, il n'y a donc pas d'arguments pour désigner un répertoire de départ.

Sa syntaxe générale devra être de la forme :

Syntaxe

rgrep [-l] [-in] CHAINE

Exemple d'utilisation :

#> rgrep -n "print"
...

Le script aura les même codes de retour que la commande grep.

Compréhension de script

Lire le script rm_secure.sh de Christophe Blaess à cette adresse :
http://www.emse.fr/~serpaggi/enseignement/Shell/rm_secure.sh
et répondez aux questions suivantes :

  1. À quoi sert ce script ?
  2. ligne 31 : pourquoi traiter l'option - ?
  3. ligne 71 : pourquoi avoir mis les commandes cd et ls entre parenthèse ?
  4. ligne 93 : à quoi sert ce continue ?
  5. ligne 100 : à quoi sert ce continue ?
  6. ligne 110 : que signifie cette ligne et quel est son effet ?

Si vous avez du temps...

Écrivez un script qui liste de manière récursive les répertoires et les fichiers en les présentant sous la forme d'un arbre simple.

Un exemple d'utilisation de ce script serait :

#> lstree ~
tmp.txt
bashrc
bashr_profile
local/
|--- readme
|--- bin/
|     |--- uhelp
|     |--- rgrep
|     |--- wget
|--- man/
|     |--- man1/
|     |--- man2/
tmp/
|--- foo
|--- bar

Les fichiers sont, à chaque niveau, affichés avant les répertoires et le mode de parcours de l'arborescence du système de fichiers est en profondeur (on traite les fils avant les frères).

Commencez par faire une version qui n'affiche que la structure des répertoires, sans se préoccuper des fichiers et sans "dessiner" l'arbre, uniquement en faisant des indentations différentes en fonction de la profondeur.

Faites ensuite une version avec les fichiers, puis enfin avec le "dessin" de l'arbre.