[dhcp] Handle missing ProxyDHCP servers
authorMichael Brown <mcb30@etherboot.org>
Fri, 23 Jan 2009 01:32:04 +0000 (01:32 +0000)
committerMichael Brown <mcb30@etherboot.org>
Fri, 23 Jan 2009 01:32:04 +0000 (01:32 +0000)
It is possible to configure a DHCP server to hand out PXE options
without a ProxyDHCP server present.  This requires setting option 60
to "PXEClient", which will cause gPXE to attempt ProxyDHCP.

We assume in several places that dhcp->proxydhcpack is set to the
DHCPACK packet containing option 60 set to "PXEClient".  When we
transition into ProxyDHCPREQUEST, set dhcp->proxydhcpack=dhcp->dhcpack
so that this assumption holds true.

We ought to rename several references to "proxydhcp" to something more
accurate, such as "pxedhcp".  Treating a single DHCP response as
potentially both DHCPOFFER and ProxyDHCPOFFER does make the code
smaller, but the variable names get confusing.

src/net/udp/dhcp.c

index 4955ea1..14de828 100644 (file)
@@ -745,6 +745,13 @@ static void dhcp_next_state ( struct dhcp_session *dhcp ) {
                break;
        case DHCP_STATE_REQUEST:
                if ( dhcp->proxydhcpoffer ) {
+                       /* Store DHCPACK as ProxyDHCPACK.  This
+                        * handles the case in which the DHCP server
+                        * itself responds with "PXEClient" and PXE
+                        * options but there is no actual ProxyDHCP
+                        * server resident on the machine.
+                        */
+                       dhcp->proxydhcpack = dhcpset_get ( dhcp->dhcpack );
                        dhcp_set_state ( dhcp, DHCP_STATE_PROXYREQUEST );
                        break;
                }
@@ -990,7 +997,7 @@ static void dhcp_rx_proxydhcpack ( struct dhcp_session *dhcp,
        proxydhcpack->settings.name = PROXYDHCP_SETTINGS_NAME;
 
        /* Record ProxyDHCPACK */
-       assert ( dhcp->proxydhcpack == NULL );
+       dhcpset_put ( dhcp->proxydhcpack );
        dhcp->proxydhcpack = dhcpset_get ( proxydhcpack );
 
        /* Register settings */