Client with select.select() 
Author Message
 Client with select.select()

Hi,

What's wrong?
I have some simple server programmed for experiments. You can chat with it.
blabla.
But with the code below, I want to connect with it. In the beginning it
prints a welcome message.
Or, it's meant to do. But it only prints the first line from the
welcome-message and not the
following. What am I doing wrong? Because in the logfile from my server,
there's  a line
in which stands that a login-connection has been made. So that's good.
But what am I doing wrong? I want the whole message printed, not the first
line.

Excuse me for my English, blame my teacher :)

A[r]TA

--
-Life can kick your ass, but all you got to do is stand up and move on...

----------------------------------------------------------------------------
--------------
----------------------------------------------------------------------------
--------------

from socket import *
from select import *

s = socket(AF_INET, SOCK_STREAM)
s.connect('127.0.0.1', 23)
text = ''

while 1:
    q = [s.fileno()]
    rd, wr, er = select(q, q, [], None)

    for n in rd:
        if n == s.fileno():
            print rd, wr, er, q
            text = s.makefile().readline()
            print text

    for n in wr:
        if n == s.fileno():
            g = 'password' +chr(13)+ '\n'
            s.send(g)



Fri, 29 Nov 2002 03:00:00 GMT  
 Client with select.select()

| What's wrong?
| I have some simple server programmed for experiments. You can chat with it.
| blabla.
| But with the code below, I want to connect with it. In the beginning it
| prints a welcome message.
| Or, it's meant to do. But it only prints the first line from the
| welcome-message and not the
| following. What am I doing wrong? Because in the logfile from my server,
| there's  a line
| in which stands that a login-connection has been made. So that's good.
| But what am I doing wrong? I want the whole message printed, not the first
| line.

The file object you make with makefile() is an input buffer.  When
you invoke readline() on that buffer, it fills itself with whatever
data it can get from its source, the socket, and then gives you the
first line of that data.  Then you throw away the file object, and
the rest of the data from the socket goes with it.

You probably would be better off without the file object.  Use s.recv()
to read from the socket, and string.split(text, '\n') to separate the
lines.  If the last string isn't empty, save it and append the first
string next time around.

I think you also may have the wrong idea about the write-set parameter
to select().  The test with select() is ``will I block?''  That is,
if read-set returns a file descriptor, you may read from that descriptor
without blocking - either there's data, or end of file or whatever may
cause a non-blocking state on a blocking descriptor.  The same is true
of the write set, mutatis mutandi.  The reader on the other end will
probably ignore what you're writing, you just won't block.  Sockets
are usually in this state.  I guess it's a good thing to check anyway,
but by no means is there any implication that the other end of the socket
has requested data.  ("block" means "wait".)

While I'm at it - chr(13) + '\n' is more conveniently spelled '\r\n'.


----------------------------------------
| from socket import *
| from select import *
|
| s = socket(AF_INET, SOCK_STREAM)
| s.connect('127.0.0.1', 23)
| text = ''
|
| while 1:
|     q = [s.fileno()]
|     rd, wr, er = select(q, q, [], None)
|
|     for n in rd:
|         if n == s.fileno():
|             print rd, wr, er, q
|             text = s.makefile().readline()
|             print text
|
|     for n in wr:
|         if n == s.fileno():
|             g = 'password' +chr(13)+ '\n'
|             s.send(g)



Fri, 29 Nov 2002 03:00:00 GMT  
 Client with select.select()
Information which could be very useful. :)

Thanks,
A[r]TA

--
-Life can kick your ass, but all you got to do is stand up and move on...



Fri, 29 Nov 2002 03:00:00 GMT  
 Client with select.select()

Quote:
> I think you also may have the wrong idea about the write-set parameter
> to select().  The test with select() is ``will I block?''  That is,
> if read-set returns a file descriptor, you may read from that descriptor
> without blocking - either there's data, or end of file or whatever may
> cause a non-blocking state on a blocking descriptor.  The same is true
> of the write set, mutatis mutandi.  The reader on the other end will
> probably ignore what you're writing, you just won't block.  Sockets
> are usually in this state.  I guess it's a good thing to check anyway,
> but by no means is there any implication that the other end of the socket
> has requested data.  ("block" means "wait".)

But if you want to write a telnet-client. The server requests for data,
isn't he?
Then you can check with the write-set and send some data.
Or am I missing something?

A[r]TA

--
-Life can kick your ass, but all you got to do is stand up and move on...



Sat, 30 Nov 2002 03:00:00 GMT  
 Client with select.select()

Quote:

> But if you want to write a telnet-client. The server requests for data,
> isn't he?
> Then you can check with the write-set and send some data.
> Or am I missing something?

A telnet server never explicitly "requests" data from a telnet client
- it's always ready to receive data.  I suppose the initial options
negotiation could be considered a little more of a request since a
client does generate a response to the information being presented by
the server, but there are no such requests during normal data flow.
Once a telnet client has connected to a server, it is free to send
data at any point in time.

Now, it is possible that if a server is unresponsive, or slow, or if
there is network congestion, that the client may build up a queue of
stuff still waiting to be sent by the network layer on the client
machine.  So it can still be useful to use select() to decide if the
underlying network layer is ready to receive more data.

--
-- David
--
/-----------------------------------------------------------------------\

  |             FitLinxx, Inc.            \  Phone: (203) 708-5192    |
 /  860 C{*filter*}Street, Stamford, CT  06902   \  Fax: (203) 316-5150     \
\-----------------------------------------------------------------------/



Sat, 30 Nov 2002 03:00:00 GMT  
 Client with select.select()

[quoting myself]
|> I think you also may have the wrong idea about the write-set parameter
|> to select().  The test with select() is ``will I block?''  That is,
|> if read-set returns a file descriptor, you may read from that descriptor
|> without blocking - either there's data, or end of file or whatever may
|> cause a non-blocking state on a blocking descriptor.  The same is true
|> of the write set, mutatis mutandi.  The reader on the other end will
|> probably ignore what you're writing, you just won't block.  Sockets
|> are usually in this state.  I guess it's a good thing to check anyway,
|> but by no means is there any implication that the other end of the socket
|> has requested data.  ("block" means "wait".)
|
| But if you want to write a telnet-client. The server requests for data,
| isn't he?
| Then you can check with the write-set and send some data.
| Or am I missing something?

There is absolutely no way to tell, from your end, whether there is
a read waiting on the other end.  But otherwise, yes, that makes
sense.  Maybe we could write it like this:

    sfd = sock.fileno()
    while 1:
        rfds = [sfd, pty]
        efds = rfds
        wfds = []
        if ptydata:
            wfds.append(sock)
        if socketdata:
            wfds.append(pty)
        rfds, wfds, efds = select.select(rfds, wfds, efds, timeout)
        if sfd in rfds:
            data = sock.recv(16384)
            if data:
                socketdata = socketdata + data
            else:
                   sock.close()
                   raise EOFError
        [and likewise if pty in rfds, read into ptydata]
        if sfd in wfds:
            nbytes = sock.send(ptydata)
            ptydata = ptydata[nbytes:]
        [and likewise if pty in wfds, write from socketdata]

So I check first whether more socket output can be accepted.  I don't
think you will really find this done very often, though, because only
in relatively dire circumstances would select say "no", and even then
it may be OK to simply block.  It's more important to check the amount
actually sent, in any case, because it may be less than the full string
you gave send() and the rest will have to be re-sent.

When I learned to use sockets and pipes, I had already worked with the
somewhat pipe-like VMS MBX device.  It can notify you specifically when
the process on the other end posts a read.  I loved that.  Haven't seen
anything like it since.




Sat, 30 Nov 2002 03:00:00 GMT  
 Client with select.select()

[select]

Quote:
>Then you can check with the write-set and send some data.
>Or am I missing something?

select will tell you a socket is writable as long as the outbound network
buffers aren't full. It has nothing to do with whether the other end wants
to read. That's all.

- Gordon



Sat, 30 Nov 2002 03:00:00 GMT  
 
 [ 7 post ] 

 Relevant Pages 

1. Clarion Browse using SQL doing a SELECT ASC and then SELECT DESC

2. select and select

3. ASSOCIATE, SELECT TYPE, and SELECT CASE

4. select.select question

5. select.select example?

6. is there any troubles with select.select in python

7. select.select

8. Windows NT select.select( )

9. ports with select.select() ???

10. NT select.select?

11. tcl sql selecting and retrieving selected fields

12. select.select for non-sockets in win2k

 

 
Powered by phpBB® Forum Software