Async verbinden und trennen mit epoll (Linux)

8

Ich brauche eine asynchrone Verbindung und Trennung für TCP-Client mit Epoll für Linux. Es gibt ext. Funktionen in Windows, wie ConnectEx, DisconnectEx, AcceptEx, etc ... In TCP-Server-Standard akzeptieren Funktion funktioniert, aber in TCP-Client funktioniert nicht verbinden und trennen ... Alle Sockets sind nicht blockierend.

Wie kann ich das tun?

Danke!

    
Alexander 17.04.2012, 08:00
quelle

4 Antworten

29

Um eine nicht-blockierende connect () auszuführen, vorausgesetzt, der Socket wurde bereits nicht blockierend gemacht:

%Vor%

Für den zweiten Fall, bei dem connect () mit EINPROGRESS fehlgeschlagen ist (und nur in diesem Fall), müssen Sie warten, bis der Socket beschreibbar ist, z. Für epoll geben Sie an, dass Sie auf diesen Socket auf EPOLLOUT warten. Sobald Sie benachrichtigt werden, dass es beschreibbar ist (mit epoll, auch erwarten, ein EPOLLERR oder EPOLLHUP-Ereignis zu erhalten), überprüfen Sie das Ergebnis des Verbindungsversuchs:

%Vor%

Nach meiner Erfahrung ist connect () unter Linux niemals sofort erfolgreich und Sie müssen immer auf Schreibbarkeit warten. Unter FreeBSD habe ich jedoch festgestellt, dass non-blocking connect () zu localhost sofort erfolgreich ist.

    
Ambroz Bizjak 17.04.2012 16:07
quelle
2

Aus Erfahrung erkennt epoll bei der Erkennung einer nicht blockierenden Verbindung etwas anders als Auswählen und Abfragen.

mit epoll:

Nachdem der Aufruf von connect () ausgeführt wurde, überprüfen Sie den Rückkehrcode.

Wenn die Verbindung nicht sofort hergestellt werden kann, registrieren Sie das Ereignis EPOLLOUT mit epoll.

Rufen Sie epoll_wait () auf.

Wenn die Verbindung fehlgeschlagen ist, werden Ihre Ereignisse mit EPOLLERR oder EPOLLHUP gefüllt, andernfalls wird EPOLLOUT ausgelöst.

    
Bugs 15.08.2013 09:14
quelle
1

Ich habe die Sonny-Lösung ausprobiert und epoll_ctl gibt ein ungültiges Argument zurück. Also denke ich, dass der richtige Weg dies wie folgt ist:

1.create socketfd und epollfd

2.Verwenden Sie epoll_ctl, um socketfd und epollfd mit dem Ereignis epoll zu verknüpfen.

3. verbinden Sie (socketfd, ...)

4. Überprüfen Sie den Rückgabewert oder errno

5.if errno == EINPROGRESS, tu epoll_wait

    
Aaron 03.05.2014 07:46
quelle
0

Ich habe hier eine "vollständige" Antwort, falls jemand anderes danach sucht:

%Vor%     
Sonny 05.06.2012 21:19
quelle