Infotro/ptr (#23)
This commit is contained in:
8 files changed
+255
-7
No files matched your search
+248
-5
@@ -20,8 +20,8 @@ Cela permet d'éviter de bloquer toutes les applications lorsqu'une seule est en
|
|||||||
La programmation concurrente sur plusieurs CPU permet en plus un gain de temps.
|
La programmation concurrente sur plusieurs CPU permet en plus un gain de temps.
|
||||||
|
|
||||||
# Exclusion mutuelle
|
# Exclusion mutuelle
|
||||||
un programme est une entité statique
|
- un programme est une entité statique qui contient des processus
|
||||||
un processus est une entité dynamique
|
- un processus est une entité dynamique (il s'agit d'une tâche en cours d'exécution)
|
||||||
|
|
||||||
Les processus ne sont jamais totalement indépendants.
|
Les processus ne sont jamais totalement indépendants.
|
||||||
Ils partagent des ressources (mémoire, fichiers, périphériques, variable, etc.)
|
Ils partagent des ressources (mémoire, fichiers, périphériques, variable, etc.)
|
||||||
@@ -196,7 +196,7 @@ Sinon, **un** processus peut modifier la ressource et aucun peut lire.
|
|||||||
```cpp
|
```cpp
|
||||||
void BeginRead(void) {
|
void BeginRead(void) {
|
||||||
osSemaphoreAcquire(rw, osWaitForever);
|
osSemaphoreAcquire(rw, osWaitForever);
|
||||||
osSemaphoreAcquire(mutexNbReader, osWaitForever); // ENTER CRITICAL SECTION
|
osSemaphoreAcquire(mutexNbReader, osWaitForever); // ENTER CRITICAL SECTION
|
||||||
nbReader++;
|
nbReader++;
|
||||||
if(nbReader == 1) osSemaphoreAcquire(w, osWaitForever);
|
if(nbReader == 1) osSemaphoreAcquire(w, osWaitForever);
|
||||||
osSemaphoreRelease(mutexNbReader); // EXIT CRITICAL SECTION
|
osSemaphoreRelease(mutexNbReader); // EXIT CRITICAL SECTION
|
||||||
@@ -221,13 +221,98 @@ void EndWrite(void) {
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
# Coopération-Synchronisation
|
||||||
|
La coopération entre processus implique la synchronisation entre eux pour éviter de ressource.
|
||||||
|
|
||||||
|
## Évènement
|
||||||
|
L'évènement est un outil permettant de résoudre un problème de synchronisation comme les sémaphores ou les mutex.
|
||||||
|
On peut manipuler les évènements :
|
||||||
|
- ***Wait()*** : Attendre un évènement
|
||||||
|
- ***Signal()*** : Déclencher un évènement
|
||||||
|
- ***Init()*** : Initialiser un évènement
|
||||||
|
|
||||||
|
On peut aussi résoudre un problème de synchronisation entre processus avec un sémaphore initialisé à 0. On peut le comparer
|
||||||
|
à une barrière déclenchable depuis un autre processus.
|
||||||
|
|
||||||
# Synchronisation
|
Les sémaphores ne permettent pas de résoudre tous les problèmes de synchronisation. Trop grand risque de DEADLOCK.
|
||||||
|
Il faut utiliser d'autres outils plus performants.
|
||||||
|
|
||||||
|
## Le moniteur (monitor)
|
||||||
|
On peut l'imager avec une classe entièrement protégée par des sémaphores pour l'accès au variable et fonction (procédure).
|
||||||
|
|
||||||
Etat d'un processus :
|
Le moniteur possède comme primitive :
|
||||||
|
- ***x.wait*** : bloque le processus jusqu'à ce qu'un x.send soit émis.
|
||||||
|
- ***x.send*** : débloque le processus qui attend sur un x.wait.
|
||||||
|
|
||||||
|
```pascal
|
||||||
|
monitor M;
|
||||||
|
defines DepositeChar, TakeChar;
|
||||||
|
|
||||||
|
var
|
||||||
|
c : char;
|
||||||
|
chAvailable : boolean;
|
||||||
|
x : signal;
|
||||||
|
|
||||||
|
procedure TakeChar(var ch:char);
|
||||||
|
begin
|
||||||
|
if not chAvailable then x.wait end if;
|
||||||
|
ch := c;
|
||||||
|
chAvailable := FALSE
|
||||||
|
end TakeChar;
|
||||||
|
|
||||||
|
procedure DepositeChar(ch:char);
|
||||||
|
begin
|
||||||
|
c := ch;
|
||||||
|
chAvailable := TRUE;
|
||||||
|
x.send
|
||||||
|
end DepositeChar;
|
||||||
|
|
||||||
|
begin
|
||||||
|
chAvailable := FALSE
|
||||||
|
end M;
|
||||||
|
```
|
||||||
|
```pascal
|
||||||
|
process Keyboard;
|
||||||
|
uses M;
|
||||||
|
var cRead: char;
|
||||||
|
begin
|
||||||
|
...
|
||||||
|
Read a character on keyboard
|
||||||
|
Put it in the cRead variable
|
||||||
|
M.DepositeChar(cRead);
|
||||||
|
...
|
||||||
|
end Keyboard;
|
||||||
|
|
||||||
|
process Screen;
|
||||||
|
uses M;
|
||||||
|
var cWrite: char;
|
||||||
|
begin
|
||||||
|
...
|
||||||
|
M.TakeChar(cWrite);
|
||||||
|
Write the character cWrite on the screen
|
||||||
|
...
|
||||||
|
end Screen;
|
||||||
|
```
|
||||||
|
|
||||||
|
## Producteurs / consommateurs
|
||||||
|
Le problème survient lorsque le producteur envoie un message au consommateur via une queue.
|
||||||
|
[Example](https://git.kb28.ch/Klagarge/PTR-Queue/src/branch/master/main.c)
|
||||||
|
|
||||||
|
- ***Le producteur*** (Producer) doit être mis en attente s'il veut déposer un message alors que le tampon est plein
|
||||||
|
- ***Le consommateur*** (Consumer) doit être mis en attente s'il veut prélever un message alors que le tampon est vide
|
||||||
|
- ***Le producteur*** (Producer) en attente doit être débloqué dès que le consommateur (Consumer) prélève un message
|
||||||
|
- à ce moment le tampon n'est plus plein
|
||||||
|
- ***Le consommateur*** (Consumer) en attente doit être débloqué dès que le producteur (Producer) dépose un message
|
||||||
|
- à ce moment le tampon n'est plus vide
|
||||||
|
|
||||||
|
On peut résoudre aisément le problème producteurs-consommateurs avec un moniteur ainsi qu'avec un sémaphore.
|
||||||
|
|
||||||
|
<b><u>Solution à chier :</u></b><br>
|
||||||
|
Le producteur attend que le consommateur soit capable de réceptionner le message, ainsi les deux peuvent
|
||||||
|
continuer leurs exécutions (principe de rendez-vous). Ce concept ne possède pas de buffer.
|
||||||
|
|
||||||
|
# Allocation processeur
|
||||||
|
État d'un processus :
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
@@ -238,3 +323,161 @@ contiennent le registre de status et un pointeur sur sa stack. Ils sont utilisé
|
|||||||
3. Il va prendre le descripteur du prochain processus et utiliser ses registres.
|
3. Il va prendre le descripteur du prochain processus et utiliser ses registres.
|
||||||
4. Le processus continue jusqu'au nouveau switching context.
|
4. Le processus continue jusqu'au nouveau switching context.
|
||||||
|
|
||||||
|
## Cycle processeur
|
||||||
|
Un processeur réalise alternativement une suite de :
|
||||||
|
- ***Cycles processeur*** (CPU burst cycle)
|
||||||
|
- ***Cycles d'entrée-sortie*** (I/O burst cycle)
|
||||||
|
|
||||||
|
Lorsque le temps de cycle processeur est petit et qu'il y a une attente engendrée par les entrées-sorties, il est pertinent de partager
|
||||||
|
le processeur entre plusieurs processus.
|
||||||
|
|
||||||
|
## Queues d'ordonnancement
|
||||||
|
Les processus en attente du processeur sont placés dans une liste appelée **queue de processus prêts** (ready queue).
|
||||||
|
Cette queue peut être gérée comme une file FIFO, une liste de priorité, un arbre, une pile, une liste non-ordonnée, etc.
|
||||||
|
|
||||||
|
Cette queue est sous forme d'une liste chaînée qui contient des pointeurs sur les descripteurs de processus.
|
||||||
|
Les processus qui ont besoins d'une ressource sont placés dans une liste d'attente correspondant à la ressource (mutex/sémaphore).
|
||||||
|
|
||||||
|
L'ensemble des queues peut être regroupé dans le diagramme de synthèse suivant :
|
||||||
|

|
||||||
|
|
||||||
|
|
||||||
|
## Ordonnanceurs
|
||||||
|

|
||||||
|
|
||||||
|
### Ordonnanceur à court terme
|
||||||
|
- Sélectionne un nouveau processus toutes les millisecondes.
|
||||||
|
- Doit être très rapide
|
||||||
|
- Est très simple
|
||||||
|
|
||||||
|
### Ordonnanceur à long terme
|
||||||
|
- Contrôle le degré de multiprogrammation, c'est-à-dire, le nombre de processus en mémoire.
|
||||||
|
- Assure que la charge globale du processeur soit répartie équitablement entre les processus réalisant beaucoup d'entrée-sorties et les
|
||||||
|
processus réalisant beaucoup de calculs.
|
||||||
|
- S'exécute peu fréquement
|
||||||
|
- La complexité de ce dernier augmente fortement.
|
||||||
|
|
||||||
|
### Le swapping
|
||||||
|
On peut augmenter la RAM avec de la mémoire virtuelle (swap) pour garder les processus et ne pas les mettre en stockage
|
||||||
|
long termes.
|
||||||
|
|
||||||
|
### Distributeur de tâches
|
||||||
|
Il distribue au processeur les processus sélectionnés par l'ordonnanceur court terme.
|
||||||
|
- Il charge les registres du processus sélectionné
|
||||||
|
- Il change en mode utilisateur depuis le superviseur. Ce dernier servant à modifier les registres.
|
||||||
|
- Il met à jour le PC
|
||||||
|
|
||||||
|
## Critères de performance
|
||||||
|
- ***Efficacité** (CPU utilisation) : Taux d'utilisation du processus
|
||||||
|
- ***Débit*** (troughtput) : Nombre de processus par unité de temps
|
||||||
|
- ***Temps global*** (turnaround time) : Temps qui s'écoule entre la soumission du processus et la fin de son exécution
|
||||||
|
- ***Temps d'attente*** (waiting time) : Temps d'attente d'un processus dans la queue des processus prêts
|
||||||
|
- ***Temps de réponse*** (response time) : intervalle de temps entre l'heure de soumission et l'heure de la première réponse
|
||||||
|
|
||||||
|
## Algorithme d'ordonnancement
|
||||||
|
L'allocateur du processeur doit sélectionner quels processus situés dans la queue des processeurs prêts doivent recevoir le processeur.
|
||||||
|
|
||||||
|
### FIFO
|
||||||
|
L'algorithme FIFO est le plus simple. Il sélectionne le premier processus de la queue des processus prêts. Mais, il n'est
|
||||||
|
pas forcément le plus efficace.
|
||||||
|
|
||||||
|
### Le plus court d'abord
|
||||||
|
Le processus avec la plus petite suite d'instruction est exécuté en premier. Si deux processus ont le même nombre d'instructions,
|
||||||
|
on peut utiliser un algorithme FIFO pour déterminer le vainqueur. Il est performant, mais c'est compliqué de connaître
|
||||||
|
le nombre d'instructions.
|
||||||
|
|
||||||
|
Il nécessite d'éstimer en temps réel la longueur du processus.
|
||||||
|
|
||||||
|
$$\tau_{n+1} = \alpha\cdot t_{n}+(1-\alpha)\cdot \tau_{n}$$ <br>
|
||||||
|
$\tau_{n+1}$ : prochaine valeur estimée <br>
|
||||||
|
$\alpha$ : coefficient de pondération $0\leq\alpha\leq 1$ <br>
|
||||||
|
$t_{n}$ : valeur mesurée à l'instant $n$ <br>
|
||||||
|
$\tau_{n}$ précédente valeur estimée pour l'instant $n$ <br>
|
||||||
|
|
||||||
|
### Priorité
|
||||||
|
Cet algorithme donne au processeur le processus qui a la plus haute priorité qui est défini par l'utilisateur.
|
||||||
|
On peut rencontrer plusieurs problèmes :
|
||||||
|
- ***Blocage indéfini*** (indefinite blocking) : on reste bloqué dans un processus de haute priorité.
|
||||||
|
- ***Famine*** (starvation) : Les processus de basse priorité ne sont jamais exécuté.
|
||||||
|
|
||||||
|
***Solution*** : On augmente la priorité dum processus en attente tous les quantums de temps.
|
||||||
|
|
||||||
|
### Ordonnancement avec réquisition (preemptive)
|
||||||
|
On réévalue l'ordre des processus dans la queue à chaque tick et le processus élu prend ou garde le processeur.
|
||||||
|
|
||||||
|
### Tourniquet (round-robin)
|
||||||
|
Il est basé sur une tranche de temps fixe soit quantum de temps. On donne à chacun des processus ce temps et on passe au
|
||||||
|
processus suivant une fois le temps écoulé.
|
||||||
|
Lorsque le temps est grand, on retrouve en quelque sorte une FIFO, car le temps d'exécution des processus est plus court que
|
||||||
|
le quantum de temps.
|
||||||
|
Si le temps est très petit, le tourniquet est appelé **processeur partagé** (processor sharing).
|
||||||
|
|
||||||
|
<b><u>Overhead</u></b> : temps perdu pour changer de processus.<br>
|
||||||
|
|
||||||
|
### Files multiples (multi-queue)
|
||||||
|
On utilise cette technique lorsqu'on peut facilement classer les processus en différents groupes. Chaque queue possède son
|
||||||
|
propre algorithme d'ordonnancement. Un ordonnancement entre les queues est réalisé soit par priorité et réquisition, soit
|
||||||
|
en round robin.
|
||||||
|
|
||||||
|
### Files multiples imbriquées (multi-level feedback queue)
|
||||||
|
Cette technique permet aux processus d'évoluer dans des queues en fonction du temps d'exécution écoulé.
|
||||||
|
- Un processus entrant dans la queue des processus prêts est placé dans la queue 0
|
||||||
|
- Si le quantum est écoulé et que la suite d’instruction processeur n’est pas terminée, le processus est placé dans
|
||||||
|
la queue de priorité inférieure
|
||||||
|
|
||||||
|
Plus on descend dans les queues, plus on est de priorité basse.
|
||||||
|
|
||||||
|
<u>Exemple :</u> Plus on descend dans les queues, plus le quantum devient grand.
|
||||||
|
|
||||||
|
# Interblocage (DEADLOCK)
|
||||||
|
Un processus attend indéfiniment pour accéder à une ressource bloquée.
|
||||||
|
|
||||||
|
L'interblocage apparaît si les 4 conditions apparaissent simultanément :
|
||||||
|
1. ***L'exclusion mutuelle*** (mutual exclusion) : Une ressource au minimum n'est pas partageable.
|
||||||
|
2. ***La détention et l'attente*** (hold and wait) : Un processus qui dispose déjà d'au moins une ressource et qui attend l'acquisistion
|
||||||
|
d'une nouvelle ressource déjà utilisée par un autre processus.
|
||||||
|
3. ***Pas de réquisition*** (no preemption) : Les ressources obtenues par un processus ne peuvent pas lui être retirées contre son gré
|
||||||
|
4. ***L'attente circulaire*** (circulare wait) : Il doit y avoir un cycle d'au moins deux processus, chacun d'entre eux attendant
|
||||||
|
une ressource détenue par un autre processus du cycle.
|
||||||
|
|
||||||
|
Les interblocages peuvent être décrits plus précisément en utilsant un graphe appelé **graphe
|
||||||
|
d'allocation des ressources** (ressource allocation graph).
|
||||||
|

|
||||||
|
- Si le graphe d'allocation des ressources ne contient aucun cycle $=>$ Aucun processus n'est en interblocage
|
||||||
|
- Si le graphe d'allocation des ressources contient un cycle $=>$ <u>Un risque</u> d'interblocage existe !!
|
||||||
|
|
||||||
|
On peut faire une réduction de graphe pour observer l'état suivant du graphe :
|
||||||
|
- Un graphe peut être réduit par un processus Pi, si le processus n'a pas de demande de ressource en cours.
|
||||||
|
- Pour faire une réduction, on enlève toutes les allocations du processus.
|
||||||
|
|
||||||
|
***Complètement réductible*** : si on arrive à faire des réductions successives jusqu'à ce qu'il n'y a plus de flêches
|
||||||
|
dans le graphe.
|
||||||
|
|
||||||
|
On peut résoudre le problème d'interblocage :
|
||||||
|
- ***Prévention*** : On garantit qu'aucun interblocage ne peut se produire.
|
||||||
|
- ***Prévenir** : Empêcher une des 4 conditions de se produire
|
||||||
|
- ***Éviter** : Éviter dynamiquement en allouant les ressource avec précaution
|
||||||
|
- ***Détection ou guérison*** : Lorsqu'un interblocage est détecté, on ramène le système dans un état où les processus sont débloqués
|
||||||
|
|
||||||
|
En cas d'interblocage, on peut utiliser deux algorithmes pour résoudre ce problème.
|
||||||
|
L'algorithme du banquier pour la prévention et ensuite un algorithme de reprise après interblocage.
|
||||||
|
|
||||||
|
L'algorithme de reprise fait soit appel à l'aide d'un opérateur, soit par une séquence automatique
|
||||||
|
qui tue les processus impliqués dans l'interblocage, soit un processus après l'autre jusqu'à ce que l'interblocage soit résolu.
|
||||||
|
Mais la destruction de processus est complexe et dangereuse.
|
||||||
|
|
||||||
|
## Algorithme du banquier (banker's algorithm)
|
||||||
|
Cette technique impose de connaître pour chaque processus les ressources dont il aura besoin.
|
||||||
|
- Il vérifie avant d'allouer une ressource que le graphe reste complètement réductible.
|
||||||
|
- Il alloue une ressource uniquement s'il y a plus de ressources disponibles que demandées.
|
||||||
|
- Sinon la demande de ressource est mise en attente.
|
||||||
|
|
||||||
|
|
||||||
|
<b><u>Exemple :</u></b><br>
|
||||||
|

|
||||||
|

|
||||||
|
|
||||||
|
Une ressource n'est attribuée que si les ressources demandées sont inférieurs aux ressources disponibles.
|
||||||
|
$$ (N)Needed < (A)Available $$
|
||||||
|
|
||||||
|
Si aucune rangée (processus) ne satisfait la condition, il y a <u><b>interblocage</b></u>.
|
||||||
@@ -23,6 +23,11 @@ les quantités sont modérées, le processeur est intensément utilisé, et ces
|
|||||||
4. Souvent utilisé dans des applications où une flexibilité est nécessaire, mais peut poser des défis dans les systèmes où la prédictibilité est cruciale.
|
4. Souvent utilisé dans des applications où une flexibilité est nécessaire, mais peut poser des défis dans les systèmes où la prédictibilité est cruciale.
|
||||||
5. La gestion de l'incertitude et l'adaptabilité aux conditions changeantes sont des caractéristiques clés des systèmes non-déterministes.
|
5. La gestion de l'incertitude et l'adaptabilité aux conditions changeantes sont des caractéristiques clés des systèmes non-déterministes.
|
||||||
|
|
||||||
|
### Système temps réel
|
||||||
|
- ***Temps réel dur:*** Le systéme fait une erreur si le délai est dépassé.
|
||||||
|
- ***Temps réel souple:*** Le système accepte le dépassement du délai sans grave conséquence.
|
||||||
|
- ***Temps réel ferme:*** Le système accepte le dépassement du délai, mais le résultat n'est plus d'aucune utilité.
|
||||||
|
|
||||||
|
|
||||||
### Management du temps (Timing)
|
### Management du temps (Timing)
|
||||||
Le timing peut avoir principalement deux formes différentes :
|
Le timing peut avoir principalement deux formes différentes :
|
||||||
|
|||||||
+2
-2
@@ -4,7 +4,7 @@ Introduction aux systèmes d'exploitation
|
|||||||
|
|
||||||

|

|
||||||
|
|
||||||
Le système d'expoitation virtualise la partie hardward pour :
|
Le système d'exploitation virtualise la partie hardware pour :
|
||||||
- Simplifie l'utilisation
|
- Simplifie l'utilisation
|
||||||
- Gère les ressources physiques
|
- Gère les ressources physiques
|
||||||
- Processeur
|
- Processeur
|
||||||
@@ -67,7 +67,7 @@ programme est exécuté afin d'optimiser l'utilisation du processeur.
|
|||||||
|
|
||||||
La commutation de l'exécution d'un programme à un autre est assuré par l'**ordonnanceur** (scheduler).
|
La commutation de l'exécution d'un programme à un autre est assuré par l'**ordonnanceur** (scheduler).
|
||||||
|
|
||||||
*Inconvénients :* Les programmes cours, sont pénalisés car leur temps d'exécution dépend aussi des autres
|
*Inconvénients :* Les programmes cours, sont pénalisés, car leur temps d'exécution dépend aussi des autres
|
||||||
programmes en cours d'exécution.
|
programmes en cours d'exécution.
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Binary file not shown.
|
After Width: | Height: | Size: 101 KiB |
Binary file not shown.
|
After Width: | Height: | Size: 56 KiB |
Binary file not shown.
|
After Width: | Height: | Size: 51 KiB |
Binary file not shown.
|
After Width: | Height: | Size: 30 KiB |
Binary file not shown.
|
After Width: | Height: | Size: 37 KiB |
Reference in new issue
Block a user