pkglib_MODULES += minicmd.mod extcmd.mod hello.mod handler.mod \
ls.mod cmp.mod cat.mod help.mod search.mod loopback.mod \
configfile.mod echo.mod \
- terminfo.mod test.mod blocklist.mod hexdump.mod \
+ test.mod blocklist.mod hexdump.mod \
read.mod sleep.mod loadenv.mod crc.mod parttool.mod \
msdospart.mod memrw.mod normal.mod sh.mod \
gptsync.mod true.mod probe.mod password.mod \
configfile_mod_CFLAGS = $(COMMON_CFLAGS)
configfile_mod_LDFLAGS = $(COMMON_LDFLAGS)
+ifneq ($(platform), ieee1275)
# For terminfo.mod.
+pkglib_MODULES += terminfo.mod
terminfo_mod_SOURCES = term/terminfo.c term/tparm.c
terminfo_mod_CFLAGS = $(COMMON_CFLAGS)
terminfo_mod_LDFLAGS = $(COMMON_LDFLAGS)
+endif
# For blocklist.mod.
blocklist_mod_SOURCES = commands/blocklist.c
kern/generic/millisleep.c \
kern/ieee1275/ieee1275.c \
term/ieee1275/ofconsole.c \
+ term/terminfo.c term/tparm.c \
disk/ieee1275/ofdisk.c \
symlist.c
kernel_img_HEADERS += ieee1275/ieee1275.h
kern/list.c kern/handler.c kern/command.c kern/corecmd.c \
kern/ieee1275/init.c \
kern/ieee1275/mmap.c \
- term/ieee1275/ofconsole.c \
+ term/ieee1275/ofconsole.c term/terminfo.c term/tparm.c \
kern/ieee1275/openfw.c disk/ieee1275/ofdisk.c \
kern/parser.c kern/partition.c kern/env.c kern/$(target_cpu)/dl.c \
kern/generic/millisleep.c kern/time.c \
kern/sparc64/ieee1275/init.c \
kern/ieee1275/mmap.c \
term/ieee1275/ofconsole.c \
- kern/ieee1275/openfw.c disk/ieee1275/ofdisk.c \
+ kern/ieee1275/openfw.c term/terminfo.c term/tparm.c \
+ disk/ieee1275/ofdisk.c \
kern/parser.c kern/partition.c kern/env.c kern/$(target_cpu)/dl.c \
kern/generic/millisleep.c kern/time.c \
symlist.c kern/$(target_cpu)/cache.S
void grub_terminfo_cursor_on (grub_term_output_t oterm);
void grub_terminfo_cursor_off (grub_term_output_t oterm);
+#define GRUB_TERMINFO_READKEY_MAX_LEN 4
+void grub_terminfo_readkey (int *keys, int *len, int (*readkey) (void));
+
#endif /* ! GRUB_TERMINFO_HEADER */
#include <grub/misc.h>
#include <grub/mm.h>
#include <grub/time.h>
+#include <grub/terminfo.h>
#include <grub/machine/console.h>
#include <grub/ieee1275/ieee1275.h>
static int grub_curr_x;
static int grub_curr_y;
-static int grub_keybuf;
+static int grub_keybuf[GRUB_TERMINFO_READKEY_MAX_LEN];
static int grub_buflen;
struct color
*highlight_color = grub_ofconsole_highlight_color;
}
-#define ANSI_C0 0x9b
-
static int
-grub_ofconsole_readkey (int *key)
+readkey (void)
{
grub_uint8_t c;
grub_ssize_t actual = 0;
grub_ieee1275_read (stdin_ihandle, &c, 1, &actual);
if (actual > 0)
- switch(c)
- {
- case 0x7f:
- /* Backspace: Ctrl-h. */
- c = '\b';
- break;
- case ANSI_C0:
- case '\e':
- {
- grub_uint64_t start;
-
- if (c == '\e')
- {
- grub_ieee1275_read (stdin_ihandle, &c, 1, &actual);
-
- /* On 9600 we have to wait up to 12 milliseconds. */
- start = grub_get_time_ms ();
- while (actual <= 0 && grub_get_time_ms () - start < 12)
- grub_ieee1275_read (stdin_ihandle, &c, 1, &actual);
-
- if (actual <= 0)
- {
- *key = '\e';
- return 1;
- }
-
- if (c != '[')
- return 0;
- }
-
- grub_ieee1275_read (stdin_ihandle, &c, 1, &actual);
-
- /* On 9600 we have to wait up to 12 milliseconds. */
- start = grub_get_time_ms ();
- while (actual <= 0 && grub_get_time_ms () - start < 12)
- grub_ieee1275_read (stdin_ihandle, &c, 1, &actual);
- if (actual <= 0)
- return 0;
-
- switch (c)
- {
- case 'A':
- /* Up: Ctrl-p. */
- c = GRUB_TERM_UP;
- break;
- case 'B':
- /* Down: Ctrl-n. */
- c = GRUB_TERM_DOWN;
- break;
- case 'C':
- /* Right: Ctrl-f. */
- c = GRUB_TERM_RIGHT;
- break;
- case 'D':
- /* Left: Ctrl-b. */
- c = GRUB_TERM_LEFT;
- break;
- case '3':
- {
- grub_ieee1275_read (stdin_ihandle, &c, 1, &actual);
- /* On 9600 we have to wait up to 12 milliseconds. */
- start = grub_get_time_ms ();
- while (actual <= 0 && grub_get_time_ms () - start < 12)
- grub_ieee1275_read (stdin_ihandle, &c, 1, &actual);
-
- if (actual <= 0)
- return 0;
-
- /* Delete: Ctrl-d. */
- if (c == '~')
- c = GRUB_TERM_DC;
- else
- return 0;
- break;
- }
- break;
- }
- }
- }
-
- *key = c;
- return actual > 0;
+ return c;
+ return -1;
}
static int
grub_ofconsole_checkkey (void)
{
- int key;
- int read;
-
if (grub_buflen)
return 1;
- read = grub_ofconsole_readkey (&key);
- if (read)
- {
- grub_keybuf = key;
- grub_buflen = 1;
- return 1;
- }
+ grub_terminfo_readkey (grub_keybuf, &grub_buflen, readkey);
+
+ if (grub_buflen)
+ return 1;
return -1;
}
static int
grub_ofconsole_getkey (void)
{
- int key;
-
- if (grub_buflen)
- {
- grub_buflen =0;
- return grub_keybuf;
- }
-
- while (! grub_ofconsole_readkey (&key));
-
- return key;
+ int ret;
+ while (! grub_buflen)
+ grub_terminfo_readkey (grub_keybuf, &grub_buflen, readkey);
+
+ ret = grub_keybuf[0];
+ grub_buflen--;
+ grub_memmove (grub_keybuf, grub_keybuf + 1, grub_buflen);
+ return ret;
}
static grub_uint16_t
#include <grub/tparm.h>
#include <grub/command.h>
#include <grub/i18n.h>
+#include <grub/time.h>
struct terminfo
{
putstr (grub_terminfo_tparm (term.cursor_off), oterm);
}
+#define ANSI_C0 0x9b
+
+void
+grub_terminfo_readkey (int *keys, int *len, int (*readkey) (void))
+{
+ int c;
+
+#define CONTINUE_READ \
+ { \
+ grub_uint64_t start; \
+ /* On 9600 we have to wait up to 12 milliseconds. */ \
+ start = grub_get_time_ms (); \
+ do \
+ c = readkey (); \
+ while (c == -1 && grub_get_time_ms () - start < 12); \
+ if (c == -1) \
+ return; \
+ \
+ keys[*len] = c; \
+ (*len)++; \
+ }
+
+ c = readkey ();
+ if (c < 0)
+ {
+ *len = 0;
+ return;
+ }
+ *len = 1;
+ keys[0] = c;
+ if (c != ANSI_C0 && c != '\e')
+ {
+ /* Backspace: Ctrl-h. */
+ if (c == 0x7f)
+ c = '\b';
+ *len = 1;
+ keys[0] = c;
+ return;
+ }
+
+ {
+ static struct
+ {
+ char key;
+ char ascii;
+ }
+ three_code_table[] =
+ {
+ {'4', GRUB_TERM_DC},
+ {'A', GRUB_TERM_UP},
+ {'B', GRUB_TERM_DOWN},
+ {'C', GRUB_TERM_RIGHT},
+ {'D', GRUB_TERM_LEFT},
+ {'F', GRUB_TERM_END},
+ {'H', GRUB_TERM_HOME},
+ {'K', GRUB_TERM_END},
+ {'P', GRUB_TERM_DC},
+ {'?', GRUB_TERM_PPAGE},
+ {'/', GRUB_TERM_NPAGE}
+ };
+
+ static struct
+ {
+ char key;
+ char ascii;
+ }
+ four_code_table[] =
+ {
+ {'1', GRUB_TERM_HOME},
+ {'3', GRUB_TERM_DC},
+ {'5', GRUB_TERM_PPAGE},
+ {'6', GRUB_TERM_NPAGE}
+ };
+ unsigned i;
+
+ if (c == '\e')
+ {
+ CONTINUE_READ;
+
+ if (c != '[')
+ return;
+ }
+
+ CONTINUE_READ;
+
+ for (i = 0; i < ARRAY_SIZE (three_code_table); i++)
+ if (three_code_table[i].key == c)
+ {
+ keys[0] = three_code_table[i].ascii;
+ *len = 1;
+ return;
+ }
+
+ for (i = 0; i < ARRAY_SIZE (four_code_table); i++)
+ if (four_code_table[i].key == c)
+ {
+ CONTINUE_READ;
+ if (c != '~')
+ return;
+ keys[0] = three_code_table[i].ascii;
+ *len = 1;
+ return;
+ }
+ return;
+ }
+#undef CONTINUE_READ
+}
+
/* GRUB Command. */
static grub_err_t