Nicolas LEFEVRE-LAUMONIER 3402603 LI 219 : Multi PROGRAMMATION SYSTEME 12 janvi
Nicolas LEFEVRE-LAUMONIER 3402603 LI 219 : Multi PROGRAMMATION SYSTEME 12 janvier 2015 Montréal Exercice 1 Question 1 L'objectif est d'exécuter les commandes commande1.sh commande2.sh commande3 .sh du répertoire /bin/groupe2. La variable PATH = /bin/groupe1:/bin/groupe2:/bin/groupe3. En exécutant une des trois commande ci-dessus, le shell va chercher en premier un fichier exécutable dans le premier répertoire du PATH soit /bin/groupe1. Or les trois fichiers existent avec les droits en lecture et en exécution pour tous les utilisateurs : ce sont donc ces fichiers qui seront exécutés. Pour exécuter les commandes commande1.sh commande2.sh commande3.sh du répertoire /bin/groupe2, la solution la plus simple est de retirer les droits en exécution du repertoire groupe1 comme ci dessous : chmod a-x bin/groupe1 Dès lors l'exécution des commandes commande1.sh commande2.sh commande3.sh seront celles du répertoire /bin/groupe2 Question 2 L'objectif est d'exécuter les commandes : - commande1.sh du répertoire /bin/groupe1 - commande2.sh du répertoire /bin/groupe2 - commande3.sh du répertoire /bin/groupe3 La variable PATH = /bin/groupe1:/bin/groupe2:/bin/groupe3. En exécutant une des trois commande ci-dessus, le shell va chercher les fichiers exécutables du répertoire /bin/groupe1. Il faut donc supprimer les droits en exécution de - commande2.sh du répertoire /bin/groupe2 - commande3,sh du répertoire /bin/groupe1 - commande3,sh du répertoire /bin/groupe2 Dés lors, en exécutant commande1.sh, le shell, à partir du PATH exécute commande1.sh du répertoire /bin/groupe1 Dés lors, en exécutant commande2.sh, le shell, à partir du PATH exécute commande2.sh du répertoire /bin/groupe2 Dés lors, en exécutant commande3,sh, le shell, à partir du PATH exécute commande3.sh du répertoire /bin/groupe3 Les commandes à exécuter : chmod a-x bin/groupe1/commande2.sh bin/groupe1/commande3.sh bin/groupe2/commande3.sh Question 3 Dans le même esprit que les question précédente une solution possible est la suivante : - changement de propriétaire du groupe1, affecter user1 - changement de propriétaire du groupe2, affecter user2 - changement de propriétaire du groupe3, affecter user3 - retirer les droits d’exécution à group et other pour les répertoires groupe1, groupe2, groupe3 Ainsi, si l'utilisateur user1 exécute une commande, le Shell avec l'appui du PATH exécutera celle du répertoire groupe1. Ainsi, si l'utilisateur user2 exécute une commande, le Shell avec l'appui du PATH exécutera celle du répertoire groupe2. Ainsi, si l'utilisateur user3 exécute une commande, le Shell avec l'appui du PATH exécutera celle du répertoire groupe3. Les commandes à exécuter : chown -R user1 bin/groupe1 chown -R user2 bin/groupe2 chown -R user3 bin/groupe3 chmod go-x bin/groupe1 bin/groupe2 bin/groupe3 Exercice 2 Question 1 Affichage produit par ./pere.sh 1 2 3 22 47 64 resultat: 20 Question 2 Les modifications sont les suivantes (surlignés en vert): #! /bin/bash # pere.sh val=20 export i val for i in "$@"; do ./fils.sh done echo "resultat: $val" #! /bin/bash # fils.sh x=`./alea.sh` res=`expr $i \* $val` res=`expr $res + $x` echo $res fils.sh ne prenant plus de valeurs Input, il faut donc créer une copie de la variable i et val dans le contexte d’exécution de la descendance du processus lié à pere.sh : la commande export i val rempli ce rôle. Il faut également changer le code de fils.sh en conséquence. Question 3 Les modifications sont les suivantes (surlignés en vert): #! /bin/bash # pere.sh val=20 somValAlea=0 for i in "$@"; do ./fils.sh $i $val somValAlea=`expr $somValAlea + $?` done echo "resultat: $val" echo "somme des valeurs aléatoires: $somValAlea" #! /bin/bash # fils.sh x=`./alea.sh` res=`expr $1 \* $2` res=`expr $res + $x` echo $res exit $x La modification principale réside dans l'utilisation de exit $x qui permet de donner de donner une valeur de retour à fils.sh égale à la valeur du chiffre aléatoire. Cette valeur est ensuite récupérée dans pere.sh via la commande $? qui permet de récupérer a valeur de retour du dernier processus exécuté en premier plan. Il suffit ensuite de faire une somme et gérer l'affichage au sein de pere.sh. Question 4 Les modifications sont les suivantes (surlignés en vert): #! /bin/bash # pere.sh val=20 produit=1 for i in "$@"; do source ./fils.sh $i $val produit=`expr $produit \* $res` done echo "resultat: $val" echo "produit: $produit" La modification principale réside dans l'utilisation de source qui permet d'exécuter les instructions de fils.sh dans le processus pere.sh. De la sorte la variable res de fils.sh est accessible à pere.sh à la fin de l'appel de fils.sh et permet de faire un produit. L'utilisation de source ne pose pas de souci car fils.sh ne modifie pas la valeur de la variable val et réinitialise res à chaque passage avec res=`expr $1 \* $2`. Question 5 Un processus ne peut jamais passer directement de l’état bloqué à l'état élu. Pour être élu, c'est à dire en exécution, un processus doit être choisi par l'ordonnanceur. L'ordonnanceur choisit le processus à exécuter parmi les processus prêt. Un Un processus ne peut donc jamais passer directement de l’état bloqué à l'état élu. Un processus ne peut jamais passer directement de l’état prêt à l'état bloqué. Un processus dans l’état prêt attend d'être choisit par l'ordonnanceur pour être exécuté. Il ne peut donc être bloqué. Il passera éventuellement à l'état bloqué lorsque l'ordonnanceur l'aura choisi pour être exécuté. A ce moment, un événement pour bloquer le processus. Le processus sera en attente d'un autre événement pour reprendre son exécution. Exercice 3 Question 1 Les modifications sont les suivantes (surlignés en vert): #! /bin/bash # proc1.sh fic="$1" max=$2 i=0 while [ $i -lt $max ] ; do read a echo $a ./proc2.sh $fic $i i=`expr $i + 1` done <$fic La modification principale réside dans l'utilisation de <$fic au niveau de la bloucle while de proc1.s. proc1.sh et proc2.sh partage le même offset de lecture. Voici le fonctionnement de la lecture. proc i lecture proc1 0 1 proc1 1 2 proc2 0 3 proc1 2 4 proc2 0 5 proc2 1 6 proc1 3 7 proc2 0 8 proc2 1 9 proc2 2 10 Question 2 #! /bin/bash # proc1.sh fic="$1" max=$2 i=0 while [ $i -lt $max ] ; do read a echo $a ./proc2.sh $fic $i i=`expr $i + 1` done <$fic #! /bin/bash # proc2.sh fic=$1 max=$2 i=0 while [ $i -lt $2 ] ; do read a echo $a i=`expr $i + 1` done <$fic La modification principale réside dans l'utilisation de <$fic au niveau de la boucle while de proc1.sh et proc2.sh. proc1.sh et proc2.sh ont des offset de lecture différents. proc2.sh recommence la lecture du fichier au début a chaque nouvel appel. Voici le fonctionnement de la lecture. proc i lecture proc1 0 1 proc1 1 2 proc2 0 1 proc1 2 3 proc2 0 1 proc2 1 2 proc1 3 4 proc2 0 1 proc2 1 2 proc2 2 3 Exercice 4 Question 1 Affichage Processus 1 : debut Processus 2 : debut Processus 3 : debut Processus 4 : debut Processus 4 : fin Processus 3 : fin Processus 2 : fin Processus 1 : fin L’utilisation de la commande wait bloque le processus courant tant que tous ses fils ne sont pas terminés. Dans ce cas, il y a un appel récursif de arbre.sh. 4 processus sont initiés sans pouvoir être achevé. Le premier processus à terminer son exécution est le « plus jeune » des fils soit le processus4 car il ne fait pas appel à la création d'un nouveau processus fils : la commande wait est donc inopérante. L'aboutissement du processus4 permet de lever la contrainte de la commande wait pour le processus3. Ainsi de suite jusqu'au processus1. Question 2 Arbre.sh Arbre.sh Arbre.sh Arbre.sh Wait Wait Wait Annulation Wait Annulation Wait Annulation Wait Question 3 #! /bin/bash # arbre2.sh echo "Processus $1 : debut" echo -n $2 > fic if [ "$1" -lt "$2" ]; then ./arbre2.sh `expr $1 + 1` $2 & while true; do sleep 1 read a < fic if [ "$1" = "$a" ]; then echo "Processus $1 : fin" echo -n `expr $1 - 1` > fic kill -SIGKILL $$ fi done fi echo "Processus $1 : fin" echo -n `expr $2 - 1` > fic On utilise un fichier pour gérer l’arrêt des différent processus. La commande kill -SIGKILL $$ permet de tuer le processus courant une fois que la condition est remplie. La condition est basée sur la valeur la plus élevée de la boucle qui est ensuite itérée négativement à mesure que les processus sont tués. Sans doute pas la manière la plus élégante de résoudre le problème mais fonctionne. Exercice 5 Exécution 1 : Possible L'analyse du code permet de conclure assez aisément que : - Pere : 1 arrive avant Pere : 2 La boucle for commence par i = 1 puis i = 2. La boucle est séquentielle, pas de processus parallèle. La condition est respectée Le processus générant «Fils : 1 » est exécuté en parallèle avant «echo Pere : $1 » et «echo Pere : $2 », il peut terminé avant ces processus ou après dépendamment du temps d'exécution. Le processus générant «Fils : 1 » est éxécuté en parallèle avant le processus générant « Fils : 2 » : il peut terminé avant ou après le processus générant « Fils : 2 » dépendamment uploads/Industriel/ li219-devoir1.pdf
Documents similaires










-
31
-
0
-
0
Licence et utilisation
Gratuit pour un usage personnel Attribution requise- Détails
- Publié le Apv 28, 2021
- Catégorie Industry / Industr...
- Langue French
- Taille du fichier 0.0778MB