plusieurs threads en mesure d'obtenir troupeau en même temps
J'étais sous l'impression que flock(2) est thread-safe, j'ai récemment couru à travers le cas dans le code, où plusieurs threads sont en mesure d'obtenir un verrou sur le même fichier qui sont tous synchronisés avec l'utilisation de l'obtention exclusif de verrouillage à l'aide de l'api c troupeau. Le processus 25554 est multi-thread application qui dispose de 20 threads, le nombre de threads avoir de verrouillage vers le même fichier varie lorsque le blocage se produit. Le multithread application testEvent est scénariste pour le fichier, où était le push est le reader à partir du fichier. Malheureusement, le lsof
ne pas imprimer le LWP valeur donc je ne peux pas trouver qui sont les fils qui sont maintenant le verrou. Lorsque le dessous de la condition se produit à la fois le processus et les threads sont bloqués sur le troupeau d'appel affiché par le pstack
ou strace
appel sur le pid 25569 et 25554. Toutes les suggestions sur la façon de surmonter ce dans RHEL 4.x.
Une chose que je voulais mettre à jour est troupeau ne pas se conduisent mal tout le temps, quand le tx rate des messages de plus de 2 mbit /s seulement, puis-je obtenir dans cette impasse problème avec le troupeau, ci-dessous qui tx rate tout est fichier. J'ai gardé la num_threads
= 20, size_of_msg
= 1000bytes constante et juste varier le nombre de messages tx par seconde commencer à partir de 10 messages à 100 messages qui est 20*1000*100 = 2 mbit /s, lorsque j'augmente le nombre de messages à 150 puis troupeau problème se produit.
Je voulais juste vous demander quelle est votre opinion sur flockfile c api.
sudo lsof filename.txt
COMMAND PID USER FD TYPE DEVICE SIZE NODE NAME
push 25569 root 11u REG 253.4 1079 49266853 filename.txt
testEvent 25554 root 27uW REG 253.4 1079 49266853 filename.txt
testEvent 25554 root 28uW REG 253.4 1079 49266853 filename.txt
testEvent 25554 root 29uW REG 253.4 1079 49266853 filename.txt
testEvent 25554 root 30uW REG 253.4 1079 49266853 filename.txt
Le multithread programme de test qui va appeler le write_data_lib_func
lib fonction.
void* sendMessage(void *arg) {
int* numOfMessagesPerSecond = (int*) arg;
std::cout <<" Executing p thread id " << pthread_self() << std::endl;
while(!terminateTest) {
Record *er1 = Record::create();
er1.setDate("some data");
for(int i = 0 ; i <=*numOfMessagesPerSecond ; i++){
ec = _write_data_lib_func(*er1);
if( ec != SUCCESS) {
std::cout << "write was not successful" << std::endl;
}
}
delete er1;
sleep(1);
}
return NULL;
La méthode ci-dessus sera appelée dans le pthreads dans la fonction principale de l'essai.
for (i=0; i<_numThreads ; ++i) {
rc = pthread_create(&threads[i], NULL, sendMessage, (void *)&_num_msgs);
assert(0 == rc);
}
Ici est l'écrivain/lecteur source, à cause des raisons que je ne voulais pas juste couper et coller, l'auteur de la source d'accès à plusieurs threads d'un processus
int write_data_lib_func(Record * rec) {
if(fd == -1 ) {
fd = open(fn,O_RDWR| O_CREAT | O_APPEND, 0666);
}
if ( fd >= 0 ) {
/* some code */
if( flock(fd, LOCK_EX) < 0 ) {
print "some error message";
}
else {
if( maxfilesize) {
off_t len = lseek ( fd,0,SEEK_END);
...
...
ftruncate( fd,0);
...
lseek(fd,0,SEEK_SET);
} /* end of max spool size */
if( writev(fd,rec) < 0 ) {
print "some error message" ;
}
if(flock(fd,LOCK_UN) < 0 ) {
print some error message;
}
Dans le lecteur côté des choses, c'est un processus démon sans fils.
int readData() {
while(true) {
if( fd == -1 ) {
fd= open (filename,O_RDWR);
}
if( flock (fd, LOCK_EX) < 0 ) {
print "some error message";
break;
}
if( n = read(fd,readBuf,readBufSize)) < 0 ) {
print "some error message" ;
break;
}
if( off < n ) {
if ( off <= 0 && n > 0 ) {
corrupt_file = true;
}
if ( lseek(fd, off-n, SEEK_CUR) < 0 ) {
print "some error message";
}
if( corrupt_spool ) {
if (ftruncate(fd,0) < 0 ) {
print "some error message";
break;
}
}
}
if( flock(fd, LOCK_UN) < 0 )
print some error message ;
}
}
}
flock
? simple programme de test, ce serait bien.Autant que je sache, les verrous Consultatifs ne garantit pas la cohérence. gsp.com/cgi-bin/man.cgi?section=2&rubrique=troupeau
OriginalL'auteur user1235176 | 2012-02-27
Vous devez vous connecter pour publier un commentaire.
flock(2) est décrite comme un "blocage si une incompatibilité de verrou est détenu par un autre processus"
et avec "les verrous créés par flock() sont associés à un fichier ouvert en entrée de la table", il devrait donc s'attendre à ce que
flock
-ed serrures par plusieurs threads du même processus n'interagissent pas.(
flock
la documentation ne mentionne pas les threads).Par conséquent, la solution doit être simple pour vous: pour associer une
pthread_mutex_t
à chaqueflock
-mesure descripteur de fichier, et de protéger l'appel àflock
avec ce mutex. Vous pouvez également utiliser pthread_rwlock_t si vous voulez une lecture vs écrire de verrouillage.J'ai maintenant ajouté la source.
merci pour votre réponse, j'en suis sûr, a été pensée dans la même ligne d'associer un mutex avec le troupeau, ce qui a été me tracasse était troupeau(2) se trouve sur le dessus de fcntl(2), et fcntl(2) lockf(2) ont affirmé thread-safe, donc c'était une surprise pour moi que ce ne l'est pas.
J'ai essayé cette suggestion pour l'instant, il est pthread_mutex_t pour synchroniser le troupeau des appels, maintenant ce qui se passe est de 19, les threads sont bloqués sur essayer d'obtenir de la pthread_mutex_t et 1 fil ne parvient pas à obtenir le verrou exclusif sur le fichier à l'aide du troupeau, et il est coincé sur la ligne de troupeau(fd,LOCK_EX);
et ce errno que vous obtenez de troupeau qui a échoué?
OriginalL'auteur Basile Starynkevitch
Linux page de man pour flock(2):
En outre, troupeau verrouille n'est pas une "pile", donc, si vous essayez d'acquérir un verrou que vous possédez déjà, le troupeau d'appel est un noop qui renvoie immédiatement sans blocage et sans modification de l'état de verrouillage en aucune façon.
Depuis que les threads d'un processus de partage des descripteurs de fichiers, vous pouvez troupeau le fichier plusieurs fois, de plusieurs threads, et de ne pas bloquer le verrou est déjà jugé.
Également les notes sur troupeau(2):
Les Threads d'un processus de partage des descripteurs de fichiers. Voir stackoverflow.com/questions/6223776/... EDIT ---- Et je pense que la plupart d'entre nous qui ont écrit des programmes multi-thread ont avait écrit code de travail dans laquelle les descripteurs de fichiers sont partagés entre les threads.
Ce doit avoir été accepté de répondre...
OriginalL'auteur Chris Dodd