summaryrefslogtreecommitdiff
path: root/gpxe/src/usr/pxemenu.c
diff options
context:
space:
mode:
authorH. Peter Anvin <hpa@zytor.com>2016-02-09 18:08:47 -0800
committerH. Peter Anvin <hpa@zytor.com>2016-02-09 18:08:47 -0800
commitf2f897a1762fab84d2905f32b1c15dd7b42abb56 (patch)
treea38f51d3f1fcbf44afddb4736d549c12eaf491be /gpxe/src/usr/pxemenu.c
parent72d2959272b4616f17a97667e6dfa9d06bf109a3 (diff)
downloadsyslinux-f2f897a1762fab84d2905f32b1c15dd7b42abb56.tar.gz
gpxe: delete long since obsolete snapshot of gPXE
gPXE has been deprecated in favor of iPXE for many, many years now. It is much better than users get it directly from the iPXE project, since we should no longer need any special modifications for Syslinux use. Signed-off-by: H. Peter Anvin <hpa@zytor.com>
Diffstat (limited to 'gpxe/src/usr/pxemenu.c')
-rw-r--r--gpxe/src/usr/pxemenu.c383
1 files changed, 0 insertions, 383 deletions
diff --git a/gpxe/src/usr/pxemenu.c b/gpxe/src/usr/pxemenu.c
deleted file mode 100644
index 519c200e..00000000
--- a/gpxe/src/usr/pxemenu.c
+++ /dev/null
@@ -1,383 +0,0 @@
-/*
- * Copyright (C) 2009 Michael Brown <mbrown@fensystems.co.uk>.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License as
- * published by the Free Software Foundation; either version 2 of the
- * License, or any later version.
- *
- * This program is distributed in the hope that it will be useful, but
- * WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
- */
-
-FILE_LICENCE ( GPL2_OR_LATER );
-
-#include <stdint.h>
-#include <stdlib.h>
-#include <stdio.h>
-#include <string.h>
-#include <errno.h>
-#include <ctype.h>
-#include <byteswap.h>
-#include <curses.h>
-#include <console.h>
-#include <gpxe/dhcp.h>
-#include <gpxe/keys.h>
-#include <gpxe/timer.h>
-#include <gpxe/process.h>
-#include <usr/dhcpmgmt.h>
-#include <usr/autoboot.h>
-
-/** @file
- *
- * PXE Boot Menus
- *
- */
-
-/* Colour pairs */
-#define CPAIR_NORMAL 1
-#define CPAIR_SELECT 2
-
-/** A PXE boot menu item */
-struct pxe_menu_item {
- /** Boot Server type */
- unsigned int type;
- /** Description */
- char *desc;
-};
-
-/**
- * A PXE boot menu
- *
- * This structure encapsulates the menu information provided via DHCP
- * options.
- */
-struct pxe_menu {
- /** Prompt string (optional) */
- const char *prompt;
- /** Timeout (in seconds)
- *
- * Negative indicates no timeout (i.e. wait indefinitely)
- */
- int timeout;
- /** Number of menu items */
- unsigned int num_items;
- /** Selected menu item */
- unsigned int selection;
- /** Menu items */
- struct pxe_menu_item items[0];
-};
-
-/**
- * Parse and allocate PXE boot menu
- *
- * @v menu PXE boot menu to fill in
- * @ret rc Return status code
- *
- * It is the callers responsibility to eventually free the allocated
- * boot menu.
- */
-static int pxe_menu_parse ( struct pxe_menu **menu ) {
- struct setting pxe_boot_menu_prompt_setting =
- { .tag = DHCP_PXE_BOOT_MENU_PROMPT };
- struct setting pxe_boot_menu_setting =
- { .tag = DHCP_PXE_BOOT_MENU };
- uint8_t raw_menu[256];
- int raw_prompt_len;
- int raw_menu_len;
- struct dhcp_pxe_boot_menu *raw_menu_item;
- struct dhcp_pxe_boot_menu_prompt *raw_menu_prompt;
- void *raw_menu_end;
- unsigned int num_menu_items;
- unsigned int i;
- int rc;
-
- /* Fetch raw menu */
- memset ( raw_menu, 0, sizeof ( raw_menu ) );
- if ( ( raw_menu_len = fetch_setting ( NULL, &pxe_boot_menu_setting,
- raw_menu,
- sizeof ( raw_menu ) ) ) < 0 ) {
- rc = raw_menu_len;
- DBG ( "Could not retrieve raw PXE boot menu: %s\n",
- strerror ( rc ) );
- return rc;
- }
- if ( raw_menu_len >= ( int ) sizeof ( raw_menu ) ) {
- DBG ( "Raw PXE boot menu too large for buffer\n" );
- return -ENOSPC;
- }
- raw_menu_end = ( raw_menu + raw_menu_len );
-
- /* Fetch raw prompt length */
- raw_prompt_len = fetch_setting_len ( NULL,
- &pxe_boot_menu_prompt_setting );
- if ( raw_prompt_len < 0 )
- raw_prompt_len = 0;
-
- /* Count menu items */
- num_menu_items = 0;
- raw_menu_item = ( ( void * ) raw_menu );
- while ( 1 ) {
- if ( ( ( ( void * ) raw_menu_item ) +
- sizeof ( *raw_menu_item ) ) > raw_menu_end )
- break;
- if ( ( ( ( void * ) raw_menu_item ) +
- sizeof ( *raw_menu_item ) +
- raw_menu_item->desc_len ) > raw_menu_end )
- break;
- num_menu_items++;
- raw_menu_item = ( ( ( void * ) raw_menu_item ) +
- sizeof ( *raw_menu_item ) +
- raw_menu_item->desc_len );
- }
-
- /* Allocate space for parsed menu */
- *menu = zalloc ( sizeof ( **menu ) +
- ( num_menu_items * sizeof ( (*menu)->items[0] ) ) +
- raw_menu_len + 1 /* NUL */ +
- raw_prompt_len + 1 /* NUL */ );
- if ( ! *menu ) {
- DBG ( "Could not allocate PXE boot menu\n" );
- return -ENOMEM;
- }
-
- /* Fill in parsed menu */
- (*menu)->num_items = num_menu_items;
- raw_menu_item = ( ( ( void * ) (*menu) ) + sizeof ( **menu ) +
- ( num_menu_items * sizeof ( (*menu)->items[0] ) ) );
- memcpy ( raw_menu_item, raw_menu, raw_menu_len );
- for ( i = 0 ; i < num_menu_items ; i++ ) {
- (*menu)->items[i].type = le16_to_cpu ( raw_menu_item->type );
- (*menu)->items[i].desc = raw_menu_item->desc;
- /* Set type to 0; this ensures that the description
- * for the previous menu item is NUL-terminated.
- * (Final item is NUL-terminated anyway.)
- */
- raw_menu_item->type = 0;
- raw_menu_item = ( ( ( void * ) raw_menu_item ) +
- sizeof ( *raw_menu_item ) +
- raw_menu_item->desc_len );
- }
- if ( raw_prompt_len ) {
- raw_menu_prompt = ( ( ( void * ) raw_menu_item ) +
- 1 /* NUL */ );
- fetch_setting ( NULL, &pxe_boot_menu_prompt_setting,
- raw_menu_prompt, raw_prompt_len );
- (*menu)->timeout =
- ( ( raw_menu_prompt->timeout == 0xff ) ?
- -1 : raw_menu_prompt->timeout );
- (*menu)->prompt = raw_menu_prompt->prompt;
- } else {
- (*menu)->timeout = -1;
- }
-
- return 0;
-}
-
-/**
- * Draw PXE boot menu item
- *
- * @v menu PXE boot menu
- * @v index Index of item to draw
- * @v selected Item is selected
- */
-static void pxe_menu_draw_item ( struct pxe_menu *menu,
- unsigned int index, int selected ) {
- char buf[COLS+1];
- size_t len;
- unsigned int row;
-
- /* Prepare space-padded row content */
- len = snprintf ( buf, sizeof ( buf ), " %c. %s",
- ( 'A' + index ), menu->items[index].desc );
- while ( len < ( sizeof ( buf ) - 1 ) )
- buf[len++] = ' ';
- buf[ sizeof ( buf ) - 1 ] = '\0';
-
- /* Draw row */
- row = ( LINES - menu->num_items + index );
- color_set ( ( selected ? CPAIR_SELECT : CPAIR_NORMAL ), NULL );
- mvprintw ( row, 0, "%s", buf );
- move ( row, 1 );
-}
-
-/**
- * Make selection from PXE boot menu
- *
- * @v menu PXE boot menu
- * @ret rc Return status code
- */
-static int pxe_menu_select ( struct pxe_menu *menu ) {
- int key;
- unsigned int key_selection;
- unsigned int i;
- int rc = 0;
-
- /* Initialise UI */
- initscr();
- start_color();
- init_pair ( CPAIR_NORMAL, COLOR_WHITE, COLOR_BLACK );
- init_pair ( CPAIR_SELECT, COLOR_BLACK, COLOR_WHITE );
- color_set ( CPAIR_NORMAL, NULL );
-
- /* Draw initial menu */
- for ( i = 0 ; i < menu->num_items ; i++ )
- printf ( "\n" );
- for ( i = 0 ; i < menu->num_items ; i++ )
- pxe_menu_draw_item ( menu, ( menu->num_items - i - 1 ), 0 );
-
- while ( 1 ) {
-
- /* Highlight currently selected item */
- pxe_menu_draw_item ( menu, menu->selection, 1 );
-
- /* Wait for keyboard input */
- while ( ! iskey() )
- step();
- key = getkey();
-
- /* Unhighlight currently selected item */
- pxe_menu_draw_item ( menu, menu->selection, 0 );
-
- /* Act upon key */
- if ( ( key == CR ) || ( key == LF ) ) {
- pxe_menu_draw_item ( menu, menu->selection, 1 );
- break;
- } else if ( ( key == CTRL_C ) || ( key == ESC ) ) {
- rc = -ECANCELED;
- break;
- } else if ( key == KEY_UP ) {
- if ( menu->selection > 0 )
- menu->selection--;
- } else if ( key == KEY_DOWN ) {
- if ( menu->selection < ( menu->num_items - 1 ) )
- menu->selection++;
- } else if ( ( key < KEY_MIN ) &&
- ( ( key_selection = ( toupper ( key ) - 'A' ) )
- < menu->num_items ) ) {
- menu->selection = key_selection;
- pxe_menu_draw_item ( menu, menu->selection, 1 );
- break;
- }
- }
-
- /* Shut down UI */
- endwin();
-
- return rc;
-}
-
-/**
- * Prompt for (and make selection from) PXE boot menu
- *
- * @v menu PXE boot menu
- * @ret rc Return status code
- */
-static int pxe_menu_prompt_and_select ( struct pxe_menu *menu ) {
- unsigned long start = currticks();
- unsigned long now;
- unsigned long elapsed;
- size_t len = 0;
- int key;
- int rc = 0;
-
- /* Display menu immediately, if specified to do so */
- if ( menu->timeout < 0 ) {
- if ( menu->prompt )
- printf ( "%s\n", menu->prompt );
- return pxe_menu_select ( menu );
- }
-
- /* Display prompt, if specified */
- if ( menu->prompt )
- printf ( "%s", menu->prompt );
-
- /* Wait for timeout, if specified */
- while ( menu->timeout > 0 ) {
- if ( ! len )
- len = printf ( " (%d)", menu->timeout );
- if ( iskey() ) {
- key = getkey();
- if ( key == KEY_F8 ) {
- /* Display menu */
- printf ( "\n" );
- return pxe_menu_select ( menu );
- } else if ( ( key == CTRL_C ) || ( key == ESC ) ) {
- /* Abort */
- rc = -ECANCELED;
- break;
- } else {
- /* Stop waiting */
- break;
- }
- }
- now = currticks();
- elapsed = ( now - start );
- if ( elapsed >= TICKS_PER_SEC ) {
- menu->timeout -= 1;
- do {
- printf ( "\b \b" );
- } while ( --len );
- start = now;
- }
- }
-
- /* Return with default option selected */
- printf ( "\n" );
- return rc;
-}
-
-/**
- * Boot using PXE boot menu
- *
- * @ret rc Return status code
- *
- * Note that a success return status indicates that a PXE boot menu
- * item has been selected, and that the DHCP session should perform a
- * boot server request/ack.
- */
-int pxe_menu_boot ( struct net_device *netdev ) {
- struct pxe_menu *menu;
- unsigned int pxe_type;
- struct settings *pxebs_settings;
- struct in_addr next_server;
- char filename[256];
- int rc;
-
- /* Parse and allocate boot menu */
- if ( ( rc = pxe_menu_parse ( &menu ) ) != 0 )
- return rc;
-
- /* Make selection from boot menu */
- if ( ( rc = pxe_menu_prompt_and_select ( menu ) ) != 0 ) {
- free ( menu );
- return rc;
- }
- pxe_type = menu->items[menu->selection].type;
-
- /* Free boot menu */
- free ( menu );
-
- /* Return immediately if local boot selected */
- if ( ! pxe_type )
- return 0;
-
- /* Attempt PXE Boot Server Discovery */
- if ( ( rc = pxebs ( netdev, pxe_type ) ) != 0 )
- return rc;
-
- /* Attempt boot */
- pxebs_settings = find_settings ( PXEBS_SETTINGS_NAME );
- assert ( pxebs_settings );
- fetch_ipv4_setting ( pxebs_settings, &next_server_setting,
- &next_server );
- fetch_string_setting ( pxebs_settings, &filename_setting,
- filename, sizeof ( filename ) );
- return boot_next_server_and_filename ( next_server, filename );
-}