socket buffer flush question

Jim Segrave jes at nl.demon.net
Wed Jul 5 10:27:08 EDT 2006


In article <1152104115.156123.120200 at b68g2000cwa.googlegroups.com>,
Kiran <Kiran.Karra at gmail.com> wrote:
>Hello Everybody!
>  I am writing a networking application in python for a small piece of
>hardware, in which there could sometimes be timeouts.  I am using
>sockets to communicate to this device.  Data that is sent to the device
>is instructions for that piece of hardware, and data recieved is just
>responses from that hardware.
>  When a timeout happens, for some reason extra data is stored inside
>the buffer, so when the timeout is over, that extra data (remember this
>data is instructions) is executed by the hardware, which I don't want.
>For timeout purposes, I want the socket to be nonblocking, but at the
>same time this means that I can't flush the buffer, which I think would
>solve the problem.
>
>I realize this is probably quite unclear, so below is a tcpdump which
>will explain what I mean.
>
>15:10:37.667963 aurl06f2.39979 > 192.168.128.161.46667: P 481:493(12)
>ack 481 win 5840 <nop,nop,timestamp 157458905 528016> (DF)
>			 4500 0040 090c 4000 4006 599f 8fd1 06f2
>			 c0a8 80a1 9c2b b64b 30c7 9289 a552 55df
>			 8018 16d0 c3ec 0000 0101 080a 0962 a1d9
>			 0008 0e90 0000 0001 f800 0110 0000 0000

You sent a read f8000110 command to the device 12 bytes, sequence
481..493 in this connection. You've received 480 bytes from the device

>15:10:51.107769 aurl06f2.39979 > 192.168.128.161.46667: P 481:493(12)
>ack 481 win 5840 <nop,nop,timestamp 157460249 528016> (DF)
>			 4500 0040 090d 4000 4006 599e 8fd1 06f2
>			 c0a8 80a1 9c2b b64b 30c7 9289 a552 55df
>			 8018 16d0 beac 0000 0101 080a 0962 a719
>			 0008 0e90 0000 0001 f800 0110 0000 0000

You sent the command again

>15:10:51.108259 192.168.128.161.46667 > aurl06f2.39979: P 481:493(12)
>ack 493 win 5792 <nop,nop,timestamp 533605 157460249> (DF)
>			 4500 0040 5580 4000 3f06 0e2b c0a8 80a1
>			 8fd1 06f2 b64b 9c2b a552 55df 30c7 9295
>			 8018 16a0 dbf5 0000 0101 080a 0008 2465
>			 0962 a719 8000 0001 f800 0110 0000 4d05

the device responds to your command with 12 bytes, which also appear
to be sequence 481..493. The device confirms it has received 492 bytes
from your program. I assume every command gets an equal length
return, so that when things are running correctly, the received
sequence numbers will match the last sent command.


>15:10:51.108283 aurl06f2.39979 > 192.168.128.161.46667: P 493:565(72)
>ack 493 win 5840 <nop,nop,timestamp 157460249 533605> (DF)
>			 4500 007c 090e 4000 4006 5961 8fd1 06f2
>			 c0a8 80a1 9c2b b64b 30c7 9295 a552 55eb
>			 8018 16d0 cb29 0000 0101 080a 0962 a719
>			 0008 2465 0000 0001 f800 0110 0000 0000
>			 0000 0001 f800 0110 0000 0000 0000 0001
>			 f800

It looks to me like you've sent 6 more commands during the timeout period,
so you should expect 6 responses back, the first being sequence
493..505, then another for 505..517, etc.

>            ************* NOTICE THE EXTRA DATA *****************
>15:10:51.108731 192.168.128.161.46667 > aurl06f2.39979: P 493:505(12)
>ack 565 win 5792 <nop,nop,timestamp 533605 157460249> (DF)
>			 4500 0040 5581 4000 3f06 0e2a c0a8 80a1
>			 8fd1 06f2 b64b 9c2b a552 55eb 30c7 92dd
>			 8018 16a0 db99 0000 0101 080a 0008 2465
>			 0962 a719 8000 0001 f800 0110 0000 4d0d

Here the device confirms that it has received 564 bytes from your
program and sends the first 12 bytes of responses.


>15:10:51.111760 aurl06f2.39979 > 192.168.128.161.46667: P 565:577(12)
>ack 505 win 5840 <nop,nop,timestamp 157460249 533605> (DF)
>			 4500 0040 090f 4000 4006 599c 8fd1 06f2
>			 c0a8 80a1 9c2b b64b 30c7 92dd a552 55f7
>			 8018 16d0 a867 0000 0101 080a 0962 a719
>			 0008 2465 0000 0001 f800 0114 0000 0000


you send another command. At this point you've sent 576 bytes out (48
commands) and received back 504 bytes (42 responses). The last
response shows that 47 of the commands have made it to the device and
are (presumably) awaiting processing.

>The last 3 words (32 bits/word) of the hex printout shows the
>condition.  The first of the last 3 words is the instruction, in this
>case a read instruction: 0000_0001.  The second is the address:
>f800_0110 or f800_0114.  The third is the data recieved.
>As you can see, the first 2 printouts are a timeout (it is much longer
>than this, but i didnt want to post all of that) because one machine is
>communicating to the other without a response.  The third printout is
>when the machine recovers from the timeout, and it works fine.
>However, the printout after the machine recovers has some extra data at
>the end.  This is the data I want to flush out of the buffer, but I
>cant really figure out how to do so.

What I see is that you continued sending new commands while not
getting responses from the device. The device has received them, since
it acknowledges that it has seen up to byte 565 of your output. This
is not an unflushed buffer problem - the data has reached the TCP/IP
stack of the device and what happens to it next depends on the
application layer in the device. If it is reading and discarding
commands, then you have a problem that you have sent several commands
which won't receive replies. If the device's application works
correctly, it will continue to dequeue commands 12 bytes at a time and
send replies. If it reads whatever is available and only processes 12
bytes from the read, then the device end application is sub-optimal
and you will have to ensure you don't issue any new commands until the
previous command has been processed. Once you transfer data to your
machine's network stack, there's no way to stop it being sent to the
remote end - in fact there's no practical way to determine if it's
been put in a packet, sent to the remote end and lost or put in a
packet, sent to the remote end and is awaiting processing, or is
waiting to be put into a packet and hasn't left your machine at all. 

What happens if your application simply stops transmitting new
commands after a timeout? Do you eventually get all the responses in?

-- 
Jim Segrave           (jes at jes-2.demon.nl)




More information about the Python-list mailing list