Fonctionnement du buffer circulaire

Le buffer circulaire fonctionne avec deux indices, read_index et write_index. Il faut le voir comme une bande qui boucle sur elle-même :

   read_index         write_index
       |                   |
       v                   v
WWWWWW.rrrrrrrrrrrrrrrrrrrrWWWWWW  => retour au début

Tout ce qui est marqué r, de read_index à write_index (non compris), représente une donnée présente dans le buffer qui peut être lue. Cela signifie que si read_index == write_index alors il n'y a rien à lire.

Tout ce qui est marqué W, de write_index à read_index - 1 (non compris), est un espace dans lequel il est possible d'écrire. Si write_index == read_index - 1 (modulo la capacité du buffer), il n'y a plus de place pour écrire.

L'endroit marqué . ne peut pas être utilisé car si on y écrivait sans rien lire entre temps on aurait read_index == write_index ce qui serait compris comme un buffer vide. On peut donc stocker jusqu'à capacity - 1 valeurs dans notre buffer circulaire à un moment donné.

Votre travail

Les champs read_index et write_index, qui sont des AtomicUsize, sont les seuls points de synchronisation entre le lecteur et l'écrivain. C'est à travers ces deux champs et les modes d'écriture atomique qu'on sera sûr de lire une donnée dont l'écriture est bien visible dans le thread qui lit et qu'on sera sûr d'écrire à un endroit qui ne contient plus rien d'utile dans le thread qui écrit.