Question

Je suis en train de coder l’arrêt d’un serveur multithread. Si tout se passe comme il se doit, tous les threads se débrouillent seuls, mais il existe un faible risque qu’un thread se coince. Dans ce cas, il serait commode d’avoir un -blocage rejoindre pour que je puisse faire.

Existe-t-il un moyen de créer un pthread_join non bloquant? Une sorte de jointure chronométrée serait également utile.

quelque chose comme ceci:

foreach thread do
  nb_pthread_join();
    if still running
      pthread_cancel();

Je peux penser à davantage de cas où une jointure sans blocus serait utile.

Comme il semble qu’il n’existe pas de telle fonction, j’ai déjà codé une solution de contournement, mais ce n’est pas aussi simple que je le voudrais.

Était-ce utile?

La solution

Comme d'autres l'ont souligné, il n'existe pas de pthread_join non bloquant dans les bibliothèques pthread standard.

Cependant, étant donné le problème que vous avez énoncé (essayer de garantir que tous vos threads ont disparu lors de l'arrêt du programme), une telle fonction n'est pas nécessaire. Vous pouvez simplement faire ceci:

int killed_threads = 0;
for(i = 0; i < num_threads; i++) {
   int return = pthread_cancel(threads[i]);
   if(return != ESRCH)
      killed_threads++;
}
if(killed_threads)
    printf("%d threads did not shutdown properly\n", killed_threads)
else
    printf("All threads exited successfully");

Il n'y a rien de mal à appeler pthread_cancel sur tous vos threads (terminés ou non), donc appeler cela pour tous vos threads ne bloquera pas et garantira la sortie du thread (propre ou non).

Cela devrait être considéré comme une solution de contournement "simple".

Autres conseils

Si vous exécutez votre application sous Linux, sachez que:

int pthread_tryjoin_np(pthread_t thread, void **retval);

int pthread_timedjoin_np(pthread_t thread, void **retval,
                                const struct timespec *abstime);

Faites attention, comme le suggère le suffixe, "np" signifie "non-portable". Ce ne sont pas des extensions standard de gnu, bien qu’elles soient utiles.

lien vers la page de manuel

Le mécanisme 'pthread_join' est pratique à utiliser s'il fait exactement ce que vous voulez. Il ne fait rien que vous ne puissiez faire vous-même, et là où ce n'est pas exactement ce que vous voulez, codez exactement ce que vous voulez.

Il n’existe aucune raison réelle de vous demander si un thread est terminé ou non. Ce qui compte, c'est de savoir si le travail effectué par le fil est terminé. Pour dire cela, demandez au fil de faire quelque chose pour indiquer qu'il fonctionne. Cela dépend de ce qui convient le mieux à votre problème spécifique, qui dépend fortement de ce que font les threads.

Commencez par changer votre façon de penser. Ce n'est pas un fil qui se coince, c'est ce que faisait le fil qui se coince.

Si vous développez pour QNX, vous pouvez utiliser la fonction pthread_timedjoin ().

Sinon, vous pouvez créer un thread séparé qui effectuera pthread_join () et alertera le thread parent, en signalant un sémaphore, par exemple, que le thread enfant est terminé. Ce thread séparé peut renvoyer ce qui est obtenu de pthread_join () pour permettre au thread parent de déterminer non seulement le moment où l’enfant est terminé, mais également la valeur qu’il renvoie.

La réponse dépend vraiment de la raison pour laquelle vous voulez faire cela. Si vous souhaitez simplement nettoyer les threads morts, par exemple, il est probablement plus simple de disposer d'un "nettoyeur de thread mort". fil qui boucle et se joint.

Je ne suis pas sûr de ce que vous voulez dire exactement, mais je suppose que ce dont vous avez vraiment besoin, c'est d'un mécanisme d'attente et de notification.

En bref, voici comment cela fonctionne: vous attendez une condition à remplir avec un délai d'attente. Votre attente sera terminée si:

  • le délai d'attente est écoulé ou
  • Si la condition est remplie.

Vous pouvez avoir cela en boucle et ajouter plus d'intelligence à votre logique. La meilleure ressource que j'ai trouvée pour ce sujet lié à Pthreads est ce tutoriel: Programmation POSIX Threads ( https://computing.llnl.gov/tutorials/pthreads/ ) .

Je suis également très surpris de constater qu'il n'y a pas d'API pour les jointures temporisées dans Pthreads.

Il n'y a pas de pthread_join chronométré, mais si vous attendez qu'un autre thread soit bloqué sous certaines conditions, vous pouvez utiliser pthread_cond_timed_wait au lieu de pthread_cond_wait .

Vous pouvez insérer un octet dans un canal ouvert en tant que non bloquant pour signaler à l'autre thread à la fin de l'opération, puis utiliser une lecture non bloquante pour vérifier l'état du canal.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top