Scanning for local servers, getting a broadcast address

Chris Lyon chris.lyon at spritenote.co.uk
Fri Jun 13 13:02:59 CEST 2003


Again much thanks for the help
here is my present code I would appreciate any comments.

I would have liked to have used the write list of the select statement
but I found that If I did that the routine never exited because the
write thread is always ready and the timeout doesn't start. I could
clear the write list inside the while but wouldn't I still be in a
loop if I couldn't write in the first place?


Anyway here they are:-

remote server code:-

import socket
import select
myname = socket.getfqdn(socket.gethostname())

s = socket.socket(socket.AF_INET,socket.SOCK_DGRAM,
socket.IPPROTO_UDP)
s.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST,1)
s.bind(('',20031))

while 1:
     
    (rfd,wfd,efd) = select.select([s] ,[] ,[])
    if s in rfd:       # I have a message 
        (string, address) = s.recvfrom(100)
        print 'RECEIVED:-',string, address
        if string == 'scan\n':       # I've been requested by a scan
to identify myself
            print 'replying to scan from ',address
            s.sendto('IAM '+ myname +'\n',address)


questioning server code:-

import socket
import select

remotedict = {}
broadcast_attempts = 3   # I assume UDP broadcasts can get dropped
like anything else in UDP
reply_attempts = 3       # three re-trys on recieving a broadcast
ack_flag =  1            # I have recieved an acknowledgement ... shut
up
myname = socket.getfqdn(socket.gethostname())

s = socket.socket(socket.AF_INET,socket.SOCK_DGRAM,
socket.IPPROTO_UDP)
s.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST,1)
s.bind(('',20031))

while 1:
    if broadcast_attempts:   # I need to broadcast
        broadcast_attempts = broadcast_attempts - 1
        print 'sending scan'
        s.sendto('scan\n', ('<broadcast>', 20031))
        
    (rfd,wfd,efd) = select.select([s] ,[] ,[] , 5)
    if s in rfd:       # I have a message 
        (string, address) = s.recvfrom(100)
        print 'RECEIVED:-',string, address
        if string == 'scan\n':       # I've been requested by a scan
to identify myself
            print 'replying to scan from ',address
            if ack_flag and reply_attempts:
                print 'sending myname ', myname
                reply_attempts = reply_attempts -1
                s.sendto('IAM '+ myname +'\n',address)
                if not reply_attempts:
                    ack_flag = None
        if string[:4] == 'IAM ':     # I've received an answer
            print 'got a reply from ' ,address
            remotedict[address[0]] = string[4:-1]
    if rfd == [] and wfd == [] and efd ==[]:
        print 'breaking'
        break

print remotedict


Now I just have to work out how to switch between these two chunks of
code when a server stops being a wallflower and want's to get
interested in who it can talk to.

Someone will now tell me what fun this all is :-)




More information about the Python-list mailing list