J'ai un processus hautement prioritaire qui doit adopter des données à un processus à faible priorité. J'ai écrit un tampon de bague de base pour gérer le passage des données: Voici le problème. Supposons que le processus de faible priorité ait un oracle qui lui indique exactement la quantité de données à lire, de sorte que Je pourrais mettre un mutex autour des accès au début et à la fin, mais cela causerait une inversion prioritaire si le fil de haute priorité a Attendre la serrure acquise par le fil à faible priorité. P> Je pourrais peut-être travailler quelque chose à l'aide d'opérations atomiques, mais je ne suis pas au courant d'une belle bibliothèque multiplate-forme qui les fournisse. P> Y a-t-il une conception tampon standard qui évite ces problèmes? P> P> compte () code> ne soit jamais appelé. Ensuite (sauf si je manque quelque chose), il n'y a pas de problèmes de concurrence. Cependant, dès que le fil à faible priorité doit appeler
compter () code> (le thread de haute priorité pourrait vouloir l'appeler aussi pour vérifier si le tampon est trop complet) Il y a la possibilité que le maths in comptez () ou la mise à jour à la fin n'est pas atomique, introduisant un bug. p>
3 Réponses :
Ce que vous avez devrait être correct, tant que vous adhérez à ces directives: P>
Démarrer code> et fin code> sont atomiques. Cela pourrait être automatique, par exemple Microsoft States: Li>
ul>
simple lit et écrit à
Les variables 32 bits correctement alignées sont
Opérations atomiques. En d'autres termes, vous
ne finira pas avec une seule partie
de la variable mise à jour; Tous les bits sont
mis à jour sous une mode atomique. P>
blockQuote>
- Vous permettez au fait que
comptent code> pourrait être obsolète, même si vous obtenez la valeur. Dans le fil de lecture, comptage code> retournera le nombre minimum em> em> que vous puissiez compter sur; Pour le thread d'écriture comptage code> retournera le nombre em> maximum em> et que le décompte véritable pourrait être plus bas. LI>
ul>
Existe-t-il un risque de compilation des mises à jour dans une séquence non atomique d'étapes? C'est-à-dire tourner la dernière ligne d'écriture () dans fin + = octets; fin% = taille; code>?
Le compilateur peut calculer le RHS non atomique et en fonction de votre plate-forme pourrait même stocker un int sans atomique (c'est-à-dire de stocker un Int 16 bits à l'aide de deux écrives de 8 bits sur une plate-forme 8 bits).
@ user168715, si vous ne faites absolument pas confiance à votre compilateur pour faire la bonne chose, créez une variable de code code> Volatile code> pour contenir le calcul, puis copiez-le pour la mise à jour.
Boost fournit un tampon circulaire, mais ce n'est pas le fil sûr. Malheureusement, je ne connais aucune mise en œuvre qui est. P>
Le prochain standard C ++ ajoute des opérations atomiques à la bibliothèque standard, de sorte qu'ils seront disponibles à l'avenir, mais ils ne sont pas encore pris en charge par la plupart des implémentations. P>
Je ne vois aucune solution croisée pour garder Normalement, vous utiliseriez probablement un système de messagerie et forcez le fil de la priorité faible pour demander que le thread de priorité élevée effectue des mises à jour ou quelque chose de similaire. Par exemple, si le fil à faible priorité consomme 15 octets, il devrait demander au fil hautement prioritaire de réduire le nombre de 15. P>
essentiellement, vous limiteriez l'accès «Écrivez» au fil de priorité élevée et permettez uniquement au fil de la priorité faible. De cette façon, vous pouvez éviter tout verrouillage et le thread de priorité élevée n'aura pas à vous soucier d'attendre que l'écriture soit remplie par le fil inférieur, rendant la priorité très prioritaire de la priorité. P> compter code> sain d'esprit tandis que les deux threads y écrivent, à moins que vous n'ayez implémenter le verrouillage. p>
boost :: interprocession code> offre des fonctions atomiques multiplateformes dans
boost / interprocessation / détail / atomic.hpp code> p> P>
Avez-vous des contraintes sur les plates-formes utilisées?
@Peter Supposons X86 (où EIRC 32 bits écrit aux adresses alignées sont atomiques) bien que le plus portable mieux.
Voici une file d'attente qui fonctionne principalement logiciel .Intel.com / FR-US / Articles / ...