2009-01-31 Colin D Bennett <colin@gibibit.com>
* normal/main.c: Add include to grub/menu_viewer.h. (free_menu_entry_classes): Added. (grub_normal_menu_addentry): Added class property handling. (grub_normal_execute): Changed to use new menu viewer for menu viewing. (GRUB_MOD_INIT(normal)): Added register for text based menu viewer. * normal/menu_viewer.c: New file. * normal/menu.c (run_menu_entry): Renamed to ... (grub_menu_execute_entry): ... this and made it as global. (grub_menu_run): Renamed to ... (show_text_menu): ... this and made it local. (show_text_menu): Adapt to new function names. (grub_normal_terminal_menu_viewer): New global variable. * include/grub/menu.h: New file. * include/grub/menu_viewer.h: New file. * include/grub/normal.h: Added include to grub/menu.h. (grub_menu_entry): Moved to include/grub/menu.h. (grub_menu_entry_t): Likewise. (grub_menu): Likewise. (grub_menu_t): Likewise. (grub_normal_terminal_menu_viewer): Added. (grub_menu_execute_entry): Likewise. (grub_menu_run): Removed. * DISTLIST: Added include/grub/menu.h. Added include/grub/menu_viewer.h. Added normal/menu_viewer.c. 2009-01-31 Vesa Jääskeläinen <chaac@nic.fi> * normal/execute.c (grub_script_execute_menuentry): Changed to use arglist for menutitle arguments. * normal/main.c (grub_normal_menu_addentry): Likewise. * normal/parser.y (menuentry): Likewise. * normal/script.c (grub_script_create_cmdmenu): Likewise. * include/grub/script.h (grub_script_cmd_menuentry): Likewise. (grub_script_create_cmdmenu): Likewise. * include/grub/normal.h (grub_normal_menu_addentry): Likewise. * conf/i386-pc.rmk (normal_mod_SOURCES): Adapt Colin D Bennett's changes. * conf/x86_64-efi.rmk (normal_mod_SOURCES): Likewise. * conf/i386-coreboot.rmk (normal_mod_SOURCES): Likewise. * conf/i386-efi.rmk (normal_mod_SOURCES): Likewise. * conf/i386-ieee1275.rmk (normal_mod_SOURCES): Likewise. * conf/powerpc-ieee1275.rmk (normal_mod_SOURCES): Likewise. * conf/sparc64-ieee1275.rmk (normal_mod_SOURCES): Likewise.
This commit is contained in:
parent
56192c2346
commit
6fa42fa65a
26 changed files with 934 additions and 301 deletions
|
@ -1,7 +1,7 @@
|
|||
/* execute.c -- Execute a GRUB script. */
|
||||
/*
|
||||
* GRUB -- GRand Unified Bootloader
|
||||
* Copyright (C) 2005,2007,2008 Free Software Foundation, Inc.
|
||||
* Copyright (C) 2005,2007,2008,2009 Free Software Foundation, Inc.
|
||||
*
|
||||
* GRUB is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
|
@ -148,11 +148,11 @@ grub_script_execute_cmdline (struct grub_script_cmd *cmd)
|
|||
parser = (struct grub_arg_option *) grubcmd->options;
|
||||
while (parser && (parser++)->doc)
|
||||
maxargs++;
|
||||
|
||||
|
||||
/* Set up the option state. */
|
||||
state = grub_malloc (sizeof (struct grub_arg_list) * maxargs);
|
||||
grub_memset (state, 0, sizeof (struct grub_arg_list) * maxargs);
|
||||
|
||||
|
||||
/* Start the command. */
|
||||
if (! (grubcmd->flags & GRUB_COMMAND_FLAG_NO_ARG_PARSE))
|
||||
{
|
||||
|
@ -161,7 +161,7 @@ grub_script_execute_cmdline (struct grub_script_cmd *cmd)
|
|||
}
|
||||
else
|
||||
ret = (grubcmd->func) (state, argcount, args);
|
||||
|
||||
|
||||
grub_free (state);
|
||||
}
|
||||
else
|
||||
|
@ -178,7 +178,7 @@ grub_script_execute_cmdline (struct grub_script_cmd *cmd)
|
|||
return ret;
|
||||
}
|
||||
|
||||
/* Execute a block of one or more commands. */
|
||||
/* Execute a block of one or more commands. */
|
||||
grub_err_t
|
||||
grub_script_execute_cmdblock (struct grub_script_cmd *cmd)
|
||||
{
|
||||
|
@ -216,32 +216,53 @@ grub_err_t
|
|||
grub_script_execute_menuentry (struct grub_script_cmd *cmd)
|
||||
{
|
||||
struct grub_script_cmd_menuentry *cmd_menuentry;
|
||||
char *title;
|
||||
struct grub_script_arglist *arglist;
|
||||
struct grub_script *script;
|
||||
char **args = 0;
|
||||
int argcount = 0;
|
||||
int i = 0;
|
||||
|
||||
cmd_menuentry = (struct grub_script_cmd_menuentry *) cmd;
|
||||
|
||||
/* The title can contain variables, parse them and generate a string
|
||||
from it. */
|
||||
title = grub_script_execute_argument_to_string (cmd_menuentry->title);
|
||||
if (! title)
|
||||
return grub_errno;
|
||||
if (cmd_menuentry->arglist)
|
||||
{
|
||||
argcount = cmd_menuentry->arglist->argcount;
|
||||
|
||||
/* Create argv from the arguments. */
|
||||
args = grub_malloc (sizeof (char *) * argcount);
|
||||
|
||||
if (! args)
|
||||
{
|
||||
return grub_errno;
|
||||
}
|
||||
|
||||
for (arglist = cmd_menuentry->arglist; arglist; arglist = arglist->next)
|
||||
{
|
||||
char *str;
|
||||
str = grub_script_execute_argument_to_string (arglist->arg);
|
||||
args[i++] = str;
|
||||
}
|
||||
}
|
||||
|
||||
/* Parse the menu entry *again*. */
|
||||
script = grub_script_parse ((char *) cmd_menuentry->sourcecode, 0);
|
||||
|
||||
if (! script)
|
||||
/* Add new menu entry. */
|
||||
if (script)
|
||||
{
|
||||
grub_free (title);
|
||||
return grub_errno;
|
||||
grub_normal_menu_addentry (argcount, (const char **)args,
|
||||
script, cmd_menuentry->sourcecode);
|
||||
}
|
||||
|
||||
/* XXX: When this fails, the memory should be freed? */
|
||||
return grub_normal_menu_addentry (title, script,
|
||||
cmd_menuentry->sourcecode);
|
||||
/* Free arguments. */
|
||||
for (i = 0; i < argcount; i++)
|
||||
grub_free (args[i]);
|
||||
grub_free (args);
|
||||
|
||||
return grub_errno;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/* Execute any GRUB pre-parsed command or script. */
|
||||
grub_err_t
|
||||
|
|
115
normal/main.c
115
normal/main.c
|
@ -1,7 +1,7 @@
|
|||
/* main.c - the normal mode main routine */
|
||||
/*
|
||||
* GRUB -- GRand Unified Bootloader
|
||||
* Copyright (C) 2000,2001,2002,2003,2005,2006,2007,2008 Free Software Foundation, Inc.
|
||||
* Copyright (C) 2000,2001,2002,2003,2005,2006,2007,2008,2009 Free Software Foundation, Inc.
|
||||
*
|
||||
* GRUB is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
|
@ -28,6 +28,7 @@
|
|||
#include <grub/env.h>
|
||||
#include <grub/parser.h>
|
||||
#include <grub/script.h>
|
||||
#include <grub/menu_viewer.h>
|
||||
|
||||
grub_jmp_buf grub_exit_env;
|
||||
|
||||
|
@ -147,14 +148,41 @@ free_menu (grub_menu_t menu)
|
|||
grub_env_unset_data_slot ("menu");
|
||||
}
|
||||
|
||||
static void
|
||||
free_menu_entry_classes (struct grub_menu_entry_class *head)
|
||||
{
|
||||
/* Free all the classes. */
|
||||
while (head)
|
||||
{
|
||||
struct grub_menu_entry_class *next;
|
||||
|
||||
grub_free (head->name);
|
||||
next = head->next;
|
||||
grub_free (head);
|
||||
head = next;
|
||||
}
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_normal_menu_addentry (const char *title, struct grub_script *script,
|
||||
grub_normal_menu_addentry (int argc, const char **args, struct grub_script *script,
|
||||
const char *sourcecode)
|
||||
{
|
||||
const char *menutitle;
|
||||
const char *menutitle = 0;
|
||||
const char *menusourcecode;
|
||||
grub_menu_t menu;
|
||||
grub_menu_entry_t *last;
|
||||
int failed = 0;
|
||||
int i;
|
||||
struct grub_menu_entry_class *classes_head; /* Dummy head node for list. */
|
||||
struct grub_menu_entry_class *classes_tail;
|
||||
|
||||
/* Allocate dummy head node for class list. */
|
||||
classes_head = grub_malloc (sizeof (struct grub_menu_entry_class));
|
||||
if (! classes_head)
|
||||
return grub_errno;
|
||||
classes_head->name = 0;
|
||||
classes_head->next = 0;
|
||||
classes_tail = classes_head;
|
||||
|
||||
menu = grub_env_get_data_slot("menu");
|
||||
if (! menu)
|
||||
|
@ -166,10 +194,81 @@ grub_normal_menu_addentry (const char *title, struct grub_script *script,
|
|||
if (! menusourcecode)
|
||||
return grub_errno;
|
||||
|
||||
menutitle = grub_strdup (title);
|
||||
if (! menutitle)
|
||||
/* Parse menu arguments. */
|
||||
for (i = 0; i < argc; i++)
|
||||
{
|
||||
/* Capture arguments. */
|
||||
if (grub_strncmp ("--", args[i], 2) == 0)
|
||||
{
|
||||
const char *arg = &args[i][2];
|
||||
|
||||
/* Handle menu class. */
|
||||
if (grub_strcmp(arg, "class") == 0)
|
||||
{
|
||||
char *class_name;
|
||||
struct grub_menu_entry_class *new_class;
|
||||
|
||||
i++;
|
||||
class_name = grub_strdup (args[i]);
|
||||
if (! class_name)
|
||||
{
|
||||
failed = 1;
|
||||
break;
|
||||
}
|
||||
|
||||
/* Create a new class and add it at the tail of the list. */
|
||||
new_class = grub_malloc (sizeof (struct grub_menu_entry_class));
|
||||
if (! new_class)
|
||||
{
|
||||
grub_free (class_name);
|
||||
failed = 1;
|
||||
break;
|
||||
}
|
||||
/* Fill in the new class node. */
|
||||
new_class->name = class_name;
|
||||
new_class->next = 0;
|
||||
/* Link the tail to it, and make it the new tail. */
|
||||
classes_tail->next = new_class;
|
||||
classes_tail = new_class;
|
||||
continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Handle invalid argument. */
|
||||
failed = 1;
|
||||
grub_error (GRUB_ERR_MENU, "invalid argument for menuentry: %s", args[i]);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Capture title. */
|
||||
if (! menutitle)
|
||||
{
|
||||
menutitle = grub_strdup (args[i]);
|
||||
}
|
||||
else
|
||||
{
|
||||
failed = 1;
|
||||
grub_error (GRUB_ERR_MENU, "too many titles for menuentry: %s", args[i]);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Validate arguments. */
|
||||
if ((! failed) && (! menutitle))
|
||||
{
|
||||
grub_error (GRUB_ERR_MENU, "menuentry is missing title");
|
||||
failed = 1;
|
||||
}
|
||||
|
||||
/* If argument parsing failed, free any allocated resources. */
|
||||
if (failed)
|
||||
{
|
||||
free_menu_entry_classes (classes_head);
|
||||
grub_free ((void *) menutitle);
|
||||
grub_free ((void *) menusourcecode);
|
||||
|
||||
/* Here we assume that grub_error has been used to specify failure details. */
|
||||
return grub_errno;
|
||||
}
|
||||
|
||||
|
@ -180,6 +279,7 @@ grub_normal_menu_addentry (const char *title, struct grub_script *script,
|
|||
*last = grub_malloc (sizeof (**last));
|
||||
if (! *last)
|
||||
{
|
||||
free_menu_entry_classes (classes_head);
|
||||
grub_free ((void *) menutitle);
|
||||
grub_free ((void *) menusourcecode);
|
||||
return grub_errno;
|
||||
|
@ -187,6 +287,7 @@ grub_normal_menu_addentry (const char *title, struct grub_script *script,
|
|||
|
||||
(*last)->commands = script;
|
||||
(*last)->title = menutitle;
|
||||
(*last)->classes = classes_head;
|
||||
(*last)->next = 0;
|
||||
(*last)->sourcecode = menusourcecode;
|
||||
|
||||
|
@ -476,7 +577,7 @@ grub_normal_execute (const char *config, int nested)
|
|||
|
||||
if (menu && menu->size)
|
||||
{
|
||||
grub_menu_run (menu, nested);
|
||||
grub_menu_viewer_show_menu (menu, nested);
|
||||
if (nested)
|
||||
free_menu (menu);
|
||||
}
|
||||
|
@ -519,6 +620,8 @@ GRUB_MOD_INIT(normal)
|
|||
if (mod)
|
||||
grub_dl_ref (mod);
|
||||
|
||||
grub_menu_viewer_register (&grub_normal_terminal_menu_viewer);
|
||||
|
||||
grub_set_history (GRUB_DEFAULT_HISTORY_SIZE);
|
||||
|
||||
/* Register a command "normal" for the rescue mode. */
|
||||
|
|
|
@ -24,6 +24,7 @@
|
|||
#include <grub/time.h>
|
||||
#include <grub/env.h>
|
||||
#include <grub/script.h>
|
||||
#include <grub/menu_viewer.h>
|
||||
|
||||
static grub_uint8_t grub_color_menu_normal;
|
||||
static grub_uint8_t grub_color_menu_highlight;
|
||||
|
@ -41,9 +42,9 @@ static void
|
|||
draw_border (void)
|
||||
{
|
||||
unsigned i;
|
||||
|
||||
|
||||
grub_setcolorstate (GRUB_TERM_COLOR_NORMAL);
|
||||
|
||||
|
||||
grub_gotoxy (GRUB_TERM_MARGIN, GRUB_TERM_TOP_BORDER_Y);
|
||||
grub_putcode (GRUB_TERM_DISP_UL);
|
||||
for (i = 0; i < (unsigned) GRUB_TERM_BORDER_WIDTH - 2; i++)
|
||||
|
@ -97,7 +98,7 @@ print_message (int nested, int edit)
|
|||
grub_printf ("\n\
|
||||
ESC to return previous menu.");
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
static grub_menu_entry_t
|
||||
|
@ -128,7 +129,7 @@ print_entry (int y, int highlight, grub_menu_entry_t entry)
|
|||
if (! unicode_title)
|
||||
/* XXX How to show this error? */
|
||||
return;
|
||||
|
||||
|
||||
len = grub_utf8_to_ucs4 (unicode_title, title_len,
|
||||
(grub_uint8_t *) title, -1, 0);
|
||||
if (len < 0)
|
||||
|
@ -157,7 +158,7 @@ print_entry (int y, int highlight, grub_menu_entry_t entry)
|
|||
grub_ssize_t width;
|
||||
|
||||
width = grub_getcharwidth (unicode_title[i]);
|
||||
|
||||
|
||||
if (x + width > (GRUB_TERM_LEFT_BORDER_X + GRUB_TERM_BORDER_WIDTH
|
||||
- GRUB_TERM_MARGIN - 1))
|
||||
grub_putcode (GRUB_TERM_DISP_RIGHT);
|
||||
|
@ -187,7 +188,7 @@ print_entries (grub_menu_t menu, int first, int offset)
|
|||
{
|
||||
grub_menu_entry_t e;
|
||||
int i;
|
||||
|
||||
|
||||
grub_gotoxy (GRUB_TERM_LEFT_BORDER_X + GRUB_TERM_BORDER_WIDTH,
|
||||
GRUB_TERM_FIRST_ENTRY_Y);
|
||||
|
||||
|
@ -248,13 +249,13 @@ get_timeout (void)
|
|||
{
|
||||
char *val;
|
||||
int timeout;
|
||||
|
||||
|
||||
val = grub_env_get ("timeout");
|
||||
if (! val)
|
||||
return -1;
|
||||
|
||||
|
||||
grub_error_push ();
|
||||
|
||||
|
||||
timeout = (int) grub_strtoul (val, 0, 0);
|
||||
|
||||
/* If the value is invalid, unset the variable. */
|
||||
|
@ -266,7 +267,7 @@ get_timeout (void)
|
|||
}
|
||||
|
||||
grub_error_pop ();
|
||||
|
||||
|
||||
return timeout;
|
||||
}
|
||||
|
||||
|
@ -278,7 +279,7 @@ set_timeout (int timeout)
|
|||
if (timeout > 0)
|
||||
{
|
||||
char buf[16];
|
||||
|
||||
|
||||
grub_sprintf (buf, "%d", timeout);
|
||||
grub_env_set ("timeout", buf);
|
||||
}
|
||||
|
@ -290,13 +291,13 @@ get_entry_number (const char *name)
|
|||
{
|
||||
char *val;
|
||||
int entry;
|
||||
|
||||
|
||||
val = grub_env_get (name);
|
||||
if (! val)
|
||||
return -1;
|
||||
|
||||
|
||||
grub_error_push ();
|
||||
|
||||
|
||||
entry = (int) grub_strtoul (val, 0, 0);
|
||||
|
||||
if (grub_errno != GRUB_ERR_NONE)
|
||||
|
@ -306,7 +307,7 @@ get_entry_number (const char *name)
|
|||
}
|
||||
|
||||
grub_error_pop ();
|
||||
|
||||
|
||||
return entry;
|
||||
}
|
||||
|
||||
|
@ -317,7 +318,7 @@ print_timeout (int timeout, int offset, int second_stage)
|
|||
They are required to clear the line. */
|
||||
char *msg = " The highlighted entry will be booted automatically in %ds. ";
|
||||
char *msg_end = grub_strchr (msg, '%');
|
||||
|
||||
|
||||
grub_gotoxy (second_stage ? (msg_end - msg) : 0, GRUB_TERM_HEIGHT - 3);
|
||||
grub_printf (second_stage ? msg_end : msg, timeout);
|
||||
grub_gotoxy (GRUB_TERM_CURSOR_X, GRUB_TERM_FIRST_ENTRY_Y + offset);
|
||||
|
@ -331,9 +332,9 @@ run_menu (grub_menu_t menu, int nested)
|
|||
grub_uint64_t saved_time;
|
||||
int default_entry;
|
||||
int timeout;
|
||||
|
||||
|
||||
first = 0;
|
||||
|
||||
|
||||
default_entry = get_entry_number ("default");
|
||||
|
||||
/* If DEFAULT_ENTRY is not within the menu entries, fall back to
|
||||
|
@ -370,7 +371,7 @@ run_menu (grub_menu_t menu, int nested)
|
|||
{
|
||||
int c;
|
||||
timeout = get_timeout ();
|
||||
|
||||
|
||||
if (timeout > 0)
|
||||
{
|
||||
grub_uint64_t current_time;
|
||||
|
@ -390,11 +391,11 @@ run_menu (grub_menu_t menu, int nested)
|
|||
grub_env_unset ("timeout");
|
||||
return default_entry;
|
||||
}
|
||||
|
||||
|
||||
if (grub_checkkey () >= 0 || timeout < 0)
|
||||
{
|
||||
c = GRUB_TERM_ASCII_CHAR (grub_getkey ());
|
||||
|
||||
|
||||
if (timeout >= 0)
|
||||
{
|
||||
grub_gotoxy (0, GRUB_TERM_HEIGHT - 3);
|
||||
|
@ -404,7 +405,7 @@ run_menu (grub_menu_t menu, int nested)
|
|||
grub_env_unset ("fallback");
|
||||
grub_gotoxy (GRUB_TERM_CURSOR_X, GRUB_TERM_FIRST_ENTRY_Y + offset);
|
||||
}
|
||||
|
||||
|
||||
switch (c)
|
||||
{
|
||||
case GRUB_TERM_HOME:
|
||||
|
@ -439,7 +440,7 @@ run_menu (grub_menu_t menu, int nested)
|
|||
print_entries (menu, first, offset);
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
case GRUB_TERM_DOWN:
|
||||
case 'v':
|
||||
if (menu->size > first + offset + 1)
|
||||
|
@ -459,7 +460,7 @@ run_menu (grub_menu_t menu, int nested)
|
|||
}
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
case GRUB_TERM_PPAGE:
|
||||
if (first == 0)
|
||||
{
|
||||
|
@ -490,12 +491,12 @@ run_menu (grub_menu_t menu, int nested)
|
|||
else
|
||||
{
|
||||
first += GRUB_TERM_NUM_ENTRIES;
|
||||
|
||||
|
||||
if (first + offset >= menu->size)
|
||||
{
|
||||
first -= GRUB_TERM_NUM_ENTRIES;
|
||||
offset += GRUB_TERM_NUM_ENTRIES;
|
||||
|
||||
|
||||
if (offset > menu->size - 1 ||
|
||||
offset > GRUB_TERM_NUM_ENTRIES - 1)
|
||||
{
|
||||
|
@ -510,13 +511,13 @@ run_menu (grub_menu_t menu, int nested)
|
|||
}
|
||||
print_entries (menu, first, offset);
|
||||
break;
|
||||
|
||||
|
||||
case '\n':
|
||||
case '\r':
|
||||
case 6:
|
||||
grub_setcursor (1);
|
||||
return first + offset;
|
||||
|
||||
|
||||
case '\e':
|
||||
if (nested)
|
||||
{
|
||||
|
@ -524,7 +525,7 @@ run_menu (grub_menu_t menu, int nested)
|
|||
return -1;
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
case 'c':
|
||||
grub_cmdline_run (1);
|
||||
goto refresh;
|
||||
|
@ -536,11 +537,11 @@ run_menu (grub_menu_t menu, int nested)
|
|||
grub_menu_entry_run (e);
|
||||
}
|
||||
goto refresh;
|
||||
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
grub_refresh ();
|
||||
}
|
||||
}
|
||||
|
@ -550,25 +551,25 @@ run_menu (grub_menu_t menu, int nested)
|
|||
}
|
||||
|
||||
/* Run a menu entry. */
|
||||
static void
|
||||
run_menu_entry (grub_menu_entry_t entry)
|
||||
void
|
||||
grub_menu_execute_entry(grub_menu_entry_t entry)
|
||||
{
|
||||
grub_script_execute (entry->commands);
|
||||
|
||||
|
||||
if (grub_errno == GRUB_ERR_NONE && grub_loader_is_loaded ())
|
||||
/* Implicit execution of boot, only if something is loaded. */
|
||||
grub_command_execute ("boot", 0);
|
||||
}
|
||||
|
||||
void
|
||||
grub_menu_run (grub_menu_t menu, int nested)
|
||||
static grub_err_t
|
||||
show_text_menu (grub_menu_t menu, int nested)
|
||||
{
|
||||
while (1)
|
||||
{
|
||||
int boot_entry;
|
||||
grub_menu_entry_t e;
|
||||
int fallback_entry;
|
||||
|
||||
|
||||
boot_entry = run_menu (menu, nested);
|
||||
if (boot_entry < 0)
|
||||
break;
|
||||
|
@ -576,13 +577,13 @@ grub_menu_run (grub_menu_t menu, int nested)
|
|||
e = get_entry (menu, boot_entry);
|
||||
if (! e)
|
||||
continue; /* Menu is empty. */
|
||||
|
||||
|
||||
grub_cls ();
|
||||
grub_setcursor (1);
|
||||
|
||||
grub_printf (" Booting \'%s\'\n\n", e->title);
|
||||
|
||||
run_menu_entry (e);
|
||||
|
||||
grub_menu_execute_entry (e);
|
||||
|
||||
/* Deal with a fallback entry. */
|
||||
/* FIXME: Multiple fallback entries like GRUB Legacy. */
|
||||
|
@ -591,11 +592,11 @@ grub_menu_run (grub_menu_t menu, int nested)
|
|||
{
|
||||
grub_print_error ();
|
||||
grub_errno = GRUB_ERR_NONE;
|
||||
|
||||
|
||||
e = get_entry (menu, fallback_entry);
|
||||
grub_env_unset ("fallback");
|
||||
grub_printf ("\n Falling back to \'%s\'\n\n", e->title);
|
||||
run_menu_entry (e);
|
||||
grub_menu_execute_entry (e);
|
||||
}
|
||||
|
||||
if (grub_errno != GRUB_ERR_NONE)
|
||||
|
@ -606,4 +607,12 @@ grub_menu_run (grub_menu_t menu, int nested)
|
|||
grub_wait_after_message ();
|
||||
}
|
||||
}
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
struct grub_menu_viewer grub_normal_terminal_menu_viewer =
|
||||
{
|
||||
.name = "terminal",
|
||||
.show_menu = show_text_menu
|
||||
};
|
||||
|
|
63
normal/menu_viewer.c
Normal file
63
normal/menu_viewer.c
Normal file
|
@ -0,0 +1,63 @@
|
|||
/*
|
||||
* GRUB -- GRand Unified Bootloader
|
||||
* Copyright (C) 2009 Free Software Foundation, Inc.
|
||||
*
|
||||
* GRUB 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 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GRUB 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 GRUB. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include <grub/mm.h>
|
||||
#include <grub/misc.h>
|
||||
#include <grub/env.h>
|
||||
#include <grub/menu_viewer.h>
|
||||
#include <grub/menu.h>
|
||||
|
||||
/* The list of menu viewers. */
|
||||
static grub_menu_viewer_t menu_viewer_list;
|
||||
|
||||
void
|
||||
grub_menu_viewer_register (grub_menu_viewer_t viewer)
|
||||
{
|
||||
viewer->next = menu_viewer_list;
|
||||
menu_viewer_list = viewer;
|
||||
}
|
||||
|
||||
static grub_menu_viewer_t get_current_menu_viewer (void)
|
||||
{
|
||||
const char *selected_name = grub_env_get ("menuviewer");
|
||||
|
||||
/* If none selected, pick the last registered one. */
|
||||
if (selected_name == 0)
|
||||
return menu_viewer_list;
|
||||
|
||||
grub_menu_viewer_t cur;
|
||||
for (cur = menu_viewer_list; cur; cur = cur->next)
|
||||
{
|
||||
if (grub_strcmp (cur->name, selected_name) == 0)
|
||||
return cur;
|
||||
}
|
||||
|
||||
/* Fall back to the first entry (or null). */
|
||||
return menu_viewer_list;
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_menu_viewer_show_menu (grub_menu_t menu, int nested)
|
||||
{
|
||||
grub_menu_viewer_t cur = get_current_menu_viewer ();
|
||||
if (!cur)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, "No menu viewer available.");
|
||||
|
||||
return cur->show_menu (menu, nested);
|
||||
}
|
||||
|
|
@ -1,7 +1,7 @@
|
|||
/* parser.y - The scripting parser. */
|
||||
/*
|
||||
* GRUB -- GRand Unified Bootloader
|
||||
* Copyright (C) 2005,2006,2007,2008 Free Software Foundation, Inc.
|
||||
* Copyright (C) 2005,2006,2007,2008,2009 Free Software Foundation, Inc.
|
||||
*
|
||||
* GRUB is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
|
@ -204,7 +204,7 @@ commandblock: '{'
|
|||
;
|
||||
|
||||
/* A menu entry. Carefully save the memory that is allocated. */
|
||||
menuentry: "menuentry" argument
|
||||
menuentry: "menuentry" arguments
|
||||
{
|
||||
grub_script_lexer_ref (state->lexerstate);
|
||||
} newlines '{'
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
/* script.c -- Functions to create an in memory description of the script. */
|
||||
/*
|
||||
* GRUB -- GRand Unified Bootloader
|
||||
* Copyright (C) 2005,2006,2007 Free Software Foundation, Inc.
|
||||
* Copyright (C) 2005,2006,2007,2009 Free Software Foundation, Inc.
|
||||
*
|
||||
* GRUB is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
|
@ -206,7 +206,7 @@ grub_script_create_cmdif (struct grub_parser_param *state,
|
|||
The options for this entry are passed in OPTIONS. */
|
||||
struct grub_script_cmd *
|
||||
grub_script_create_cmdmenu (struct grub_parser_param *state,
|
||||
struct grub_script_arg *title,
|
||||
struct grub_script_arglist *arglist,
|
||||
char *sourcecode,
|
||||
int options)
|
||||
{
|
||||
|
@ -232,9 +232,9 @@ grub_script_create_cmdmenu (struct grub_parser_param *state,
|
|||
cmd->cmd.next = 0;
|
||||
/* XXX: Check if this memory is properly freed. */
|
||||
cmd->sourcecode = sourcecode;
|
||||
cmd->title = title;
|
||||
cmd->arglist = arglist;
|
||||
cmd->options = options;
|
||||
|
||||
|
||||
return (struct grub_script_cmd *) cmd;
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue