2121import netifaces
2222import ipaddress
2323
24+ from .Encoding import *
2425from .MessageReceiver import *
2526
2627class DiscoveryClient (MessageReceiver ):
2728 MSG_DISCOVERY_PORT = 5466
2829
2930 def __init__ (self , address_list , on_device_discovered ):
30- super ().__init__ (self . send_broadcast , self . message_received , None )
31+ super ().__init__ ()
3132
3233 self .address_list = address_list
3334 self .on_device_discovered = on_device_discovered
3435
35- def datagram_received ( self , data , addr ):
36- self . remote_addr = addr
37- super (). bytes_received ( data )
36+ @ staticmethod
37+ async def create ( addr , callback ):
38+ loop = asyncio . get_running_loop ( )
3839
39- self .status = MsgRxStatus .MSG_RX_MAGIC
40- self .buffer = b"\x00 \x00 \x00 \x00 "
40+ _ , protocol = await loop .create_datagram_endpoint (
41+ lambda : DiscoveryClient (addr , callback ),
42+ remote_addr = None ,
43+ family = socket .AF_INET ,
44+ allow_broadcast = True
45+ )
46+
47+ return protocol
48+
49+ def connection_made (self , transport ):
50+ super ().connection_made (transport )
4151
42- def send_broadcast (self ):
4352 self .validator = random .randint (0 , 2 ** 64 - 1 )
4453
4554 message = MessageReceiver .MSG_MAGIC_IDENTIFIER
46- message += Messages .MSG_ID_DISCOVERY . to_bytes ( 2 , byteorder = "little" )
47- message += b" \x08 \x00 "
48- message += self .validator . to_bytes ( 8 , byteorder = "little" )
55+ message += encode_u16 ( Messages .MSG_ID_DISCOVERY )
56+ message += encode_u16 ( 8 )
57+ message += encode_u64 ( self .validator )
4958
5059 for address in self .address_list :
5160 self .transport .sendto (message , (address , DiscoveryClient .MSG_DISCOVERY_PORT ))
5261
62+ def datagram_received (self , data , addr ):
63+ self .remote_addr = addr
64+ super ().bytes_received (data )
65+
66+ self .status = MsgRxStatus .MSG_RX_MAGIC
67+ self .buffer = b"\x00 \x00 \x00 \x00 "
68+
69+ def error_received (self , err ):
70+ pass
71+
72+ def connection_lost (self , exc ):
73+ pass
74+
5375 def message_received (self , msg_id , msg_payload ):
5476 if msg_id != Messages .MSG_ID_DISCOVERY or len (msg_payload ) <= 67 :
5577 return
5678
57- validator = int . from_bytes (msg_payload [0 :8 ], byteorder = 'little' , signed = False )
79+ validator = decode_u64 (msg_payload [0 :8 ])
5880
5981 if validator != self .validator :
6082 return
@@ -64,7 +86,7 @@ def message_received(self, msg_id, msg_payload):
6486 device ["version" ] = (
6587 msg_payload [11 ],
6688 msg_payload [10 ],
67- int . from_bytes (msg_payload [8 :10 ], byteorder = 'little' , signed = False ),
89+ decode_u16 (msg_payload [8 :10 ]),
6890 msg_payload [12 :28 ].strip (b"\x00 " ).decode ("UTF-8" ),
6991 msg_payload [28 :44 ].strip (b"\x00 " ).decode ("UTF-8" ),
7092 "d" if msg_payload [44 ] else ""
@@ -101,24 +123,11 @@ def message_received(self, msg_id, msg_payload):
101123 return
102124
103125 device ["address" ] = address_list
104- device ["port" ] = int . from_bytes (msg_payload [65 :67 ], byteorder = 'little' , signed = False )
126+ device ["port" ] = decode_u16 (msg_payload [65 :67 ])
105127 device ["name" ] = msg_payload [67 :].decode ("UTF-8" )
106128
107129 self .on_device_discovered (device )
108130
109- @staticmethod
110- async def create (addr , callback ):
111- loop = asyncio .get_running_loop ()
112-
113- _ , protocol = await loop .create_datagram_endpoint (
114- lambda : DiscoveryClient (addr , callback ),
115- remote_addr = None ,
116- family = socket .AF_INET ,
117- allow_broadcast = True
118- )
119-
120- return protocol
121-
122131async def discover_devices (timeout ):
123132 address_list = []
124133 device_list = []
0 commit comments