Académique Documents
Professionnel Documents
Culture Documents
exercices
v4
Hervé COSTANTINI
Table des matières
introduction ............................................................................................................................................. 3
processus ................................................................................................................................................. 4
mémoire .................................................................................................................................................. 5
fichiers ..................................................................................................................................................... 5
v3 ......................................................................................................................................................... 8
shells/scripts ............................................................................................................................................ 9
Exercice 1 : énoncé .............................................................................................................................. 9
Exercice 2 : énoncé .............................................................................................................................. 9
Signalisation........................................................................................................................................... 10
Exercice 1 : énoncé ............................................................................................................................ 10
Exercice 2 : énoncé ............................................................................................................................ 10
Exercice 3 : énoncé ............................................................................................................................ 11
Manipulation de chiffres binaires (bits) ................................................................................................ 13
Exercice 1 : énoncé ............................................................................................................................ 13
Entrées/Sorties et Communication Inter-processus ............................................................................. 14
Exercice 1 : synchrones bloquantes : énoncé.................................................................................... 14
Exercice 2 : synchrones non bloquantes par pipe : énoncé .............................................................. 16
2
introduction
Ce fascicule d’exercices suit l’ordre des thèmes du cours correspondant. Vous devez vous familiariser
tout d’abord avec les commandes de la présente section afin de pouvoir ensuite parcourir les sections
suivantes. Commencez, sous une distribution Linux de votre choix, par lancer l’application Terminal.
Le tableau ci-dessous vous invite à taper des commandes, constater les affichages provoqués par ces
commandes ; en outre, des commentaires sont clairsemés ; ils apparaissent derrière le mot « nota ».
Enfin, le caractère point-virgule (;) permet d’écrire plusieurs commandes sur la même ligne, en les
séparant l’une de l’autre. Par exemple :
cd .. ; pwd
est équivalent à :
cd ..
pwd
3
processus
taper la commande suivante constater qu’elle affiche et expliquer
ps
ps
kill 29004
ou bien
kill -9 29004
sleep 80 &
sleep 60 &
sleep 90 &
killall sleep
killall -u <nom_uti>
killall -w sleep
pidof bash
nice -n 19 ls -l
renice -n 18 12345
4
top
pstree
time ls -l
mémoire
taper la commande suivante constater qu’elle affiche et expliquer
df
du
fichiers
taper la commande suivante constater qu’elle affiche
pwd
mkdir –v rep1
ls
5
cd rep1 ; pwd
cd .. ; pwd
cd
touch fichier1.txt ; ls
clear
echo "bonjour"
cat fichier1.txt
echo "au revoir" >> fichier1.txt
head -1 fichier1.txt
tail -1 fichier1.txt
stat fichier1.txt
stat rep1
6
du –xh ~
cp –v fichier1.txt rep1
mv –v fichier1.txt rep1
md5sum fichier1.txt
7
ln –v fichier1.txt file1.txt
rm –v fichier1.txt
v3
taper la commande suivante constater qu’elle affiche
grep hello fichier1.txt
grep -r hello .
wc fichier1.txt
sort nouveau.txt;
8
diff nouveau.txt fichier1.txt
dirname fichier1.txt
basename ./fichier1.txt
shells/scripts
Exercice 1 : énoncé
1. Écrivez un script qui affiche le nom d'une ville.
5. Le script précédent n'influence pas votre shell actuel (les variables n'existent pas en dehors du
script). Exécutez maintenant le script pour qu'il influence votre shell actuel.
Exercice 2 : énoncé
1. Écrivez un script qui demande deux nombres et génère la somme et le produit (comme illustré ci-
dessous).
Entrez un nombre: 5
Entrez un autre numéro: 2
Somme: 5 + 2 = 7
Produit: 5 x 2 = 10
2. Améliorez le script précédent pour tester que les nombres sont compris entre 1 et 100, quittez avec
une erreur si nécessaire.
3. Améliorez le script précédent pour féliciter l'utilisateur si la somme est égale au produit.
4. Écrivez un script avec une déclaration de casse insensible à la casse, en utilisant l'option shopt
nocasematch. L'option nocasematch est réinitialisée à la valeur qu'elle avait avant le démarrage des
scripts.
9
Signalisation
Exercice 1 : énoncé
Dans votre navigateur préféré, se rendre à l'url suivante :
https://www.onlinegdb.com/
void
segViolation (int sig)
{
exit (1);
}
puis cliquer Run ( ) puis cliquer le bouton Download code ( ) afin d'enregistrer ce
code sur votre ordinateur, et surtout vos modifications. Enfin, y copier/coller les lignes ci-dessous aux
bons endroits :
printf("D\u00e9but.\n");
printf("D\u00e9claration pointeur fou (=qui pointe nulle part).\n");
printf("Vectorisation signal SIGSEGV (%d) : violation segmentation.\n", SIGSEGV);
printf("Boucle d'\u00e9critures en m\u00e9moire depuis le pointeur fou.\n");
printf("Ce message ne devrait pas s'afficher.\n");
printf ("Signal %d re\u00e7u. Violation de segmentation.\n", sig);
printf ("Fin pr\u00e9matur\u00e9e.\n");
Nota : les lettres accentuées ne sont pas supportées d'où l'utilisation de \u00e9 pour é, \u00e7 pour
ç. Cf. https://outils-javascript.aliasdmc.fr/encodage-caracteres-accentues/ et choisir la valeur Js.
Exercice 2 : énoncé
Dans votre navigateur préféré, se rendre à l'url suivante :
https://www.onlinegdb.com/
10
#include <stdio.h>
#include <errno.h>
#include <signal.h>
#include <stdlib.h>
#include <unistd.h>
#define N 3
int
main ()
{
void sigalrm (int);
if (signal (SIGALRM, sigalrm) == SIG_ERR)
{
perror ("signal");
exit (1);
}
alarm (N);
pause ();
return 0;
}
void
sigalrm (int sig)
{
}
puis cliquer Run ( ) puis cliquer le bouton Download code ( ) afin d'enregistrer ce
code sur votre ordinateur, et surtout vos modifications. Enfin, y copier/coller les lignes ci-dessous aux
bons endroits :
printf("D\u00e9but.\n");
printf("Vectorisation SIGALRM (%d).\n", SIGALRM);
printf("Armement alarme à %d sec.\n", N);
printf("Attente \u00e9ch\u00e9ance.\n");
printf("\u00c9ch\u00e9ance trait\u00e9e.\n");
printf("Fin.\n");
printf ("Signal (%d) re\u00e7u.\n", sig);
printf ("\u00c9ch\u00e9ance atteinte.\n");
Nota : les lettres accentuées ne sont pas supportées d'où l'utilisation de \u00e9 pour é, \u00e7 pour
ç. Cf. https://outils-javascript.aliasdmc.fr/encodage-caracteres-accentues/ et choisir la valeur Js.
Exercice 3 : énoncé
Dans votre navigateur préféré, se rendre à l'url suivante :
https://www.onlinegdb.com/
int idpere;
int idfils;
#define FILS 0
#define SYS_ERR -1
int
main ()
11
{
idpere = getpid ();
if (signal (SIGUSR1, func_user1) == SIG_ERR)
{
perror ("signal");
exit (1);
}
switch (idfils = fork ())
{
case FILS:
fils ();
break;
case SYS_ERR:
erreur ("fork");
break;
default:
pere ();
break;
}
return 0;
}
int
pere ()
{
sleep(1);
if (kill (idfils, SIGUSR1))
{
perror ("kill p\u00e8re");
exit (1);
}
pause ();
return 0;
}
int
fils ()
{
pause ();
if (kill (idpere, SIGUSR1))
{
perror ("kill fils");
exit (1);
}
return 0;
}
void
erreur (char *nom)
{
perror (nom);
exit (1);
}
void
func_user1 (int sig)
{
}
puis cliquer Run ( ) puis cliquer le bouton Download code ( ) afin d'enregistrer ce
code sur votre ordinateur, et surtout vos modifications. Enfin, y copier/coller les lignes ci-dessous aux
bons endroits :
printf ("P\u00e8re. D\u00e9but.\n");
printf ("P\u00e8re. Identifiant=%d.\n", idpere);
printf ("P\u00e8re. Vectorisation SIGUSR1 (%d).\n", SIGUSR1);
printf ("P\u00e8re. Cr\u00e9ation Fils.\n");
printf ("P\u00e8re. Identifiant Fils=%d.\n", idfils);
printf ("P\u00e8re. Attente stabilisation Fils.\n");
printf ("P\u00e8re. Envoi signal.\n");
printf ("P\u00e8re. Attente signal.\n");
printf ("P\u00e8re. Signal trait\u00e9.\n");
printf ("P\u00e8re. Fin.\n");
12
printf ("Fils. D\u00e9but.\n");
printf ("Fils. Attente signal.\n");
printf ("Fils. Signal trait\u00e9.\n");
printf ("Fils. Envoi signal.\n");
printf ("Fils. Fin.\n");
printf ("%d. Signal SIGUSR1 (%d) re\u00e7u.\n", getpid (), sig);
Nota : les lettres accentuées ne sont pas supportées d'où l'utilisation de \u00e9 pour é, \u00e7 pour
ç. Cf. https://outils-javascript.aliasdmc.fr/encodage-caracteres-accentues/ et choisir la valeur Js.
https://www.onlinegdb.com/
*******************************************************************************/
#include <stdio.h>
#include <stdlib.h>
int
main ()
{
unsigned char map[SIZE];
init_bm (map);
print_bm (map);
s_bm (map, BIT);
print_bm (map);
t_bm (map, BIT);
print_bm (map);
r_bm (map, BIT);
print_bm (map);
return 0;
}
// INIT BITMAP
void
init_bm (unsigned char *map)
{
for (int i = 0; i < SIZE; i++)
map[i] = 0;
// PRINT BITMAP
void
print_bm (unsigned char *map)
{
int i = SIZE;
while (i-- > 0) printf ("map[%d]=%x%s", i, map[i], i > 0 ? ", " : ".\n");
i = SIZE;
while (i-- > 0) {
13
printf ("map[%d]=", i);
int j = 8;
while (j > 0) printf("%x", (map[i] >> --j) & 1);
printf("%s", i > 0 ? ", " : ".\n"); }
}
// SET BIT
void
s_bm (unsigned char *map, int c)
{
valid_c (c);
map[c >> 3] |= 1 << (c & 0x07);
return;
}
// RESET BIT
void
r_bm (unsigned char *map, int c)
{
valid_c (c);
map[c >> 3] &= ~(1 << (c & 0x07));
return;
}
// TEST BIT
int
t_bm (unsigned char *map, int c)
{
int ret;
valid_c (c);
ret = (map[c >> 3] & (1 << (c & 0x07)));
return ret;
}
void
valid_c (int c)
{
if (c >> 3 < SIZE)
return;
exit (1);
}
puis cliquer Run ( ) puis cliquer le bouton Download code ( ) afin d'enregistrer ce
code sur votre ordinateur, et surtout vos modifications. Enfin, y copier/coller les lignes ci-dessous aux
bons endroits :
printf ("D\u00e9but\n");
printf ("D\u00e9clarer un tableau de %d bits, i.e. %d octets.\n", SIZE * 8, SIZE);
printf ("Initialiser le tableau \u00e0 z\u00e9ro.\n");
printf ("Valeurs du tableau en octets puis en chiffres binaires (bits).\n");
printf ("Demande re\u00e7ue : mettre à 1 le bit %d.\n", c);
printf ("Demande effectu\u00e9e : mettre à 1 le bit %d.\n", c);
printf ("Demande re\u00e7ue : mettre à 0 le bit %d.\n", c);
printf ("Demande effectu\u00e9e : mettre à 0 le bit %d.\n", c);
printf ("Demande re\u00e7ue : tester le bit%d.\n", c);
printf ("Demande effectu\u00e9e : bit%d=%d.\n", c, ret);
printf ("D\u00e9passement de capacit\u00e9 : %d > %d.\n", c, SIZE*8 - 1);
Nota : les lettres accentuées ne sont pas supportées d'où l'utilisation de \u00e9 pour é, \u00e7 pour
ç. Cf. https://outils-javascript.aliasdmc.fr/encodage-caracteres-accentues/ et choisir la valeur Js.
https://www.onlinegdb.com/
14
puis y copier/coller le code ci-après :
/******************************************************************************
E/S synchrones Bloquantes
******************************************************************************/
#include <stdio.h>
#include <errno.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
int
main ()
{
int fd, status;
char buffer[SIZE];
if (!(fd = open (FILE, O_RDWR | O_APPEND | O_CREAT)))
{
perror ("Open/Create");
return (1);
}
switch (status = read (fd, buffer, SIZE))
{
case -1:
perror ("Read");
return (1);
case 0:
break;
default:
break;
}
sleep(WAIT);
// Préparer l'écriture
sprintf (buffer, "%s\n", "Ecriture de texte");
puis cliquer Run ( ) puis cliquer le bouton Download code ( ) afin d'enregistrer ce
code sur votre ordinateur, et surtout vos modifications. Enfin, y copier/coller les lignes ci-dessous aux
bons endroits :
printf("D\u00e9but.\n");
printf("D\u00e9claration d'un tampon d'entr\u00e9e/sortie, de taille %d.\n", SIZE);
printf("Ouverture du fichier d'entr\u00e9e/sortie \"%s\".\n", FILE);
printf("Lecture du fichier.\n");
printf ("End Of File\n");
printf ("Lecture (%d octets) :\n>>>\n%s\n<<<\n", (int)strlen(buffer), buffer);
printf ("Attente entre lecture et \u00e9criture : %d sec.\n", WAIT);
printf ("Pr\u00e9paration de l'\u00e9criture.\n");
printf ("\u00c9criture du fichier.\n");
printf ("End Of File\n");
printf ("Ecriture (%d octets) : %s\n", status, buffer);
15
Nota : les lettres accentuées ne sont pas supportées d'où l'utilisation de \u00e9 pour é, \u00e7 pour
ç. Cf. https://outils-javascript.aliasdmc.fr/encodage-caracteres-accentues/ et choisir la valeur Js.
https://www.onlinegdb.com/
#define MSGSIZE 9
int main()
{
int p[2];
if (pipe(p) < 0) {
exit(1);
}
if (fcntl(p[0], F_SETFL, O_NONBLOCK) < 0) {
exit(2);
}
switch (fork()) {
case -1:
exit(3);
case 0:
child_write(p);
break;
default:
parent_read(p);
break;
}
return 0;
}
void parent_read(int p[])
{
int nread;
char buf[MSGSIZE];
close(p[1]);
while (1) {
nread = read(p[0], buf, MSGSIZE);
switch (nread) {
case -1:
if (errno == EAGAIN) {
sleep(1);
break;
} else {
perror("read");
exit(4);
}
case 0:
close(p[0]);
exit(0);
default:
}
}
16
}
void child_write(int p[])
{
close(p[0]);
for (int i = 0; i < 3; i++) {
printf(" Fils. \u00c9criture tube. ");
write(p[1], msg1, MSGSIZE);
printf("Message \u00e9mis. Taille = %d. Contenu = \"%s\".\n", MSGSIZE, msg1);
sleep(3);
}
write(p[1], msg2, MSGSIZE);
exit(0);
}
puis cliquer Run ( ) puis cliquer le bouton Download code ( ) afin d'enregistrer ce
code sur votre ordinateur, et surtout vos modifications. Enfin, y copier/coller les lignes ci-dessous aux
bons endroits :
printf("P\u00e8re. D\u00e9but.\n");
printf("P\u00e8re. Cr\u00e9ation d'un tube.\n");
printf("P\u00e8re. Tubes non support\u00e9s. Fin\n");
printf("P\u00e8re. Activation du mode non bloquant.\n");
printf("P\u00e8re. Mode non bloquant indisponible. Fin\n");
printf("P\u00e8re. Cr\u00e9ation Fils.\n");
printf("P\u00e8re. Fork impossible.\n");
printf("Fils. D\u00e9but.\n");
printf("P\u00e8re. Fermeture acc\u00e8s \u00e9criture du tube.\n");
printf("P\u00e8re. Boucle de lecture.\n");
printf(" P\u00e8re. Lecture tube. ");
printf("Tube vide.\n");
printf("Fin de communication re\u00e7ue.\n");
printf("P\u00e8re. Fermeture acc\u00e8s lecture du tube.\n");
printf("P\u00e8re. Fin.\n");
printf("Message re\u00e7u. Taille = %d. Contenu = \"%s\".\n", nread, buf);
printf("Fils. Fermeture acc\u00e8s lecture du tube.\n");
printf("Fils. Boucle d'\u00e9criture.\n");
printf("Fils. \u00c9criture tube. ");
printf("Message \u00e9mis. Taille = %d. Contenu = \"%s\".\n", MSGSIZE, msg2);
printf("Fils. Fin \u00e9mise.\n");
printf("Fils. Fin.\n");
Nota : les lettres accentuées ne sont pas supportées d'où l'utilisation de \u00e9 pour é, \u00e7 pour
ç. Cf. https://outils-javascript.aliasdmc.fr/encodage-caracteres-accentues/ et choisir la valeur Js.
17