J'ai peu de questions liées à lire () / préad () appels système dans un environnement multithreadé p>
J'utilise Mac-OSX qui est FreeBSD basé, si cela aide de quelque manière que ce soit Je n'utilise que ce fichier en mode lecture et je ne lis pas / écrire Et la langue est C / C ++ P>
Supposons que nous ayons un fichier sur disque AAAABBBBCCCCDDDEEEEE ... P>
et 4 alphabets correspondent sur une page du fichier p>
alors Page1: AAAA P>
page2: BBBB ..... et ainsi de suite sur p>
Maintenant, j'en initie un appel de système de lecture de deux threads différents avec le même descripteur de fichier Mon intensation est de lire la première page du fil 1, deuxième page du fil 2, etc. p>
lire (fd, buff, taille de (page)); p>
de la page d'homme que je suis donné pour comprendre que lire sera également incrémenter le pointeur de fichier, donc je vais certainement avoir des réponses brouillées comme p>
ABCC ABBB .. etc. (sans séquence particulière) p>
Pour remédier à ce que je peux utiliser PRADA () P>
"PRADA () effectue la même fonction, mais se lit auprès de la spécification position fiée dans le fichier sans modifier le pointeur de fichier "// des pages man p>
Mais je ne suis pas sûr de savoir si l'utilisation de PRADA m'aidera réellement dans mon objectif, car elle ne peut pas incrémenter le pointeur de fichiers interne, il n'y a pas de garantie que les réponses ne sont pas cognées. P>
Toutes mes données sont alignées sur une page et je souhaite lire une page de chaque fil comme p>
thread 1 lit: aaaa Fil 2 Reads: BBBB Le fil 3 se lit comme suit: CCCC ... sans faire de la teneur en réalité. P>
J'ai aussi trouvé un message Est-il sûr de lire () à partir d'un fichier dès que Write () renvoie? P>
Mais ce n'était pas très utile. p>
Je ne suis pas sûr que je ne suis pas sûr de savoir si lire () aura le problème, que je pense que le dossier que je lis est un fichier binaire et que je suis donc limité difficile à lire et à vérifier manuellement. p>
Toute aide sera appréciée p>
3 Réponses :
Partagez un verrou de mutex entre les deux threads, actionnez le verrou dans le fil avant de se lit et déverrouillez le verrou lorsque la lecture correcte est terminée. Voir pthread_mutex_create code>,
pthread_mutex_lock code> et
pthread_mutex_unlock code>. P>.
C'est un remède mais il limitera les E / S à un seul fil, je ne veux pas faire cela car je ne suis intéressé que par la lecture, et pas lire-écrire
Je ne pense pas que tu le fais sans bloquer un fil sur les E / S. De plus, si vous ne bloquez que pendant la lecture simple, et non la totalité de l'exécution du fil, l'attente doit être minimale. La seule autre alternative consiste à ouvrir chaque fil d'ouvrir le fichier avec son propre descripteur de fichier, mais vous devrez savoir ce que chacun lit pour ignorer cette information. Cela ralentira également les threads comme il y aura deux fois plus d'E / S.
Ceci est inutile et non la réponse à la question de l'OP. L'ensemble du point de préad code> est de faire ce que veut OP, et la réponse est que oui c'est sûr.
Je n'étais pas au courant de ces fonctions. Je suppose que je n'ai jamais eu ce genre de besoin. Apprendre quelque chose de nouveau chaque jour. Le seul inconvénient, vous devez toujours être conscient de ce que le ou les autres threads traitent de sorte que vous ne doublechez pas.
D'autre part, lire code> et
écriture code> modifier la position du fichier ouvert sous-jacent. Ils sont "fil de fil" en ce sens que votre programme n'aura pas un comportement non défini (crash ou pire) si plusieurs threads exécutent IO sur le même fichier ouvert à la fois les utiliser, mais la commande et l'atomicité des opérations peuvent varier en fonction de la Type de fichier et la mise en œuvre. P>
préad code> et
Pwrite code> Ne modifiez pas la position dans le fichier ouvert. Ils ont été ajoutés à POSIX pour exactement le but que vous souhaitez: effectuer des opérations IO sur le même fichier ouvert à partir de plusieurs threads ou processus sans les opérations interférentes avec la position des autres. Vous pouvez toujours rencontrer des problèmes avec la commande si vous mélangez
préad code> et
pwrite code> (ou plusieurs appels vers
Pwrite code>) avec des parties qui se chevauchent de la Fichier, mais aussi longtemps que vous évitez cela, ils sont parfaitement sûrs pour ce que vous voulez faire. P>
Et ceci: pubs.opengroup.org/onlinepubs/9699919799/fonctions/... (XSH 2.9.7 Interactions de fil avec les opérations de fichier régulières).
fcntl code> Les serrures de conseil sont des verrous sur une plage em> du fichier. Vous pouvez trouver cela utile pour sérialiser des lectures et écrit dans la même région tout en laissant la concurrence sur les régions distinctes.
int rc;
struct flock f;
f.l_type = F_RDLCK; /* or F_WRLCK */
f.l_whence = SEEK_SET;
f.l_start = n;
f.l_len = 1;
while ((rc = fcntl(fd, F_SETLKW, &f)) == -1 && errno = EINTR)
;
if (rc == -1)
perror("fcntl(F_SETLKW)");
else {
/* do stuff */
f.l_type = F_UNLCK;
fcntl(fd, F_SETLK, &f);
}
Soyez averti que beaucoup de verrouillage de fichiers ne fonctionnent pas entre les threads, uniquement les processus. Je ne me souviens pas de FCNTL mais ne vous en faites pas confiance. Essaye-le.
FCNTL est en fait verrouillant entre les processus. Linux.die.net/man/2/fcntl Si vous utilisez Pthread, le La bibliothèque fournit pthread_rwlock_ * Fonctions qui implémentent le verrouillage en lecture / écriture de fil. Il ne fournit pas de verrouillage de la plage cependant, vous devrez écrire votre propre ...