problem with sockets under win32; premature connection termination

Downs default_357-line at yahoo.de
Thu May 10 16:26:24 PDT 2007


Chris Miller wrote:
> On Thu, 10 May 2007 18:55:05 -0400, Downs <default_357-line at yahoo.de> 
> wrote:
> 
>> The following code should theoretically wait for a single TCP 
>> connection, and transfer a file over it.
>>
>> import std.stdio, std.socket, std.string, std.file;
>>
>> void main(char[][] args) {
>>   auto l=new Socket(AddressFamily.INET, SocketType.STREAM, 
>> ProtocolType.TCP);
>>   l.blocking=true;
>>   with (l) {
>>    bind(new InternetAddress("0.0.0.0", atoi(args[1])));
>>    listen(16);
>>   }
>>   auto request=l.accept;
>>   request.send("HTTP/1.0 200 OK\r\n\r\n");
>>   request.send(read(args[2]));
>>   request.shutdown(SocketShutdown.BOTH);
>>   request.close;
>> }
>>
>> Trying to use this program to host a file (images work best), I ran 
>> into the following problem:
>> the image would transmit, partially, then the request.send call would 
>> return - prematurely -
>> and the rest of the unsent data would be silently discarded.
>> Experimenting with linger and SetOption produced no discernible effect.
>> I've tried to find a solution to this problem for weeks now, but I 
>> don't seem to be making headway.
>>
>> Halp? ;_;
>>
>>   -- downs
>>
>> PS: If you try to replicate it, it is recommended to use a mid-latency 
>> connection so that the transfer doesn't complete immediately.
>> PPS: Interestingly, it works with netcat. Firefox, IE and Opera break 
>> though.
> 
> Socket.send doesn't guarantee the whole thing will send; it returns how 
> many bytes are buffered to be sent.

Sorry, I omitted this. I tried it; didn't help.

> Also, using Socket.shutdown to shutdown sends/writes (included 
> by BOTH) might be aborting the unsent buffer.

Yes, on Linux. Not on Win32. (it's even recommended, see the std.socket docs)

> Finally, after these 
> appropriate changes, I believe there's still a chance that the whole 
> buffer won't be sent if the linger time expires before the whole buffer 
> was able to send.

I tried sending linger to 30s. Didn't help any. But thanks for your input.
  -- downs



More information about the Digitalmars-d mailing list