[invirt-dhcp] Improve standards compliance 0.0.3
authorJoshua Oreman <oremanj@mit.edu>
Tue, 29 Sep 2009 02:53:22 +0000 (22:53 -0400)
committerJoshua Oreman <oremanj@mit.edu>
Tue, 29 Sep 2009 02:53:22 +0000 (22:53 -0400)
Provide a server-identifier option containing our IP address, as
is required by several DHCP clients including gPXE (used for the
Debathena network install CD) and Windows.

Reuse the existing DHCP socket in a bindtodevice - sendto - restore
global binding sequence, instead of creating a new socket for each
reply, in order to keep replies coming from port 67. This is required
by the standard, some client programs, and all DHCP forwarders.

svn path=/trunk/packages/invirt-dhcp/; revision=2491

debian/changelog
invirt-dhcpserver

index ea490a8..68c0865 100644 (file)
@@ -1,3 +1,13 @@
+invirt-dhcp (0.0.3) unstable; urgency=low
+
+  * Detect local IP address and pass it as the DHCP server-identifier
+    option, as required by several DHCP clients.
+  * Reuse the existing DHCP socket for replies by binding it to the
+    client VM interface and then restoring its global binding after
+    sendto(); this keeps replies coming from port 67, as is standard.
+
+ -- Joshua Oreman <oremanj@mit.edu>  Mon, 28 Sep 2009 22:46:41 -0400
+
 invirt-dhcp (0.0.2) unstable; urgency=low
 
   * Don't throw a sqlalchemy.exceptions.InvalidRequestError exception if
 invirt-dhcp (0.0.2) unstable; urgency=low
 
   * Don't throw a sqlalchemy.exceptions.InvalidRequestError exception if
index 04376d0..d4e40e0 100755 (executable)
@@ -162,12 +162,9 @@ class DhcpServer(pydhcplib.dhcp_network.DhcpServer):
     def SendDhcpPacketTo(self, To, packet):
         intf = self.backend.find_interface(packet)
         if intf:
     def SendDhcpPacketTo(self, To, packet):
         intf = self.backend.find_interface(packet)
         if intf:
-            out_socket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
-            out_socket.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST,1)
-            out_socket.setsockopt(socket.SOL_SOCKET, IN.SO_BINDTODEVICE, intf)
-            #out_socket.bind((ip, self.listen_port))
-            ret = out_socket.sendto(packet.EncodePacket(), (To,self.emit_port))
-            out_socket.close()
+            self.dhcp_socket.setsockopt(socket.SOL_SOCKET, IN.SO_BINDTODEVICE, intf)
+            ret = self.dhcp_socket.sendto(packet.EncodePacket(), (To,self.emit_port))
+            self.dhcp_socket.setsockopt(socket.SOL_SOCKET, IN.SO_BINDTODEVICE, '')
             return ret
         else:
             return self.dhcp_socket.sendto(packet.EncodePacket(),(To,self.emit_port))
             return ret
         else:
             return self.dhcp_socket.sendto(packet.EncodePacket(),(To,self.emit_port))
@@ -257,6 +254,14 @@ if '__main__' == __name__:
     options = { "server_listen_port":67,
                 "client_listen_port":68,
                 "listen_address":"0.0.0.0"}
     options = { "server_listen_port":67,
                 "client_listen_port":68,
                 "listen_address":"0.0.0.0"}
+
+    myip = socket.gethostbyname(socket.gethostname())
+    if not myip:
+        print "invirt-dhcpserver: cannot determine local IP address by looking up %s" % socket.gethostname()
+        sys.exit(1)
+    
+    dhcp_options['server_identifier'] = myip
+
     backend = DhcpBackend()
     server = DhcpServer(backend, options)
 
     backend = DhcpBackend()
     server = DhcpServer(backend, options)