J'avais une discussion avec un coéquipier sur le verrouillage en .NET. C'est un gars très brillant avec une vaste expérience dans la programmation de niveau inférieur et supérieur, mais son expérience avec la programmation de niveau inférieur dépasse de loin la mienne. Quoi qu'il en soit, il a fait valoir que le verrouillage .NET devrait être évité sur les systèmes critiques censés être soumis à une charge élevée si possible afin d'éviter la possibilité certes faible d'un «fil zombie» de planter un système. J'utilise régulièrement le verrouillage et je ne savais pas ce qu'était un «fil zombie», alors j'ai demandé. L'impression que j'ai eue de son explication est qu'un fil zombie est un fil qui s'est terminé mais qui conserve en quelque sorte encore certaines ressources. Un exemple qu'il a donné de la façon dont un fil zombie pourrait briser un système si un fil commence une procédure après avoir verrouillé un objet, puis se termine à un moment donné avant que le verrou puisse être libéré. Cette situation a le potentiel de planter le système, car en fin de compte, les tentatives d'exécution de cette méthode entraîneront tous les threads en attente d'accès à un objet qui ne sera jamais renvoyé, car le thread qui utilise l'objet verrouillé est mort.
Je pense que j'ai compris l'essentiel, mais si je suis hors de la base, faites-le moi savoir. Le concept avait du sens pour moi. Je n'étais pas complètement convaincu qu'il s'agissait d'un scénario réel qui pourrait se produire dans .NET. Je n'ai jamais entendu parler de "zombies", mais je reconnais que les programmeurs qui ont travaillé en profondeur à des niveaux inférieurs ont tendance à avoir une compréhension plus approfondie des principes fondamentaux de l'informatique (comme le filetage). Cependant, je vois vraiment la valeur du verrouillage, et j'ai vu de nombreux programmeurs de classe mondiale tirer parti du verrouillage. J'ai également une capacité limitée à évaluer cela par moi-même parce que je sais que l' lock(obj)
énoncé est vraiment juste du sucre syntaxique pour:
bool lockWasTaken = false;
var temp = obj;
try { Monitor.Enter(temp, ref lockWasTaken); { body } }
finally { if (lockWasTaken) Monitor.Exit(temp); }
et parce que Monitor.Enter
et Monitor.Exit
sont marqués extern
. Il semble concevable que .NET fasse une sorte de traitement qui protège les threads de l'exposition aux composants du système qui pourraient avoir ce genre d'impact, mais c'est purement spéculatif et probablement juste basé sur le fait que je n'ai jamais entendu parler de "threads zombies" avant. J'espère donc pouvoir obtenir des commentaires à ce sujet ici:
- Existe-t-il une définition plus claire d'un "fil zombie" que ce que j'ai expliqué ici?
- Les threads zombies peuvent-ils se produire sur .NET? (Pourquoi pourquoi pas?)
- Le cas échéant, comment pourrais-je forcer la création d'un fil zombie dans .NET?
- Le cas échéant, comment puis-je tirer parti du verrouillage sans risquer un scénario de thread zombie dans .NET?
Mise à jour
J'ai posé cette question il y a un peu plus de deux ans. Aujourd'hui, c'est arrivé:
wait
ou waitpid
. Le processus enfant est alors appelé "processus zombie". Voir aussi howtogeek.com/119815