1 # -*- coding: utf-8 -*-
2 # Copyright (c) 2009 Ondřej Súkup
3 # Parallel Python Software: http://www.parallelpython.com
4 # Copyright (c) 2005-2009, Vitalii Vanovschi
6 # Redistribution and use in source and binary forms, with or without
7 # modification, are permitted provided that the following conditions are met:
8 # * Redistributions of source code must retain the above copyright notice,
9 # this list of conditions and the following disclaimer.
10 # * Redistributions in binary form must reproduce the above copyright
11 # notice, this list of conditions and the following disclaimer in the
12 # documentation and/or other materials provided with the distribution.
13 # * Neither the name of the author nor the names of its contributors
14 # may be used to endorse or promote products derived from this software
15 # without specific prior written permission.
17 # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
18 # AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 # ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
21 # LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
22 # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23 # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24 # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
25 # CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26 # ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
27 # THE POSSIBILITY OF SUCH DAMAGE.
36 copyright
= "Copyright (c) 2009 Ondřej Súkup /n \
37 Copyright (c) 2005-2009 Vitalii Vanovschi. All rights reserved"
39 # broadcast every 10 sec
40 BROADCAST_INTERVAL
= 10
43 class Discover(object):
44 """Auto-discovery service class"""
46 def __init__(self
, base
, isclient
=False):
49 self
.isclient
= isclient
51 def run(self
, interface_addr
, broadcast_addr
):
52 """Starts auto-discovery"""
53 self
.interface_addr
= interface_addr
54 self
.broadcast_addr
= broadcast_addr
55 self
.bsocket
= socket
.socket(socket
.AF_INET
, socket
.SOCK_DGRAM
)
56 self
.bsocket
.setsockopt(socket
.SOL_SOCKET
, socket
.SO_REUSEADDR
, 1)
57 self
.bsocket
.setsockopt(socket
.SOL_SOCKET
, socket
.SO_BROADCAST
, 1)
62 sys
.excepthook(*sys
.exc_info())
65 """Sends a broadcast"""
67 logging
.debug("Client sends initial broadcast to (%s, %i)"
68 % self
.broadcast_addr
)
69 self
.bsocket
.sendto("C", self
.broadcast_addr
)
72 logging
.debug("Server sends broadcast to (%s, %i)"
73 % self
.broadcast_addr
)
74 self
.bsocket
.sendto("S", self
.broadcast_addr
)
75 time
.sleep(BROADCAST_INTERVAL
)
78 """Listens for broadcasts from other clients/servers"""
79 logging
.debug("Listening (%s, %i)" % self
.interface_addr
)
80 s
= socket
.socket(socket
.AF_INET
, socket
.SOCK_DGRAM
)
81 s
.setsockopt(socket
.SOL_SOCKET
, socket
.SO_REUSEADDR
, 1)
82 s
.setsockopt(socket
.SOL_SOCKET
, socket
.SO_BROADCAST
, 1)
83 s
.bind(self
.interface_addr
)
85 _thread
.start_new_thread(self
.broadcast
, ())
89 message
, (host
, port
) = s
.recvfrom(1024)
90 remote_address
= (host
, self
.broadcast_addr
[1])
91 hostid
= host
+ ":" + str(self
.broadcast_addr
[1])
92 logging
.debug("Discovered host (%s, %i) message=%c"
93 % (remote_address
+ (message
[0], )))
94 if not self
.base
.autopp_list
.get(hostid
, 0) and self
.isclient \
95 and message
[0] == 'S':
96 logging
.debug("Connecting to host %s" % (hostid
, ))
97 _thread
.start_new_thread(self
.base
.connect1
,
98 remote_address
+(False, ))
99 if not self
.isclient
and message
[0] == 'C':
100 logging
.debug("Replying to host %s" % (hostid
, ))
101 self
.bsocket
.sendto("S", self
.broadcast_addr
)
103 logging
.error("An error has occured during execution of "
105 sys
.excepthook(*sys
.exc_info())