Partager via


Arrêt approprié, options de persistance et fermeture de socket

Le matériel suivant est fourni comme clarification pour l’objet de l’arrêt des connexions de socket fermant les sockets. Il est important de distinguer la différence entre l’arrêt d’une connexion de socket et la fermeture d’un socket.

L’arrêt d’une connexion de socket implique un échange de messages de protocole entre les deux points de terminaison, appelé ci-après séquence d’arrêt. Deux classes générales de séquences d’arrêt sont définies : normalement et abortive (également appelée hard). Dans une séquence d’arrêt appropriée, toutes les données qui ont été mises en file d’attente, mais qui ne sont pas encore transmises peuvent être envoyées avant la fermeture de la connexion. Dans un arrêt abortif, toutes les données non contenues sont perdues. L’occurrence d’une séquence d’arrêt (normale ou abandonnée) peut également être utilisée pour fournir une indication FD_CLOSE aux applications associées indiquant qu’un arrêt est en cours.

En revanche, la fermeture d’un socket entraîne la désallocation du handle de socket afin que l’application ne puisse plus référencer ou utiliser le socket de quelque manière que ce soit.

Dans Windows Sockets, la fonction d’arrêt et la fonction WSASendDisconnect peuvent être utilisées pour lancer une séquence d’arrêt, tandis que la fonction closesocket est utilisée pour libérer des handles de socket et libérer toutes les ressources associées. Toutefois, une certaine confusion survient du fait que le closesocket fonction provoque implicitement une séquence d’arrêt si elle n’a pas déjà eu lieu. En fait, il est devenu une pratique de programmation plutôt courante pour s’appuyer sur cette fonctionnalité et utiliser closesocket pour lancer la séquence d’arrêt et libérer le handle de socket.

Pour faciliter cette utilisation, l’interface de sockets fournit des contrôles par le biais du mécanisme d’option de socket qui permet au programmeur d’indiquer si la séquence d’arrêt implicite doit être normale ou abandonnée, et également si l'closesocket fonction doit s’attarder (ce qui n’est pas terminé immédiatement) pour permettre la fin d’une séquence d’arrêt appropriée. Ces distinctions importantes et les ramifications de l’utilisation de closesocket de cette manière ne sont toujours pas largement comprises.

En établissant les valeurs appropriées pour les options de socket SO_LINGER et SO_DONTLINGER, les types de comportement suivants peuvent être obtenus avec la fonction closesocket :

  • Séquence d’arrêt abandonnée, retour immédiat de closesocket.
  • Arrêt approprié, délai de retour jusqu’à ce que la séquence d’arrêt se termine ou qu’un intervalle de temps spécifié s’écoule. Si l’intervalle de temps expire avant la fin de la séquence d’arrêt appropriée, une séquence d’arrêt abortive se produit et closesocket retourne.
  • Arrêt approprié, retour immédiat, permettant à la séquence d’arrêt de se terminer en arrière-plan. Bien qu’il s’agisse du comportement par défaut, l’application n’a aucun moyen de savoir quand (ou si) la séquence d’arrêt appropriée se termine réellement.

L’utilisation des options de socket SO_LINGER et SO_DONTLINGER et de la structure deassociée est abordée plus en détail dans les sections de référence sur SOL_SOCKET options de socket et la structure persistante.

Une technique qui peut être utilisée pour réduire le risque de problèmes lors de la suppression de connexion consiste à éviter de compter sur un arrêt implicite lancé par closesocket. Utilisez plutôt l’une des deux fonctions d’arrêt explicites, d’arrêt ou WSASendDisconnect. Cela entraîne la réception d’une indication FD_CLOSE par l’application homologue indiquant que toutes les données en attente ont été reçues. Pour illustrer cela, le tableau suivant montre les fonctions qui seraient appelées par les composants client et serveur d’une application, où le client est responsable du lancement d’un arrêt approprié.

Côté client Côté serveur
(1) Appelle d’arrêt (s, SD_SEND) pour signaler la fin de session et que le client n’a plus de données à envoyer.
(2) Reçoit FD_CLOSE, indiquant l’arrêt correct en cours et que toutes les données ont été reçues.
(3) Envoie toutes les données de réponse restantes.
(importance du minutage local uniquement) Obtient FD_READ et appelle recv pour obtenir les données de réponse envoyées par le serveur. (4) Appelle 'arrêt(s, SD_SEND) pour indiquer que le serveur n’a plus de données à envoyer.
(5) Reçoit FD_CLOSE indication. (importance du minutage local uniquement) Appelle closesocket .
(6) Appelle closesocket.