J'essaie de définir un délai d'expiration de 100 ms sur un socket UDP. J'utilise C. J'ai posté des morceaux pertinents de mon code ci-dessous. Je ne sais pas pourquoi ce n'est pas une fin de temps mais un blocage quand il ne reçoit pas de segment. Cela ne fonctionne-t-il que sur les sockets qui ne sont pas liés à l'aide de la méthode bind ()?
#define TIMEOUT_MS 100 /* Seconds between retransmits */
if ((rcv_sock = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0)
DieWithError("socket() failed");
if ((rcv_sock = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0)
DieWithError("socket() failed");
//set timer for recv_socket
static int timeout = TIMEOUT_MS;
setsockopt(rcv_sock, SOL_SOCKET, SO_RCVTIMEO,(char*)&timeout,sizeof(timeout));
if(recvfrom(rcv_sock, ackBuffer,sizeof(ackBuffer), 0,
(struct sockaddr *) &servAddr2, &fromSize) < 0){
//timeout reached
printf("Timout reached. Resending segment %d\n", seq_num);
num_timeouts++;
}
L'option SO_RCVTIMEO
attend un struct timeval
défini dans sys/time.h
, et non un entier comme celui que vous lui transmettez. Le timeval struct
a comme champ pour les secondes et un champ pour les microsecondes. Pour définir le délai d’expiration sur 100 ms, procédez comme suit:
struct timeval tv;
tv.tv_sec = 0;
tv.tv_usec = 100000;
if (setsockopt(rcv_sock, SOL_SOCKET, SO_RCVTIMEO,&tv,sizeof(tv)) < 0) {
perror("Error");
}
J'ai le même problème. J'ai essayé d'adopter la solution que vous avez suggérée, en utilisant la structure timeval
. Mais cela n'a pas semblé fonctionner.
J'ai lu dans la documentation Microsoft et l'heure devrait être une DWORD
avec le nombre de millisecondes, mais il y a aussi une autre chose à faire, si le socket est créé à l'aide de la fonction WSASocket
, le paramètre dwFlags
doit avoir l'attribut WSA_FLAG_OVERLAPPED
défini le délai d'attente pour fonctionner correctement . Sinon, le délai d'attente ne prend jamais effet.