aboutsummaryrefslogtreecommitdiffstats
path: root/src/hci/commands/dhcp_cmd.c
diff options
context:
space:
mode:
authorMichael Brown <mcb30@etherboot.org>2009-01-31 07:36:05 +0000
committerMichael Brown <mcb30@etherboot.org>2009-02-01 01:21:40 +0000
commite65afc4b10552ec9ac7de2f0d924b96bc71aaad0 (patch)
tree36e528a6d947aa8701208953e74cd496728955b4 /src/hci/commands/dhcp_cmd.c
parentd2b0081740de9e31fb28f7c6761bbf78835c07d7 (diff)
downloadipxe-e65afc4b10552ec9ac7de2f0d924b96bc71aaad0.tar.gz
[dhcp] Split PXE menuing code out of dhcp.c
The DHCP client code now implements only the mechanism of the DHCP and PXE Boot Server protocols. Boot Server Discovery can be initiated manually using the "pxebs" command. The menuing code is separated out into a user-level function on a par with boot_root_path(), and is entered in preference to a normal filename boot if the DHCP vendor class is "PXEClient" and the PXE boot menu option exists.
Diffstat (limited to 'src/hci/commands/dhcp_cmd.c')
-rw-r--r--src/hci/commands/dhcp_cmd.c99
1 files changed, 94 insertions, 5 deletions
diff --git a/src/hci/commands/dhcp_cmd.c b/src/hci/commands/dhcp_cmd.c
index 07acc615c..b44433e7d 100644
--- a/src/hci/commands/dhcp_cmd.c
+++ b/src/hci/commands/dhcp_cmd.c
@@ -26,6 +26,7 @@
#include <assert.h>
#include <getopt.h>
#include <gpxe/netdevice.h>
+#include <gpxe/in.h>
#include <gpxe/command.h>
#include <usr/dhcpmgmt.h>
@@ -60,7 +61,7 @@ static int dhcp_exec ( int argc, char **argv ) {
{ "help", 0, NULL, 'h' },
{ NULL, 0, NULL, 0 },
};
- const char *name;
+ const char *netdev_txt;
struct net_device *netdev;
int c;
int rc;
@@ -82,14 +83,16 @@ static int dhcp_exec ( int argc, char **argv ) {
dhcp_syntax ( argv );
return 1;
}
- name = argv[optind];
+ netdev_txt = argv[optind];
- /* Perform DHCP */
- netdev = find_netdev ( name );
+ /* Parse arguments */
+ netdev = find_netdev ( netdev_txt );
if ( ! netdev ) {
- printf ( "No such interface: %s\n", name );
+ printf ( "No such interface: %s\n", netdev_txt );
return 1;
}
+
+ /* Perform DHCP */
if ( ( rc = dhcp ( netdev ) ) != 0 ) {
printf ( "Could not configure %s: %s\n", netdev->name,
strerror ( rc ) );
@@ -99,10 +102,96 @@ static int dhcp_exec ( int argc, char **argv ) {
return 0;
}
+/**
+ * "pxebs" command syntax message
+ *
+ * @v argv Argument list
+ */
+static void pxebs_syntax ( char **argv ) {
+ printf ( "Usage:\n"
+ " %s <interface> <discovery_ip> <server_type>\n"
+ "\n"
+ "Perform PXE Boot Server discovery\n",
+ argv[0] );
+}
+
+/**
+ * The "pxebs" command
+ *
+ * @v argc Argument count
+ * @v argv Argument list
+ * @ret rc Exit code
+ */
+static int pxebs_exec ( int argc, char **argv ) {
+ static struct option longopts[] = {
+ { "help", 0, NULL, 'h' },
+ { NULL, 0, NULL, 0 },
+ };
+ const char *netdev_txt;
+ const char *pxe_server_txt;
+ const char *pxe_type_txt;
+ struct net_device *netdev;
+ struct in_addr pxe_server;
+ unsigned int pxe_type;
+ char *end;
+ int c;
+ int rc;
+
+ /* Parse options */
+ while ( ( c = getopt_long ( argc, argv, "h", longopts, NULL ) ) >= 0 ){
+ switch ( c ) {
+ case 'h':
+ /* Display help text */
+ default:
+ /* Unrecognised/invalid option */
+ pxebs_syntax ( argv );
+ return 1;
+ }
+ }
+
+ /* Need exactly one interface name remaining after the options */
+ if ( optind != ( argc - 3 ) ) {
+ pxebs_syntax ( argv );
+ return 1;
+ }
+ netdev_txt = argv[optind];
+ pxe_server_txt = argv[ optind + 1 ];
+ pxe_type_txt = argv[ optind + 2 ];
+
+ /* Parse arguments */
+ netdev = find_netdev ( netdev_txt );
+ if ( ! netdev ) {
+ printf ( "No such interface: %s\n", netdev_txt );
+ return 1;
+ }
+ if ( inet_aton ( pxe_server_txt, &pxe_server ) == 0 ) {
+ printf ( "Bad discovery IP address: %s\n", pxe_server_txt );
+ return 1;
+ }
+ pxe_type = strtoul ( pxe_type_txt, &end, 0 );
+ if ( *end ) {
+ printf ( "Bad server type: %s\n", pxe_type_txt );
+ return 1;
+ }
+
+ /* Perform Boot Server Discovery */
+ if ( ( rc = pxebs ( netdev, pxe_server, pxe_type ) ) != 0 ) {
+ printf ( "Could not discover boot server on %s: %s\n",
+ netdev->name, strerror ( rc ) );
+ return 1;
+ }
+
+ return 0;
+}
+
/** DHCP management commands */
struct command dhcp_commands[] __command = {
{
.name = "dhcp",
.exec = dhcp_exec,
},
+ {
+ .name = "pxebs",
+ .exec = pxebs_exec,
+ },
};