From 8c5886df17cdfb148d4e17bddf38143ed65fe674 Mon Sep 17 00:00:00 2001 From: Vladimir 'phcoder' Serbinenko Date: Thu, 28 Jun 2012 15:27:54 +0200 Subject: [PATCH 001/364] Add monochrome text support (mda_text, aka `hercules' in grub-legacy). * grub-core/Makefile.core.def (mda_text): New module. * grub-core/lib/legacy_parse.c (grub_legacy_parse): Support `hercules'. * grub-core/term/i386/vga_common.c (grub_console_cur_color): Moved to .. * grub-core/term/i386/pc/vga_text.c (cur_color): ... here * grub-core/term/i386/pc/console.c (grub_console_cur_color): ... and here. * grub-core/term/i386/vga_common.c (grub_console_getwh): Moved to .. * grub-core/term/i386/pc/vga_text.c (grub_console_getwh): ... here * grub-core/term/i386/pc/console.c (grub_console_getwh): ... and here. * grub-core/term/i386/vga_common.c (grub_console_setcolorstate): Moved to .. * grub-core/term/i386/pc/vga_text.c (grub_console_setcolorstate): ... here * grub-core/term/i386/pc/console.c (grub_console_setcolorstate): ... and here. * grub-core/term/i386/vga_common.c: Removed. * include/grub/i386/vga_common.h: Likewise. * include/grub/vga.h (grub_vga_cr_bw_write): New function. (grub_vga_cr_bw_read): Likewise. * include/grub/vgaregs.h (GRUB_VGA_IO_CR_BW_INDEX): New enum value. (GRUB_VGA_IO_CR_BW_DATA): Likewise. * grub-core/term/i386/pc/vga_text.c [MODE_MDA]: Call grub_vga_cr_bw_read/grub_vga_cr_bw_write instead of grub_vga_cr_read/grub_vga_cr_write. (grub_vga_text_setcolorstate) [MODE_MDA]: Ignore color. --- ChangeLog | 31 +++++++++ grub-core/Makefile.core.def | 12 ++-- grub-core/lib/legacy_parse.c | 15 ++-- grub-core/term/i386/pc/console.c | 27 ++++++++ grub-core/term/i386/pc/vga_text.c | 141 +++++++++++++++++++++++++++++++++----- grub-core/term/i386/vga_common.c | 48 ------------- include/grub/i386/pc/console.h | 1 - include/grub/i386/vga_common.h | 32 --------- include/grub/vga.h | 14 ++++ include/grub/vgaregs.h | 2 + 10 files changed, 213 insertions(+), 110 deletions(-) delete mode 100644 grub-core/term/i386/vga_common.c delete mode 100644 include/grub/i386/vga_common.h diff --git a/ChangeLog b/ChangeLog index 81bdae9..f6e864a 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,34 @@ +2012-06-28 Vladimir Serbinenko + + Add monochrome text support (mda_text, aka `hercules' in grub-legacy). + + * grub-core/Makefile.core.def (mda_text): New module. + * grub-core/lib/legacy_parse.c (grub_legacy_parse): Support `hercules'. + * grub-core/term/i386/vga_common.c (grub_console_cur_color): Moved to .. + * grub-core/term/i386/pc/vga_text.c (cur_color): ... here + * grub-core/term/i386/pc/console.c (grub_console_cur_color): ... and + here. + * grub-core/term/i386/vga_common.c (grub_console_getwh): Moved to .. + * grub-core/term/i386/pc/vga_text.c (grub_console_getwh): ... here + * grub-core/term/i386/pc/console.c (grub_console_getwh): ... and + here. + * grub-core/term/i386/vga_common.c (grub_console_setcolorstate): Moved + to .. + * grub-core/term/i386/pc/vga_text.c (grub_console_setcolorstate): + ... here + * grub-core/term/i386/pc/console.c (grub_console_setcolorstate): ... and + here. + * grub-core/term/i386/vga_common.c: Removed. + * include/grub/i386/vga_common.h: Likewise. + * include/grub/vga.h (grub_vga_cr_bw_write): New function. + (grub_vga_cr_bw_read): Likewise. + * include/grub/vgaregs.h (GRUB_VGA_IO_CR_BW_INDEX): New enum value. + (GRUB_VGA_IO_CR_BW_DATA): Likewise. + * grub-core/term/i386/pc/vga_text.c [MODE_MDA]: Call + grub_vga_cr_bw_read/grub_vga_cr_bw_write instead of + grub_vga_cr_read/grub_vga_cr_write. + (grub_vga_text_setcolorstate) [MODE_MDA]: Ignore color. + 2012-06-27 Vladimir Serbinenko * configure.ac: Bump version to 2.00. diff --git a/grub-core/Makefile.core.def b/grub-core/Makefile.core.def index 39e77a4..5c2fcc2 100644 --- a/grub-core/Makefile.core.def +++ b/grub-core/Makefile.core.def @@ -123,9 +123,6 @@ kernel = { i386_coreboot_multiboot_qemu = kern/i386/coreboot/init.c; i386_coreboot_multiboot_qemu = term/i386/pc/vga_text.c; - i386_coreboot_multiboot_qemu = term/i386/vga_common.c; - i386_pc = term/i386/vga_common.c; - x86 = kern/i386/pit.c; efi = disk/efi/efidisk.c; @@ -175,7 +172,6 @@ kernel = { mips_qemu_mips = term/at_keyboard.c; mips_qemu_mips = commands/keylayouts.c; mips_qemu_mips = term/i386/pc/vga_text.c; - mips_qemu_mips = term/i386/vga_common.c; mips_qemu_mips = kern/vga_init.c; mips_arc = kern/mips/arc/init.c; @@ -1591,11 +1587,17 @@ module = { module = { name = vga_text; common = term/i386/pc/vga_text.c; - common = term/i386/vga_common.c; enable = i386_pc; }; module = { + name = mda_text; + common = term/i386/pc/mda_text.c; + enable = i386_pc; + enable = i386_coreboot_multiboot_qemu; +}; + +module = { name = video_cirrus; x86 = video/cirrus.c; enable = x86; diff --git a/grub-core/lib/legacy_parse.c b/grub-core/lib/legacy_parse.c index 775eaad..14768b8 100644 --- a/grub-core/lib/legacy_parse.c +++ b/grub-core/lib/legacy_parse.c @@ -1,6 +1,6 @@ /* * GRUB -- GRand Unified Bootloader - * Copyright (C) 1999,2000,2001,2002,2003,2004,2010 Free Software Foundation, Inc. + * Copyright (C) 1999,2000,2001,2002,2003,2004,2010,2012 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 @@ -290,7 +290,7 @@ static struct legacy_command legacy_commands[] = " default values are COM1, 9600, 8N1."}, /* FIXME: setkey unsupported. */ /* NUL_TERMINATE */ /* NOTE: setup unsupported. */ - /* FIXME: --no-echo, --no-edit, hercules unsupported. */ + /* FIXME: --no-echo, --no-edit unsupported. */ /* NOTE: both terminals are activated so --silent and --timeout are useless. */ {"terminal", NULL, NULL, 0, 0, {}, FLAG_TERMINAL | FLAG_IGNORE_REST, @@ -507,8 +507,8 @@ grub_legacy_parse (const char *buf, char **entryname, char **suffix) int dumb = 0, lines = 24; #ifdef TODO int no_echo = 0, no_edit = 0; - int hercules = 0; #endif + int hercules = 0; int console = 0, serial = 0; /* Big enough for any possible resulting command. */ char outbuf[256] = ""; @@ -541,10 +541,8 @@ grub_legacy_parse (const char *buf, char **entryname, char **suffix) if (grub_memcmp (ptr, "serial", sizeof ("serial") - 1) == 0) serial = 1; -#ifdef TODO if (grub_memcmp (ptr, "hercules", sizeof ("hercules") - 1) == 0) hercules = 1; -#endif while (*ptr && !grub_isspace (*ptr)) ptr++; while (*ptr && grub_isspace (*ptr)) @@ -561,7 +559,7 @@ grub_legacy_parse (const char *buf, char **entryname, char **suffix) grub_strcpy (outptr, "serial "); outptr += grub_strlen (outptr); } - if (console) + if (console || hercules) { grub_strcpy (outptr, "console "); outptr += grub_strlen (outptr); @@ -578,6 +576,11 @@ grub_legacy_parse (const char *buf, char **entryname, char **suffix) grub_strcpy (outptr, "console "); outptr += grub_strlen (outptr); } + if (hercules) + { + grub_strcpy (outptr, "mda_text "); + outptr += grub_strlen (outptr); + } grub_strcpy (outptr, "; "); outptr += grub_strlen (outptr); if (serial) diff --git a/grub-core/term/i386/pc/console.c b/grub-core/term/i386/pc/console.c index 7cf5ffc..a681435 100644 --- a/grub-core/term/i386/pc/console.c +++ b/grub-core/term/i386/pc/console.c @@ -22,6 +22,8 @@ #include #include +static grub_uint8_t grub_console_cur_color = 0x7; + static void int10_9 (grub_uint8_t ch, grub_uint16_t n) { @@ -250,6 +252,31 @@ grub_console_getkeystatus (struct grub_term_input *term __attribute__ ((unused)) return bios_data_area->keyboard_flag_lower & ~0x80; } +static grub_uint16_t +grub_console_getwh (struct grub_term_output *term __attribute__ ((unused))) +{ + return (80 << 8) | 25; +} + +static void +grub_console_setcolorstate (struct grub_term_output *term, + grub_term_color_state state) +{ + switch (state) { + case GRUB_TERM_COLOR_STANDARD: + grub_console_cur_color = GRUB_TERM_DEFAULT_STANDARD_COLOR & 0x7f; + break; + case GRUB_TERM_COLOR_NORMAL: + grub_console_cur_color = term->normal_color & 0x7f; + break; + case GRUB_TERM_COLOR_HIGHLIGHT: + grub_console_cur_color = term->highlight_color & 0x7f; + break; + default: + break; + } +} + static struct grub_term_input grub_console_term_input = { .name = "console", diff --git a/grub-core/term/i386/pc/vga_text.c b/grub-core/term/i386/pc/vga_text.c index c934c68..d1e4ef9 100644 --- a/grub-core/term/i386/pc/vga_text.c +++ b/grub-core/term/i386/pc/vga_text.c @@ -17,10 +17,17 @@ */ #include -#include #include #include #include +#include + +/* MODESET is used for testing to force monochrome or colour mode. + You shouldn't use mda_text on vga. + */ +#ifdef MODESET +#include +#endif #if defined (GRUB_MACHINE_COREBOOT) || defined (GRUB_MACHINE_QEMU) || defined (GRUB_MACHINE_MIPS_QEMU_MIPS) || defined (GRUB_MACHINE_MULTIBOOT) #include @@ -35,10 +42,21 @@ static int grub_curr_x, grub_curr_y; #ifdef __mips__ #define VGA_TEXT_SCREEN ((grub_uint16_t *) 0xb00b8000) +#define cr_read grub_vga_cr_read +#define cr_write grub_vga_cr_write +#elif defined (MODE_MDA) +#define VGA_TEXT_SCREEN ((grub_uint16_t *) 0xb0000) +#define cr_read grub_vga_cr_bw_read +#define cr_write grub_vga_cr_bw_write +static grub_uint8_t cur_color; #else #define VGA_TEXT_SCREEN ((grub_uint16_t *) 0xb8000) +#define cr_read grub_vga_cr_read +#define cr_write grub_vga_cr_write #endif +static grub_uint8_t cur_color = 0x7; + static void screen_write_char (int x, int y, short c) { @@ -55,8 +73,8 @@ static void update_cursor (void) { unsigned int pos = grub_curr_y * COLS + grub_curr_x; - grub_vga_cr_write (pos >> 8, GRUB_VGA_CR_CURSOR_ADDR_HIGH); - grub_vga_cr_write (pos & 0xFF, GRUB_VGA_CR_CURSOR_ADDR_LOW); + cr_write (pos >> 8, GRUB_VGA_CR_CURSOR_ADDR_HIGH); + cr_write (pos & 0xFF, GRUB_VGA_CR_CURSOR_ADDR_LOW); } static void @@ -72,7 +90,7 @@ inc_y (void) for (x = 0; x < COLS; x++) screen_write_char (x, y, screen_read_char (x, y + 1)); for (x = 0; x < COLS; x++) - screen_write_char (x, ROWS - 1, ' ' | (grub_console_cur_color << 8)); + screen_write_char (x, ROWS - 1, ' ' | (cur_color << 8)); } } @@ -103,7 +121,7 @@ grub_vga_text_putchar (struct grub_term_output *term __attribute__ ((unused)), break; default: screen_write_char (grub_curr_x, grub_curr_y, - c->base | (grub_console_cur_color << 8)); + c->base | (cur_color << 8)); inc_x (); } @@ -130,7 +148,7 @@ grub_vga_text_cls (struct grub_term_output *term) { int i; for (i = 0; i < ROWS * COLS; i++) - VGA_TEXT_SCREEN[i] = grub_cpu_to_le16 (' ' | (grub_console_cur_color << 8)); + VGA_TEXT_SCREEN[i] = grub_cpu_to_le16 (' ' | (cur_color << 8)); grub_vga_text_gotoxy (term, 0, 0); } @@ -139,49 +157,136 @@ grub_vga_text_setcursor (struct grub_term_output *term __attribute__ ((unused)), int on) { grub_uint8_t old; - old = grub_vga_cr_read (GRUB_VGA_CR_CURSOR_START); + old = cr_read (GRUB_VGA_CR_CURSOR_START); if (on) - grub_vga_cr_write (old & ~GRUB_VGA_CR_CURSOR_START_DISABLE, - GRUB_VGA_CR_CURSOR_START); + cr_write (old & ~GRUB_VGA_CR_CURSOR_START_DISABLE, + GRUB_VGA_CR_CURSOR_START); else - grub_vga_cr_write (old | GRUB_VGA_CR_CURSOR_START_DISABLE, - GRUB_VGA_CR_CURSOR_START); + cr_write (old | GRUB_VGA_CR_CURSOR_START_DISABLE, + GRUB_VGA_CR_CURSOR_START); } static grub_err_t -grub_vga_text_init_fini (struct grub_term_output *term) +grub_vga_text_init (struct grub_term_output *term) { +#ifdef MODESET + struct grub_bios_int_registers regs; + regs.flags = GRUB_CPU_INT_FLAGS_DEFAULT; + +#ifdef MODE_MDA + regs.eax = 7; +#else + regs.eax = 3; +#endif + regs.flags = GRUB_CPU_INT_FLAGS_DEFAULT; + grub_bios_interrupt (0x10, ®s); +#endif grub_vga_text_cls (term); return 0; } +static grub_err_t +grub_vga_text_fini (struct grub_term_output *term) +{ +#ifdef MODESET + struct grub_bios_int_registers regs; + regs.flags = GRUB_CPU_INT_FLAGS_DEFAULT; + + regs.eax = 3; + regs.flags = GRUB_CPU_INT_FLAGS_DEFAULT; + grub_bios_interrupt (0x10, ®s); +#endif + grub_vga_text_cls (term); + return 0; +} + +static grub_uint16_t +grub_vga_text_getwh (struct grub_term_output *term __attribute__ ((unused))) +{ + return (80 << 8) | 25; +} + +#ifndef MODE_MDA + +static void +grub_vga_text_setcolorstate (struct grub_term_output *term, + grub_term_color_state state) +{ + switch (state) { + case GRUB_TERM_COLOR_STANDARD: + cur_color = GRUB_TERM_DEFAULT_STANDARD_COLOR & 0x7f; + break; + case GRUB_TERM_COLOR_NORMAL: + cur_color = term->normal_color & 0x7f; + break; + case GRUB_TERM_COLOR_HIGHLIGHT: + cur_color = term->highlight_color & 0x7f; + break; + default: + break; + } +} + +#else +static void +grub_vga_text_setcolorstate (struct grub_term_output *term __attribute__ ((unused)), + grub_term_color_state state) +{ + switch (state) { + case GRUB_TERM_COLOR_STANDARD: + cur_color = 0x07; + break; + case GRUB_TERM_COLOR_NORMAL: + cur_color = 0x07; + break; + case GRUB_TERM_COLOR_HIGHLIGHT: + cur_color = 0x70; + break; + default: + break; + } +} +#endif + static struct grub_term_output grub_vga_text_term = { +#ifdef MODE_MDA + .name = "mda_text", +#else .name = "vga_text", - .init = grub_vga_text_init_fini, - .fini = grub_vga_text_init_fini, +#endif + .init = grub_vga_text_init, + .fini = grub_vga_text_fini, .putchar = grub_vga_text_putchar, - .getwh = grub_console_getwh, + .getwh = grub_vga_text_getwh, .getxy = grub_vga_text_getxy, .gotoxy = grub_vga_text_gotoxy, .cls = grub_vga_text_cls, - .setcolorstate = grub_console_setcolorstate, + .setcolorstate = grub_vga_text_setcolorstate, .setcursor = grub_vga_text_setcursor, .flags = GRUB_TERM_CODE_TYPE_CP437, .normal_color = GRUB_TERM_DEFAULT_NORMAL_COLOR, .highlight_color = GRUB_TERM_DEFAULT_HIGHLIGHT_COLOR, }; -#if defined (GRUB_MACHINE_COREBOOT) || defined (GRUB_MACHINE_QEMU) || defined (GRUB_MACHINE_MIPS_QEMU_MIPS) || defined (GRUB_MACHINE_MULTIBOOT) +#ifdef MODE_MDA +GRUB_MOD_INIT(mda_text) +#elif defined (GRUB_MACHINE_COREBOOT) || defined (GRUB_MACHINE_QEMU) || defined (GRUB_MACHINE_MIPS_QEMU_MIPS) || defined (GRUB_MACHINE_MULTIBOOT) void grub_vga_text_init (void) #else GRUB_MOD_INIT(vga_text) #endif { +#ifdef MODE_MDA + grub_term_register_output ("mda_text", &grub_vga_text_term); +#else grub_term_register_output ("vga_text", &grub_vga_text_term); +#endif } -#if defined (GRUB_MACHINE_COREBOOT) || defined (GRUB_MACHINE_QEMU) || defined (GRUB_MACHINE_MIPS_QEMU_MIPS) || defined (GRUB_MACHINE_MULTIBOOT) +#ifdef MODE_MDA +GRUB_MOD_FINI(mda_text) +#elif defined (GRUB_MACHINE_COREBOOT) || defined (GRUB_MACHINE_QEMU) || defined (GRUB_MACHINE_MIPS_QEMU_MIPS) || defined (GRUB_MACHINE_MULTIBOOT) void grub_vga_text_fini (void) #else GRUB_MOD_FINI(vga_text) diff --git a/grub-core/term/i386/vga_common.c b/grub-core/term/i386/vga_common.c deleted file mode 100644 index 0c21769..0000000 --- a/grub-core/term/i386/vga_common.c +++ /dev/null @@ -1,48 +0,0 @@ -/* - * GRUB -- GRand Unified Bootloader - * Copyright (C) 2002,2003,2005,2007,2008 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 . - */ - -#include -#include -#include - -grub_uint8_t grub_console_cur_color = 0x7; - -grub_uint16_t -grub_console_getwh (struct grub_term_output *term __attribute__ ((unused))) -{ - return (80 << 8) | 25; -} - -void -grub_console_setcolorstate (struct grub_term_output *term, - grub_term_color_state state) -{ - switch (state) { - case GRUB_TERM_COLOR_STANDARD: - grub_console_cur_color = GRUB_TERM_DEFAULT_STANDARD_COLOR & 0x7f; - break; - case GRUB_TERM_COLOR_NORMAL: - grub_console_cur_color = term->normal_color & 0x7f; - break; - case GRUB_TERM_COLOR_HIGHLIGHT: - grub_console_cur_color = term->highlight_color & 0x7f; - break; - default: - break; - } -} diff --git a/include/grub/i386/pc/console.h b/include/grub/i386/pc/console.h index f752b9a..191964f 100644 --- a/include/grub/i386/pc/console.h +++ b/include/grub/i386/pc/console.h @@ -24,7 +24,6 @@ #include #include #include -#include /* Initialize the console system. */ void grub_console_init (void); diff --git a/include/grub/i386/vga_common.h b/include/grub/i386/vga_common.h deleted file mode 100644 index 8727903..0000000 --- a/include/grub/i386/vga_common.h +++ /dev/null @@ -1,32 +0,0 @@ -/* - * GRUB -- GRand Unified Bootloader - * Copyright (C) 2002,2005,2007,2008 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 . - */ - -#ifndef GRUB_VGA_COMMON_CPU_HEADER -#define GRUB_VGA_COMMON_CPU_HEADER 1 - -#include -#include -#include - -extern grub_uint8_t grub_console_cur_color; - -grub_uint16_t grub_console_getwh (struct grub_term_output *term); -void grub_console_setcolorstate (struct grub_term_output *term, - grub_term_color_state state); - -#endif /* ! GRUB_VGA_COMMON_CPU_HEADER */ diff --git a/include/grub/vga.h b/include/grub/vga.h index 81d40a1..1d8449c 100644 --- a/include/grub/vga.h +++ b/include/grub/vga.h @@ -57,6 +57,20 @@ grub_vga_cr_read (grub_uint8_t addr) } static inline void +grub_vga_cr_bw_write (grub_uint8_t val, grub_uint8_t addr) +{ + grub_outb (addr, GRUB_MACHINE_PCI_IO_BASE + GRUB_VGA_IO_CR_BW_INDEX); + grub_outb (val, GRUB_MACHINE_PCI_IO_BASE + GRUB_VGA_IO_CR_BW_DATA); +} + +static inline grub_uint8_t +grub_vga_cr_bw_read (grub_uint8_t addr) +{ + grub_outb (addr, GRUB_MACHINE_PCI_IO_BASE + GRUB_VGA_IO_CR_BW_INDEX); + return grub_inb (GRUB_MACHINE_PCI_IO_BASE + GRUB_VGA_IO_CR_BW_DATA); +} + +static inline void grub_vga_sr_write (grub_uint8_t val, grub_uint8_t addr) { grub_outb (addr, GRUB_MACHINE_PCI_IO_BASE + GRUB_VGA_IO_SR_INDEX); diff --git a/include/grub/vgaregs.h b/include/grub/vgaregs.h index a7b13ee..1a666a1 100644 --- a/include/grub/vgaregs.h +++ b/include/grub/vgaregs.h @@ -26,6 +26,8 @@ enum { + GRUB_VGA_IO_CR_BW_INDEX = 0x3b4, + GRUB_VGA_IO_CR_BW_DATA = 0x3b5, GRUB_VGA_IO_ARX = 0x3c0, GRUB_VGA_IO_ARX_READ = 0x3c1, GRUB_VGA_IO_MISC_WRITE = 0x3c2, -- 1.8.1.4