ctusch

Hey,

I'm currently writing a HTTP proxy in C# and I'm facing serious problems with .NET's Socket class. All the communication stuff works fine, the browser loads the webpages through the proxy, but when I check my open connections with netstat I see all the connections I opened with the proxy in the state CLOSE_WAIT. So I tried to sniff the traffic and came to the conclusion that the server sends the FIN/ACK and the clients acknowledges it but it doesn't send its FIN/ACK back (which results in the above mentioned state). So I did really a lot of googling, searched this forum and tried out a punch of things. As far as I understand it, the client sends its FIN/ACK when I close the socket. But how should I determine when to do this The .NET framework gives me no direct opportunity to check the socket state. And the connected property just changes its state when there has been a send or receive.
I think I'm missing something big.. I hope somebody can give me a hint into the right direction. I'm totally clueless what else I could do.

Thanks for any reply!


Re: .NET Framework Networking and Communication how to determine if the connection was closed remotely

ctusch

Does really noone know the answer to such a basic question




Re: .NET Framework Networking and Communication how to determine if the connection was closed remotely

Tom Frey

When 0 bytes are received, the socket connection is closed or broken.




Re: .NET Framework Networking and Communication how to determine if the connection was closed remotely

Mike Flasko

To expand on what Tom noted above, your code should have the following semantics:

int bytesRead = socket.Read( specify buffer & offset into the buffer to read data into )

while (bytesRead > 0){

// connection is still open and the buffer has data from the remote host

int bytesRead = socket.Read( specify buffer & offset into the buffer to read data into )

}

// remote host has closed the connection since bytesRead =0






Re: .NET Framework Networking and Communication how to determine if the connection was closed remotely

ctusch

Thanks for the replies, but that doesn't help me. I need to forward the traffic continously since I need the proxy for an AJAX application, thus my TCP connection stays open for a long time and every 2 minutes there is an update packet. With your solution I can receive all the data at once and that would be okay in most cases (static html, php and so on) but doesn't work with AJAX. Any other ideas




Re: .NET Framework Networking and Communication how to determine if the connection was closed remotely

Tom Frey

I'm not following AJAX uses HTTP as its transport which in turn uses TCP.
You want to know when a connection is closed or dropped, right If so, you will receive 0 bytes from the socket on such an event. Also, I don't understand what you mean by "I can receive all the data at once" You simply keep reading from the socket until you either receive 0 bytes or a send attempt fails.




Re: .NET Framework Networking and Communication how to determine if the connection was closed remotely

ctusch

I wanted to say that a standard HTTP connection is opened, the document is requested and then transmitted. After this the connection is closed. The AJAX application for which I want to use my proxy keeps the connection open in order to update a SVG every 2 minutes. So if I'd use the method Mike suggested I couldn't forward the received data (especially updates) until the connection is closed (i.e. all data is received), or did I get something wrong




Re: .NET Framework Networking and Communication how to determine if the connection was closed remotely

niels.t

Heya,

I think I have exactly the same problem as ctusch. In a tcp client/server application I do not manage to recognize

on the server-side when a client does actually close the connection. I'm using the tcplistener and tcpclient components.

Server-side looks like this:

<..>

tcpclient = tcplistener.acceptTCPClient()

do while true

if tcpclient.getStream().dataAvailable then

<read data and do some quick stuff>

end if

if not isClientConnected(tcpClient) then

<remove this tcp client and do clean-up stuff>

end if

<do other quick stuff>

loop

The client stays connected for say one week and then

closes the connection in the following way:

tcpclient.getStream().close()

tcpclient.close()

If I look at netstat, I see after doing the client-side disconnect that the connection is

in the fin-wait-2 state at the client side and in the close-wait state at the server side.

The problem is: How to implement the isClientConnected() at the server-side so that it detects

that the connection has been closed by the client

I tried the following things (which all did not work):

1) ask the tcpClient.connected property: it tells you "true" because it does not depend on the current state but

has been set during the last read/send operation, which took place when the connection was still present.

2) ask tcpClient.Client.Poll(-1, Sockets.SelectMode.SelectWrite): returns "true" although socket is in

the above mentioned "close-wait" state

3) try to do a zero-length non-blocking send via tcpClient.Client.Send(tmp, 0, 0) and catch exceptions

that might arise (and if an exception is caught, the socket is considered disconnected). This method

is recommended in the documentation of the tcpClient.Connected property. It does not work. The send

returns without any error as long as I send not a single byte. However, it does cause the desired exception if

I do really send at least one byte of data. But, I cannot send some junk data to my clients every few

milliseconds just to find out, if the connection is still alive. *g*

I have seen a lot of posts related to the same problem in many different contexts, but I did not find

an applicable solution so far. So if someone knows how to handle this properly, he would not only help

me but possibly many other people, too.

Thank you so much,

Niels