Can Windows Socket #10060 error (WSAETIMEDOUT - An attempt to connect timed out without establishing a connection) be a programming error at all? - windows

I have Delphi application that uses Indy HTTP components (that uses Windows socket). And from time to time I am receiving #10060 socket error (WSAETIMEDOUT - An attempt to connect timed out without establishing a connection) upon execution of Indy procedure:
CheckForSocketError(IdWinsock2.Connect(ASocket, #LAddr, SizeOf(LAddr)));
...
connect : TconnectProc;
...
TconnectProc = function ( const s: TSocket; const name: PSockAddr; const namelen: Integer): Integer; stdcall;
Actually all this is just wrap around Windows connect function https://learn.microsoft.com/en-us/windows/win32/api/winsock2/nf-winsock2-connect that gives error and message WSAETIMEDOUT. So - my question is - can this be programming error at all? Even if I have server running on the other computer and even that server has trouble serving request, even in such cases the low level connect should execute normally, if the server can not serve the GET/POST request, then, of course, the errors should be but those errors should spring in only during execution of other Socket functions not in the connect function, isn't so?
I am trying to solve my problem https://serverfault.com/questions/973648/is-it-possible-that-unencrypted-traffic-can-cause-windows-socket-10057-10060?noredirect=1#comment1266907_973648 and now I am seeking whats happening in my code.
My server side code is very simple - it is just TIdHttpServer component with implemented (I provide event name only here):
MyForm.IdHTTPServerCommandGet(AContext: TIdContext;
ARequestInfo: TIdHTTPRequestInfo; AResponseInfo: TIdHTTPResponseInfo);
So - what can be worng with my implemention, what can lead to the appearance of WSAETIMEDOUT for connect? Yes, my procedure can be long sometimes, but it for years it returned the answer sucessfully and there were no communication errors. And I guess, that connect function can even not depend (does not use/raise) OnCommandGet event, so, I have no control how the server side handles socket connect function from the client?
It may be possible that this is connected with TCP (not HTTP) keepalive, maybe some Windows updates have reduced client-side settings of Windows TCP keepalive for the clients and now this manifests as such error.

Indy TCP clients, like TIdHTTP, have a public ConnectTimeout property, which is set to 0 (infinite) by default. If no timeout is specified, a hard-coded 2 minute timeout is used if the client's TIdTCPClient.Connect() method is called in the main UI thread and TIdAntiFreeze is active, otherwise no timeout is used.
If a timeout is used, Indy calls Winsock's connect() function in a worker thread and waits for that thread to terminate. If Indy's timeout elapses, the socket is closed to abort the connect(), and then EIdConnectTimeout is raised to the caller. If connect() exits before Indy's timeout elapses, an exception is raised to the caller only if connect() failed.
If no timeout is used, Indy calls Winsock's connect() directly, waits for it to exit on its own accord, and then raises an exception only if failed.
So, the ONLY way you can get a WSATIMEDOUT error from Indy when it is calling Winsock's connect() function is if Winsock itself timed out internally before Indy's own timeout elapses. That does not necessarily indicate a problem in your code. It just means that the Host you are trying to connect to is simply not reachable at that moment in time. If the server were reachable, but could not accept your connection, you would get a different error, such as WSAECONNREFUSED.
If your server is behind a firewall or router, make sure it is not blocking connections from reaching your server. Try running a packet sniffer on the server machine, such as WireShark, and make sure the 3-way TCP handshake from TIdHTTP is reaching the server machine correctly.

Related

Golang ssh client timeout not working as expected

I am writing a Golang ssh/sftp client which connects to a sftp server with a slowness in connecting and writing files, using golang.org/x/crypto/ssh package. I need to set Connection timeout and SO timeout (as we do in Java JSCH library).
First to achieve Connection timeout I was using ssh.ClientConfig.Timeout, but only worked for nanosecond and microsecond values, not for milliseconds and above, where I needed to set 5 seconds. According to the API doc also I assume ssh.ClientConfig.Timeout is used only for TCP socket connection creation and ssh handshake is not included there.
So then I tried net.Conn.SetDeadline() and it was for end-to-end connection creation + writing file + connection closing. Since this is also not fine, tried net.Conn.SetWriteDeadline() which looks like SO timeout (applied in TCP packet level) but timeout error is not appeared just after the duration elasped, instead comes out after the server's late reply or subsequent write operation starts.
So can someone please show the correct way of setting Connection timeout and SO timeout in Golang ssh package or tell whether this is supported or not?

Windows sockets: How to immediately detect TCP RST on nonblocking connect()?

Our software (Nmap port scanner) needs to quickly determine the status of a non-blocking TCP socket connect(). We use select() to monitor a lot of sockets, and Windows is good at notifying us when one succeeds. But if the port is closed and the target sends a TCP RST, Windows will keep trying a few times before notifying the exceptfds, and the socket error is WSAECONNREFUSED as expected. Our application has its own timeout, though, and will usually mark the connection as timed-out before Windows gives up. We want to get as close as possible to the behavior of Linux, which is to notify with ECONNREFUSED immediately upon receipt of the first RST.
We have tried using the TCP_MAXRT socket option, and this works to get select() to signal us right away, but the result (for closed ports) is always WSAETIMEDOUT, which makes it impossible to distinguish closed (RST) from filtered/firewalled (network timeout), which puts us back at the original problem. Determining this distinction is a core feature of our application.
So what is the best way on Windows to find out if a non-blocking socket connect() has received a connection reset?
EDITED TO ADD: A core problem here is this line from Microsoft's documentation on the SO_ERROR socket option: "This per-socket error code is not always immediately set." If it were immediately set, we could check for it prior to the connect timeout.

socketException broken pipe upon upgrading httpclient jar version to 4.5.3

I am getting socket exception for broken pipe in my client side.
[write] I/O error: Connection has been shutdown: javax.net.ssl.SSLException: java.net.SocketException: Broken pipe (Write failed)
[LoggingManagedHttpClientConnection::shutdown] http-outgoing-278: Shutdown connection
1520546494584[20180308 23:01:34] [ConnectionHolder::abortConnection] Connection discarded
1520546494584[20180308 23:01:34] [BasicHttpClientConnectionManager::releaseConnection] Releasing connection [Not bound]
It seems that the upgradation of httpclient jar is causing issue.
Issue is not coming with httpclient-4.3.2
Exception is coming in every 2 minutes. Issue is intermittent at times.
after , send expect:100-continue ,conn.flush is throwing exception
client and server are Linux machine
client uses http jar to make request to server REST.
Please help me in debugging the issue
can httpjar cause such issue?
The persistent connections that are kept alive by the connection manager become stale. That is, the target server shuts down the connection on its end without HttpClient being able to react to that event, while the connection is being idle, thus rendering the connection half-closed or 'stale'
This is a general limitation of the blocking I/O in Java. There is simply no way of finding out whether or not the opposite endpoint has closed connection other than by attempting to read from the socket.
If a stale connection is used to transmit a request message the request execution usually fails in the write operation with SocketException and gets automatically retried.
Apache HttpClient works this problem around by employing the so stale connection check which is essentially a very brief read operation. However, the check can and often is disabled. In fact it is often advisable to have it disabled due to extra latency the check introduces.
The handling of stale connections was changed in version 4.4. Previously, the code would check every connection by default before re-using it. The code now only checks the connection if the elapsed time since the last use of the connection exceeds the timeout that has been set. The default timeout is set to 2000ms

tcp and apache keepalivetimouts

A few weeks ago I wrote a small program which created a socket to an apache webserver and made a request.
Back then I did not know that this web server had a KeepAliveTimeout of 5 seconds.
After my first request I waited 1 minute. After this I wanted to reuse my first socket for another webserver request, but got an error.
From Beej's Guide to Network Programming I learned that if recv returns 0, then the other side has closed its connection:
Wait! recv() can return 0. This can mean only one thing: the remote side has closed
the connection on you! A return value of 0 is recv()'s way of letting you know this
has occurred.
My questions are now:
What does Apache send when the KeepAliveTimeout is over - a FIN or a RST packet?
I know that using a TCP connection for 2 unrelated HTTP requests like in this scenario might
not be the best thing. But in order to understand TCP more the next question is:
After my first successful http request, and before sending the next HTTP request over the same socket, would there be somehow a possibility to get informed about this keepalivetimeout TCPsocket termination of the server other than receiving 0 from the next recv() call?
It will send a FIN. If you write a request to the server after that, send() will return -1 with errno/WSAGetLastError() = ECONNRESET.
would there be somehow a possibility to get informed about this keepalivetimeout tcp socket termination of the server
Yes, by reading the proper response header parameter, namely Keep-Alive: timeout=delta-seconds:
'timeout' Parameter
A host sets the value of the timeout parameter to the time that the host will allows an idle connection to remain open before it is closed. A connection is idle if no data is sent or received by a host.
The value of the timeout parameter is a single integer in seconds.
A host MAY keep an idle connection open for longer than the time that it indicates, but it SHOULD attempt to retain a connection for at least as long as indicated.
As you can see, it's up to the host to decide. Given it only SHOULD try to keep the connection open as long as promised, but it isn't required that it does in order to conform to the spec, so the server might decide to close and reuse the connection to serve another pending client.

Interrupting a connecting windows wsa socket

I was just wondering if it is possible to interrupt call to windows socket "connect" function?
The problem is that my code requires that to be done in a different thread (so GUI thread keeps running). But when the programm is closed there my still be threads calling "connect" that are wating for a WSAETIMEDOUT exception.
Any ideas?
Update/Hint: i cant call close() since i only have a valid handle when connect() returns. the latter one is not the case when using blocking sockets and having a tcp-connect to a firewalled location (for example) :/
If the socket is in blocking mode, the only way to abort connect() call is to close the socket from a different thread context than the one that is calling connect(). connect() will return an error, and the thread can then exit itself normally.
If the socket is in non-blocking or overlapped mode, connect() will return immediately with a WSAEWOULDBLOCK error, and you then have to call select(), WSAAsyncSelect(FD_CONNECT), or WSAEventSelect(FD_CONNECT) to detect when the connection has been established before continuing with your socket work. Since the calling thread is not blocked on connect(), it is free to periodically check for any termination/abort signals from the rest of your code, and if detected then close the socket (if needed) and exit itself normally.
If you write your socket code in non-blocking or overlapped mode, then you do not really need to use a thread. You can do your socket work within the main thread without blocking your UI, then you can just close the socket when needed. It takes a little more work to code that way, but it does work. Or you can continue using a thread. It will keep your socket code separate from your UI code and thus a bit more managable.

Resources