[gull] Socket
Daniel Cordey
dc at mjt.ch
Fri Sep 24 09:20:03 CEST 2004
On Friday 24 September 2004 08:52, Blaise Vogel wrote:
> En cas de
> connexion "lente" (modem/adsl), je retrouve dans le buffer 1388 bytes, puis
> 1388 bytes, puis le solde de 224 bytes ! Je dois appeler 3 fois le receive.
> En supposant un en-tête de datagramme IP de 24 bytes et un en-tête TCP de
> 24 bytes j'arrive a 1436 bytes, pas loin du mtu de l'adsl qui est de 1492.
> En résumé je ne comprends pas le comportement du receive. Que se passe-t-il
> a ce moment, la fonction ne retourne-t-elle que le(s) paquets déjà reçus ?
> Dans ce cas a quoi sert le bit de FIN de l'en tête TCP ?
Ah, ah... c'est un peu la suite de la discussion de l'autre jour a propos de
TCP. Je conseille a tous la lecture d'un livre au sujet des protocole TCP,
UDP, etc.
L'utilisation du protocole garanti que vous recevrez votre "stream" de bytes
dans l'ordre, pas que vous les recevrez d'un seul coup. En effet, le
protocole TCP implement une notion de "pointeur" dans l'ensemble de ce qu'il
doit recevoir. Ce pointeur (je schematise) vaut zero au debut de la connexion
et est equivalent a ce qu'il attendait a la fin de l'ensemble des
transactions liees au transfert. C'est a dire que ce pointeur s'incremente au
fur et a mesure que le "destinataire" recoit des paquets et qu'il est en
mesure de faire progresser son "bloc" de bytes recus et sans trous. Pour
illustrer ceci, imaginons qu'un transfert de X bytes sera (pour differentes
raisons que nous n'evoquerons pas ici) decoupe en :
A, B, C, D
Il n'y a absolument aucune garantie que ces paquets arrivent a destination
dans le meme ordre. Imaginons donc que le destinataire recoive :
A, B, D
Le pointeur restera au niveau de la "fin" de B, et le destinataire attendra le
bloc C pour continuer a faire avancer son "pointeur". Il se peut aussi, que
le bloc C (ou un autre) arrive en morceaux, soit : C1, C2, C3... de tailles
non identiques... le "pointeur" peut quand meme "progresser".
La maniere dont le "kernel" (on devrait plutot parler des modules de gestion
du stack IP) gere ceci est que chaque fois que le "pointeur" progresse (et
dans un certain lapse de temps), le bout de paquet complementaire est mis a
disposition de l'application receptrice.... Nous y voila !
C'est donc pour cette raison que l'on utilise la commande select(2), afin de
se brancher sur un read/receive des que l'on a recu quelque chose. Notez
aussi que select(2) est utilise pour l'ecriture lorsque les "buffers" sont
pleins; ce qui arrive tres vite avec du pipe !
Il est d'ailleurs tres marrant de constater que cette fonction systeme est
apparue exactement en meme temps que telnet/ftp de Berkeley. J'aurais
tendance a dire que son besoin s'est fait sentir a ce moment :-)
dc
More information about the gull
mailing list