Compare commits
4 commits
7389cdf661
...
44368b1f3c
Author | SHA1 | Date | |
---|---|---|---|
44368b1f3c | |||
1270258505 | |||
ab15c9a50a | |||
06a4a93db1 |
BIN
content/progsys/4_les-signaux/files/presentation.pdf
Normal file
242
content/progsys/4_les-signaux/index.md
Normal file
|
@ -0,0 +1,242 @@
|
||||||
|
---
|
||||||
|
title: "Les signaux"
|
||||||
|
categories: ["Programmation système", "cours"]
|
||||||
|
tags: ["C", "programmation", "signaux"]
|
||||||
|
date: 2018-09-25
|
||||||
|
---
|
||||||
|
|
||||||
|
En programmation système, un signal est une notification à un processus qu'un
|
||||||
|
évènement a eu lieu. Également appelés **Interruptions Logicielles**, les
|
||||||
|
signaux son asynchrone est il est impossible de prédire à quel moment il
|
||||||
|
arriveront.
|
||||||
|
|
||||||
|
Les signaux couvrent plusieurs types d'évènements :
|
||||||
|
|
||||||
|
* **Les actions utilisateurs** `CTRL + C` pour *SIGINT* ou `CRTL + Z` pour
|
||||||
|
*SIGSTOP*
|
||||||
|
* **Les fautes matérielles** comme la division par zéro *SIGFPE*, la référence
|
||||||
|
mémoire invalide *SIGSEGV*, écriture mémoire erronée *SIGSEGV* etc.
|
||||||
|
* **les fautes logicielles** comme l'erreur d'écriture dans un tube *SIGPIPE*,
|
||||||
|
la notification urgente de données disponibles *SIGURG*, l'alarme *SIGALRM*
|
||||||
|
|
||||||
|
Ils représentent une forme basique de communication inter-processus ( *IPC* )
|
||||||
|
mais permettent aussi à l'utilisateur d'intervenir dans le déroulement d'un
|
||||||
|
processus. (voir `man 1 kill` et `man 2 kill`).
|
||||||
|
|
||||||
|
C'est au processus de se déclarer à l'écoute d'un type d'évènement en
|
||||||
|
initialisant un gestionnaire appelé lorsque l'évènement visé aura lieu. Lorsque
|
||||||
|
ce dernier a lieu, le gestionnaire est appelé avec toutes les informations
|
||||||
|
nécessaires. A la fin de l'exécution du gestionnaire, l'exécution du processus
|
||||||
|
reprend normalement à l'endroit ou elle s'est arrêtée.
|
||||||
|
|
||||||
|
## Comportement associés aux signaux.
|
||||||
|
|
||||||
|
Par défaut, des comportements sont associés aux signaux :
|
||||||
|
|
||||||
|
* **stop** : arrête le processus
|
||||||
|
* **cont** : continuer le processus s'il est arrêté.
|
||||||
|
* **term** : terminer le processus
|
||||||
|
* **ign** : ignorer le processus
|
||||||
|
* **core** : créer un fichier *core* (contexte d'exécution du processus) puis
|
||||||
|
*sigterm*
|
||||||
|
|
||||||
|
## Liste des signaux
|
||||||
|
|
||||||
|
### Norme POSIX 1-1999
|
||||||
|
|
||||||
|
Signal | Valeur | Action | Commentaire
|
||||||
|
--------|--------|--------|----------------------------------------------------
|
||||||
|
SIGHUP | 1 | Term | Déconnexion du terminal ou fin du processus de contrôle
|
||||||
|
SIGINT | 2 | Term | Interruption depuis le clavier `CTRL + C`
|
||||||
|
SIGQUIT | 3 | Core | Demande ”Quitter” depuis le clavier `CTRL + \\`
|
||||||
|
SIGILL | 4 | Core | Instruction illégale
|
||||||
|
SIGABRT | 6 | Core | Signal d’arrêt depuis abort(3)
|
||||||
|
SIGFPE | 8 | Core | Erreur mathématique virgule flottante
|
||||||
|
SIGKILL | 9 | Term | Signal ”KILL”
|
||||||
|
SIGSEGV | 11 | Core | Référence mémoire invalide
|
||||||
|
SIGPIPE | 13 | Term | Écriture dans un tube sans lecteur
|
||||||
|
SIGALRM | 14 | Term | Temporisation alarm(2) écoulée
|
||||||
|
SIGTERM | 15 | Term | Signal de fin
|
||||||
|
SIGUSR1 | 10 | Term | Signal utilisateur 1
|
||||||
|
SIGUSR2 | 12 | Term | Signal utilisateur 2
|
||||||
|
SIGCHLD | 17 | Ign | Fils arrêté ou terminé
|
||||||
|
SIGCONT | 18 | Cont | Continuer si arrêté
|
||||||
|
SIGSTOP | 19 | Stop | Arrêt du processus
|
||||||
|
SIGTSTP | 20 | Stop | Stop invoqué depuis le terminal `CTRL + Z`
|
||||||
|
SIGTTIN | 21 | Stop | Lecture sur le terminal en arrière-plan
|
||||||
|
SIGTTOU | 22 | Stop | Écriture dans le terminal en arrière-plan
|
||||||
|
|
||||||
|
Les signaux **SIGKILL** et **SIGSTOP** ne peuvent ni être capturés ou ignorés.
|
||||||
|
|
||||||
|
|
||||||
|
### Normes SUSv2 et POSIX 1-2001
|
||||||
|
|
||||||
|
Signal | Valeur | Action | Commentaire
|
||||||
|
----------|--------|--------|--------------------------------------------------
|
||||||
|
SIGBUS | 7 | Core | Erreur de bus (mauvais accès mémoire)
|
||||||
|
SIGPOLL | | Term | Événement ”pollable”, synonyme de SIGIO
|
||||||
|
SIGPROF | 27 | Term | Expiration de la temporisation pour le suivi
|
||||||
|
SIGSYS | 31 | Core | Mauvais argument de fonction
|
||||||
|
SIGTRAP | 5 | Core | Point d’arrêt rencontré
|
||||||
|
SIGURG | 23 | Ign | Condition urgente sur socket
|
||||||
|
SIGVTALRM | 26 | Term | Alarme virtuelle
|
||||||
|
SIGXCPU | 24 | Core | Limite de temps CPU dépassée
|
||||||
|
SIGXFSZ | 25 | Core | Taille de fichier excessive
|
||||||
|
SIGWINCH | 28 | Ign | Fenêtre redimensionnée
|
||||||
|
|
||||||
|
## Le core dump
|
||||||
|
|
||||||
|
Un **core dump** est une image mémoire d'un processus prise au moment d'un
|
||||||
|
plantage. Elle contient des information utiles pour l'analyse du crash :
|
||||||
|
|
||||||
|
* copie de la mémoire au moment du plantage
|
||||||
|
* statut de terminaison du processus
|
||||||
|
* copie des registres *CPU*
|
||||||
|
|
||||||
|
Prenons l'exemple de code suivant :
|
||||||
|
|
||||||
|
```C
|
||||||
|
int main ()
|
||||||
|
{
|
||||||
|
int a = 10;
|
||||||
|
int b = 0;
|
||||||
|
a = a / b
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Compilons le et exécutons le :
|
||||||
|
|
||||||
|
```shell
|
||||||
|
$ gcc -g -Wall sigfpe.c -o sigfpe
|
||||||
|
$ ./sigfpe
|
||||||
|
[2] 8112 floating point exception (core dumped) ./sigfpe
|
||||||
|
```
|
||||||
|
|
||||||
|
Analysons maintenant le *core dump* avec `gdb`
|
||||||
|
|
||||||
|
```shell
|
||||||
|
$ gdb sigfpe core
|
||||||
|
GNU gdb (Debian 7.11.1-2) 7.11.1
|
||||||
|
Core was generated by `./sigfpe'.
|
||||||
|
Program terminated with signal SIGFPE, Arithmetic exception.
|
||||||
|
#0 0x00000000004004ec in main () at sigfpe.c:4
|
||||||
|
4 a = a / b;
|
||||||
|
(gdb) backtrace full
|
||||||
|
#0 0x00000000004004ec in main () at sigfpe.c:4
|
||||||
|
a = 10
|
||||||
|
b = 0
|
||||||
|
(gdb)
|
||||||
|
```
|
||||||
|
|
||||||
|
## Gestion des signaux.
|
||||||
|
|
||||||
|
en programmation système, la gestion des signaux revient à changer le
|
||||||
|
comportement par défaut par un souhaité lors de la réception d'un signal donné
|
||||||
|
par un processus.
|
||||||
|
|
||||||
|
```C
|
||||||
|
#include <signal.h>
|
||||||
|
|
||||||
|
typedef void (*sighandler_t)(int);
|
||||||
|
sighandler_t signal(int signum, sighandler_t handler);
|
||||||
|
```
|
||||||
|
|
||||||
|
* `signum` est le numéro de signal à modifier
|
||||||
|
* `handler` vaut soit *SIG_IGN* pour ignorer le signal, soit *SIG_DFL* pour le
|
||||||
|
réinitialiser à sa valeur par défaut ou est un pointeur vers une fonction à
|
||||||
|
appeler.
|
||||||
|
|
||||||
|
L'appel à `signal()` renvoie la valeur du gestionnaire de signal précédent en
|
||||||
|
cas de réussite, sinon *SIG_ERR*.
|
||||||
|
|
||||||
|
### exemple de code
|
||||||
|
|
||||||
|
```C
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <signal.h>
|
||||||
|
|
||||||
|
void sigusr1_trigger() {
|
||||||
|
write(1, "SIGUSR1 received\n", 17);
|
||||||
|
}
|
||||||
|
|
||||||
|
int main () {
|
||||||
|
if (signal(SIGUSR1, sigusr1_trigger) == SIG_ERR) {
|
||||||
|
perror("Unable to catch SIGUSR1\n");
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
printf("SIGUSR1 is catched on process with PID=%d\n", getpid());
|
||||||
|
}
|
||||||
|
for(;;) {
|
||||||
|
sleep(10);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
#### Exécution
|
||||||
|
|
||||||
|
##### 1 sur le premier terminal
|
||||||
|
|
||||||
|
```shell
|
||||||
|
$ ./sigusr1
|
||||||
|
SIGUSR1 is catched on process with PID=10333
|
||||||
|
```
|
||||||
|
|
||||||
|
##### 2 Sur le second terminal, envoi du signal :
|
||||||
|
|
||||||
|
```shell
|
||||||
|
$ kill -USR1 10333`
|
||||||
|
```
|
||||||
|
|
||||||
|
##### 3 Retour sur le premier terminal :
|
||||||
|
|
||||||
|
```shell
|
||||||
|
$ ./sigusr1
|
||||||
|
SIGUSR1 is catched on process with PID=10333
|
||||||
|
SIGUSR1 received
|
||||||
|
```
|
||||||
|
|
||||||
|
## Envoyer des signaux
|
||||||
|
|
||||||
|
Des signaux peuvent être envoyés à d'autres processus avec `kill()` ou au
|
||||||
|
processus en cours avec `raise()`.
|
||||||
|
|
||||||
|
```C
|
||||||
|
include <signal.h>
|
||||||
|
|
||||||
|
int kill(pid_t pid, int sig);
|
||||||
|
int raise(int sig);
|
||||||
|
```
|
||||||
|
|
||||||
|
Ces deux fonctions renvoient 0 en cas de succès, sinon -1.
|
||||||
|
|
||||||
|
Il est aussi possible de bloquer le processus courant et d'attendre un signal
|
||||||
|
avec la fonction `pause()`
|
||||||
|
|
||||||
|
```C
|
||||||
|
int pause(void);
|
||||||
|
```
|
||||||
|
|
||||||
|
En cas d'erreur, retourne -1 avec errno positionné à *EINTR*
|
||||||
|
|
||||||
|
## Poser une alarme
|
||||||
|
|
||||||
|
Un processus peut définir une alarme qui aboutira à l'envoi d'un signal
|
||||||
|
*SIGALRM* au bout d'un temps défini. Il n'est cependant possible de ne définir
|
||||||
|
qu'une seule alarme par processus.
|
||||||
|
|
||||||
|
```C
|
||||||
|
#include <unistd.h>
|
||||||
|
|
||||||
|
unsigned int alarm(unsigned int seconds);
|
||||||
|
```
|
||||||
|
|
||||||
|
Il est aussi possible d'annuler une alarme précédemment définir avec
|
||||||
|
`alarm(0)`.
|
||||||
|
|
||||||
|
### Bibliographie
|
||||||
|
|
||||||
|
[Présentation][f_pres] support de cours
|
||||||
|
|
||||||
|
[f_pres]:files/presentation.pdf
|
Before Width: | Height: | Size: 29 KiB After Width: | Height: | Size: 29 KiB |
Before Width: | Height: | Size: 23 KiB After Width: | Height: | Size: 23 KiB |
Before Width: | Height: | Size: 18 KiB After Width: | Height: | Size: 18 KiB |
Before Width: | Height: | Size: 18 KiB After Width: | Height: | Size: 18 KiB |
Before Width: | Height: | Size: 125 KiB After Width: | Height: | Size: 125 KiB |
51
content/reseau/5_distibution-ip/index.md
Normal file
|
@ -0,0 +1,51 @@
|
||||||
|
---
|
||||||
|
title : " Distribution d'adresses IP"
|
||||||
|
date : 2018-10-08
|
||||||
|
categories : ["Réseau", "cours"]
|
||||||
|
tags : ["IP", "IPv4", "IPv6", "DHCP"]
|
||||||
|
----
|
||||||
|
|
||||||
|
## Distribuer des adresses IP dans un réseau
|
||||||
|
|
||||||
|
Dans le cadre d'un réseau informmatique, il existe trois manières de distribuer
|
||||||
|
des adresse IP :
|
||||||
|
|
||||||
|
* une approche statique
|
||||||
|
* une approche dynamique
|
||||||
|
* une approche automatique
|
||||||
|
|
||||||
|
### L'approche statique
|
||||||
|
|
||||||
|
On ne s'attardera pas ici sur l'approche statique qui consiste en l'assignation
|
||||||
|
et la confitugation manuelle de la couche IP sur l'ensemble des postes.
|
||||||
|
|
||||||
|
### L'approche dynamique (DHCP)
|
||||||
|
|
||||||
|
Un serveur fourni les adresses IP aux différents clients avec une durée de vie
|
||||||
|
définie (en général de 24h). Le protocole DHCP permet de fournir d'autres
|
||||||
|
information comme les serveurs DNS, le nom d'hôte, les serveurs d'impression, de
|
||||||
|
temps etc.
|
||||||
|
|
||||||
|
###L'approche automatique
|
||||||
|
|
||||||
|
Les machines du réseau se "mettent d'accord". C'est un fonctionnement naturel
|
||||||
|
en IPv6 "backporté" en IPv4. Les adresse IP attribués sont dans la plage
|
||||||
|
169.254.0.0/16 et fe80::0/64. En IPv6, les routeurs peuvent faire du *Router
|
||||||
|
Advertisement* : chaque routeur averti les machines connectées du réseau qu'il
|
||||||
|
gère, par exemple 2001:911:4::/64.
|
||||||
|
|
||||||
|
## L'attribution des adresse IP
|
||||||
|
|
||||||
|
C'est l'IANA *Internet Assigned Numbers Authority* aui qssigne les adresse IP
|
||||||
|
publiques. L'IANA alloue des blocs IP au [RIR *Registre Internet
|
||||||
|
Régionaux*][l_lir] qui les découpent et les attibuent aux LIR *Local Internet
|
||||||
|
Regitery* qui les rnds disponibles aux utilisateurs finaux.
|
||||||
|
|
||||||
|
Les attributions sont enregistrées dans la base de donnée [*Whois*][l_whois]
|
||||||
|
|
||||||
|
En IPv4, les adresses sont en passe d'être épuisée. Il n'y en a plus de
|
||||||
|
disponible aux États-Unis par exemple. De par le fait un marché noir de l'IPv4
|
||||||
|
se dévellope.
|
||||||
|
|
||||||
|
[l_lir]:https://fr.wikipedia.org/wiki/Registre_Internet_r%C3%A9gional
|
||||||
|
[l_whois]:https://fr.wikipedia.org/wiki/Whois
|