From: Felix Fietkau Date: Tue, 9 Oct 2007 03:19:07 +0000 (+0000) Subject: move grub to package/ X-Git-Url: http://git.lede-project.org./?a=commitdiff_plain;h=8c97372e0dc7d496a9c0bae1ace912a4e7ec9540;p=openwrt%2Fstaging%2Fstintel.git move grub to package/ SVN-Revision: 9212 --- diff --git a/package/grub/Makefile b/package/grub/Makefile new file mode 100644 index 0000000000..9fc98173f5 --- /dev/null +++ b/package/grub/Makefile @@ -0,0 +1,82 @@ +# +# Copyright (C) 2006 OpenWrt.org +# +# This is free software, licensed under the GNU General Public License v2. +# See /LICENSE for more information. +# +# $Id: Makefile 4855 2006-09-24 20:49:31Z nico $ + +include $(TOPDIR)/rules.mk +include $(INCLUDE_DIR)/kernel.mk + +PKG_NAME:=grub +PKG_VERSION:=0.97 +PKG_RELEASE:=1 + +PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz +PKG_SOURCE_URL:=ftp://alpha.gnu.org/gnu/grub +PKG_MD5SUM:=cd3f3eb54446be6003156158d51f4884 +PKG_CAT:=zcat + +PKG_BUILD_DIR:=$(KERNEL_BUILD_DIR)/grub-$(PKG_VERSION) +PKG_TARGETS:=bin + +include $(INCLUDE_DIR)/package.mk + +define Package/grub + SECTION:=boot + DEPENDS:=@TARGET_x86 + CATEGORY:=Boot Loaders + TITLE:=GRand Unified Bootloader + URL:=http://www.gnu.org/software/grub/ +endef + +ifeq ($(HOST_ARCH),x86_64) +CONFIGURE_FLAGS:= \ + --target=$(GNU_TARGET_NAME) \ + --host=$(GNU_TARGET_NAME) \ + --build=$(GNU_HOST_NAME) +else +CONFIGURE_FLAGS:= +endif + +define Build/Configure + (cd $(PKG_BUILD_DIR); \ + LDFLAGS="-static" \ + ./configure \ + $(CONFIGURE_FLAGS) \ + --program-prefix="" \ + --program-suffix="" \ + --prefix=/usr \ + --exec-prefix=/usr \ + --bindir=/usr/bin \ + --sbindir=/usr/sbin \ + --libexecdir=/usr/lib \ + --sysconfdir=/etc \ + --datadir=/usr/share \ + --localstatedir=/var \ + --mandir=/usr/man \ + --infodir=/usr/info \ + $(DISABLE_NLS) \ + --disable-auto-linux-mem-opt \ + ) +endef + +# +# ./configure detects whether the host compiler supports +# -fno-stack-protector but only sets STAGE2_CFLAGS accordingly +# +define Build/Compile + $(MAKE) -C $(PKG_BUILD_DIR) \ + GRUB_CFLAGS="\$$$$(STAGE2_CFLAGS)" \ + STAGE1_CFLAGS="\$$$$(STAGE2_CFLAGS)" +endef + +define Build/InstallDev + $(MAKE) -C $(PKG_BUILD_DIR) \ + DESTDIR="$(STAGING_DIR_HOST)" \ + install + mv $(STAGING_DIR_HOST)/usr/sbin/grub $(STAGING_DIR_HOST)/bin +endef + +$(eval $(call BuildPackage,grub)) diff --git a/package/grub/menu.lst b/package/grub/menu.lst new file mode 100644 index 0000000000..cb306cc443 --- /dev/null +++ b/package/grub/menu.lst @@ -0,0 +1,15 @@ +serial --unit=0 --speed=@BAUDRATE@ --word=8 --parity=no --stop=1 +terminal --timeout=2 console serial + +default 0 +timeout 5 + +title OpenWrt +root (hd0,0) +kernel /boot/vmlinuz @CMDLINE@ noinitrd console=tty0 console=ttyS0,@BAUDRATE@n8 reboot=bios +boot + +title OpenWrt (failsafe) +root (hd0,0) +kernel /boot/vmlinuz failsafe=true @CMDLINE@ noinitrd console=tty0 console=ttyS0,@BAUDRATE@n8 reboot=bios +boot diff --git a/package/grub/patches/010-fixes-1.patch b/package/grub/patches/010-fixes-1.patch new file mode 100644 index 0000000000..6628b73822 --- /dev/null +++ b/package/grub/patches/010-fixes-1.patch @@ -0,0 +1,4490 @@ +Submitted By: Jim Gifford (jim at linuxfromscratch dot org) +Date: 2006-07-04 +Initial Package Version: 0.97 +Origin: Debian +Upstream Status: Unknown +Description: Contains various fixes and enhancements + Graphics mode support + Fixes for Raid Support + XFS Filesystem Boot Freeze Fixes + Removed 2GB Memory Limitation + Freebsd support + Fixes for initrd support + Grub installation Fixes + Linux 2.6 geometry Fixes + Intel Mac Support + Autoconf and aclocal updates + +http://trac.cross-lfs.org/browser/trunk/patches/grub-0.97-fixes-1.patch + +diff -Naur grub-0.97.orig/aclocal.m4 grub-0.97/aclocal.m4 +--- grub-0.97.orig/aclocal.m4 2005-05-07 19:41:18.000000000 -0700 ++++ grub-0.97/aclocal.m4 2006-07-04 00:08:22.000000000 -0700 +@@ -1,7 +1,7 @@ +-# generated automatically by aclocal 1.9.4 -*- Autoconf -*- ++# generated automatically by aclocal 1.9.6 -*- Autoconf -*- + +-# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004 +-# Free Software Foundation, Inc. ++# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, ++# 2005 Free Software Foundation, Inc. + # This file is free software; the Free Software Foundation + # gives unlimited permission to copy and/or distribute it, + # with or without modifications, as long as this notice is preserved. +@@ -11,23 +11,11 @@ + # even the implied warranty of MERCHANTABILITY or FITNESS FOR A + # PARTICULAR PURPOSE. + +-# -*- Autoconf -*- +-# Copyright (C) 2002, 2003 Free Software Foundation, Inc. +-# Generated from amversion.in; do not edit by hand. +- +-# 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, or (at your option) +-# 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., 59 Temple Place - Suite 330, Boston, MA ++# Copyright (C) 2002, 2003, 2005 Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + + # AM_AUTOMAKE_VERSION(VERSION) + # ---------------------------- +@@ -40,26 +28,15 @@ + # Call AM_AUTOMAKE_VERSION so it can be traced. + # This function is AC_REQUIREd by AC_INIT_AUTOMAKE. + AC_DEFUN([AM_SET_CURRENT_AUTOMAKE_VERSION], +- [AM_AUTOMAKE_VERSION([1.9.4])]) +- +-# AM_AUX_DIR_EXPAND +- +-# Copyright (C) 2001, 2003 Free Software Foundation, Inc. ++ [AM_AUTOMAKE_VERSION([1.9.6])]) + +-# 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, or (at your option) +-# any later version. ++# AM_AUX_DIR_EXPAND -*- Autoconf -*- + +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. ++# Copyright (C) 2001, 2003, 2005 Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + + # For projects using AC_CONFIG_AUX_DIR([foo]), Autoconf sets + # $ac_aux_dir to `$srcdir/foo'. In other projects, it is set to +@@ -106,26 +83,16 @@ + am_aux_dir=`cd $ac_aux_dir && pwd` + ]) + +-# AM_CONDITIONAL -*- Autoconf -*- ++# AM_CONDITIONAL -*- Autoconf -*- + +-# Copyright (C) 1997, 2000, 2001, 2003, 2004 Free Software Foundation, Inc. +- +-# 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, or (at your option) +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. ++# Copyright (C) 1997, 2000, 2001, 2003, 2004, 2005 ++# Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + +-# serial 6 ++# serial 7 + + # AM_CONDITIONAL(NAME, SHELL-CONDITION) + # ------------------------------------- +@@ -149,26 +116,15 @@ + Usually this means the macro was only invoked conditionally.]]) + fi])]) + +-# serial 7 -*- Autoconf -*- + +-# Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004 ++# Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005 + # Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + +-# 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, or (at your option) +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. +- ++# serial 8 + + # There are a few dirty hacks below to avoid letting `AC_PROG_CC' be + # written in clear, in which case automake, when reading aclocal.m4, +@@ -177,7 +133,6 @@ + # CC etc. in the Makefile, will ask for an AC_PROG_CC use... + + +- + # _AM_DEPENDENCIES(NAME) + # ---------------------- + # See how the compiler implements dependency checking. +@@ -317,27 +272,16 @@ + AC_SUBST([AMDEPBACKSLASH]) + ]) + +-# Generate code to set up dependency tracking. -*- Autoconf -*- +- +-# Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004 +-# Free Software Foundation, Inc. +- +-# 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, or (at your option) +-# any later version. ++# Generate code to set up dependency tracking. -*- Autoconf -*- + +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. ++# Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005 ++# Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + +-#serial 2 ++#serial 3 + + # _AM_OUTPUT_DEPENDENCY_COMMANDS + # ------------------------------ +@@ -396,30 +340,19 @@ + [AMDEP_TRUE="$AMDEP_TRUE" ac_aux_dir="$ac_aux_dir"]) + ]) + +-# Do all the work for Automake. -*- Autoconf -*- ++# Do all the work for Automake. -*- Autoconf -*- + +-# This macro actually does too much some checks are only needed if +-# your package does certain things. But this isn't really a big deal. +- +-# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004 ++# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005 + # Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + +-# 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, or (at your option) +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. ++# serial 12 + +-# serial 11 ++# This macro actually does too much. Some checks are only needed if ++# your package does certain things. But this isn't really a big deal. + + # AM_INIT_AUTOMAKE(PACKAGE, VERSION, [NO-DEFINE]) + # AM_INIT_AUTOMAKE([OPTIONS]) +@@ -521,51 +454,27 @@ + done + echo "timestamp for $1" >`AS_DIRNAME([$1])`/stamp-h[]$_am_stamp_count]) + ++# Copyright (C) 2001, 2003, 2005 Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. ++ + # AM_PROG_INSTALL_SH + # ------------------ + # Define $install_sh. +- +-# Copyright (C) 2001, 2003 Free Software Foundation, Inc. +- +-# 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, or (at your option) +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. +- + AC_DEFUN([AM_PROG_INSTALL_SH], + [AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl + install_sh=${install_sh-"$am_aux_dir/install-sh"} + AC_SUBST(install_sh)]) + +-# -*- Autoconf -*- +-# Copyright (C) 2003 Free Software Foundation, Inc. +- +-# 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, or (at your option) +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. ++# Copyright (C) 2003, 2005 Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + +-# serial 1 ++# serial 2 + + # Check whether the underlying file-system supports filenames + # with a leading dot. For instance MS-DOS doesn't. +@@ -580,28 +489,17 @@ + rmdir .tst 2>/dev/null + AC_SUBST([am__leading_dot])]) + +-# Add --enable-maintainer-mode option to configure. ++# Add --enable-maintainer-mode option to configure. -*- Autoconf -*- + # From Jim Meyering + +-# Copyright (C) 1996, 1998, 2000, 2001, 2002, 2003, 2004 ++# Copyright (C) 1996, 1998, 2000, 2001, 2002, 2003, 2004, 2005 + # Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + +-# 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, or (at your option) +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. +- +-# serial 3 ++# serial 4 + + AC_DEFUN([AM_MAINTAINER_MODE], + [AC_MSG_CHECKING([whether to enable maintainer-specific portions of Makefiles]) +@@ -620,26 +518,15 @@ + + AU_DEFUN([jm_MAINTAINER_MODE], [AM_MAINTAINER_MODE]) + +-# Check to see how 'make' treats includes. -*- Autoconf -*- +- +-# Copyright (C) 2001, 2002, 2003 Free Software Foundation, Inc. ++# Check to see how 'make' treats includes. -*- Autoconf -*- + +-# 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, or (at your option) +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. ++# Copyright (C) 2001, 2002, 2003, 2005 Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + +-# serial 2 ++# serial 3 + + # AM_MAKE_INCLUDE() + # ----------------- +@@ -683,27 +570,16 @@ + rm -f confinc confmf + ]) + +-# -*- Autoconf -*- +- +- +-# Copyright (C) 1997, 1999, 2000, 2001, 2003 Free Software Foundation, Inc. +- +-# 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, or (at your option) +-# any later version. ++# Fake the existence of programs that GNU maintainers use. -*- Autoconf -*- + +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. ++# Copyright (C) 1997, 1999, 2000, 2001, 2003, 2005 ++# Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + +-# serial 3 ++# serial 4 + + # AM_MISSING_PROG(NAME, PROGRAM) + # ------------------------------ +@@ -729,27 +605,16 @@ + fi + ]) + ++# Copyright (C) 2003, 2004, 2005 Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. ++ + # AM_PROG_MKDIR_P + # --------------- + # Check whether `mkdir -p' is supported, fallback to mkinstalldirs otherwise. +- +-# Copyright (C) 2003, 2004 Free Software Foundation, Inc. +- +-# 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, or (at your option) +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. +- ++# + # Automake 1.8 used `mkdir -m 0755 -p --' to ensure that directories + # created by `make install' are always world readable, even if the + # installer happens to have an overly restrictive umask (e.g. 077). +@@ -803,26 +668,15 @@ + fi + AC_SUBST([mkdir_p])]) + +-# Helper functions for option handling. -*- Autoconf -*- ++# Helper functions for option handling. -*- Autoconf -*- + +-# Copyright (C) 2001, 2002, 2003 Free Software Foundation, Inc. +- +-# 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, or (at your option) +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. ++# Copyright (C) 2001, 2002, 2003, 2005 Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + +-# serial 2 ++# serial 3 + + # _AM_MANGLE_OPTION(NAME) + # ----------------------- +@@ -847,28 +701,16 @@ + AC_DEFUN([_AM_IF_OPTION], + [m4_ifset(_AM_MANGLE_OPTION([$1]), [$2], [$3])]) + +-# +-# Check to make sure that the build environment is sane. +-# +- +-# Copyright (C) 1996, 1997, 2000, 2001, 2003 Free Software Foundation, Inc. +- +-# 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, or (at your option) +-# any later version. ++# Check to make sure that the build environment is sane. -*- Autoconf -*- + +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. ++# Copyright (C) 1996, 1997, 2000, 2001, 2003, 2005 ++# Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + +-# serial 3 ++# serial 4 + + # AM_SANITY_CHECK + # --------------- +@@ -911,25 +753,14 @@ + fi + AC_MSG_RESULT(yes)]) + +-# AM_PROG_INSTALL_STRIP +- +-# Copyright (C) 2001, 2003 Free Software Foundation, Inc. +- +-# 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, or (at your option) +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. ++# Copyright (C) 2001, 2003, 2005 Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + ++# AM_PROG_INSTALL_STRIP ++# --------------------- + # One issue with vendor `install' (even GNU) is that you can't + # specify the program used to strip binaries. This is especially + # annoying in cross-compiling environments, where the build's strip +@@ -952,25 +783,13 @@ + + # Check how to create a tarball. -*- Autoconf -*- + +-# Copyright (C) 2004 Free Software Foundation, Inc. +- +-# 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, or (at your option) +-# 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., 59 Temple Place - Suite 330, Boston, MA +-# 02111-1307, USA. +- +-# serial 1 ++# Copyright (C) 2004, 2005 Free Software Foundation, Inc. ++# ++# This file is free software; the Free Software Foundation ++# gives unlimited permission to copy and/or distribute it, ++# with or without modifications, as long as this notice is preserved. + ++# serial 2 + + # _AM_PROG_TAR(FORMAT) + # -------------------- +diff -Naur grub-0.97.orig/ChangeLog grub-0.97/ChangeLog +--- grub-0.97.orig/ChangeLog 2005-05-07 19:47:02.000000000 -0700 ++++ grub-0.97/ChangeLog 2006-07-04 00:01:50.000000000 -0700 +@@ -1,3 +1,51 @@ ++2006-05-02 Pavel Roskin ++ ++ * stage2/stage2.c (run_menu): Fix "savedefault" to save only top ++ level menu positions. Remember current position when calling a ++ submenu. Don't recalculate it when booting from a submenu. ++ ++ * grub/main.c (main): Make sure the boot drive number doesn't ++ exceed 255. ++ ++2006-05-02 Vesa Jaaskelainen ++ ++ * stage2/shared.h (vbe_mode): Back ported aligment fix from GRUB 2 ++ to GRUB Legacy. Problem reported by Gerardo Richarte. ++ ++2006-04-23 Robert Millan ++ ++ * grub/asmstub.c (get_diskinfo): Optimize sysctl routine. ++ ++2006-04-20 Robert Millan ++ ++ Fixes for kernel of FreeBSD: ++ * grub/asmstub.c (get_diskinfo): Toggle "kern.geom.debugflags" sysctl ++ before opening a device for writing. ++ * util/grub-install.in: Devices don't have this "r" prefix anymore. ++ ++2006-04-16 Yoshinori K. Okuji ++ ++ * docs/multiboot.texi: Correct the offset of address ++ fields. Reported by Jeroen Dekkers. ++ ++2006-03-21 Yoshinori K. Okuji ++ ++ * stage2/builtins.c (setup_func): Specify the size of DEVICE to ++ grub_strncat instead of a strange number 256. Reported by Vitaly ++ Fertman . ++ ++2005-09-29 Yoshinori K. Okuji ++ ++ * docs/multiboot.texi: Fix a bug in the byte order of ++ boot_device. I hope this won't affect any OS image. ++ Increased the version number to 0.6.94. ++ ++2005-09-28 Yoshinori K. Okuji ++ ++ * stage2/boot.c (load_image): Even if an OS image is an ELF ++ object, use the a.out kludge if MULTIBOOT_AOUT_KLUDGE is ++ specified. ++ + 2005-05-08 Yoshinori K. Okuji + + * configure.ac (AC_INIT): Upgraded to 0.97. +diff -Naur grub-0.97.orig/configure grub-0.97/configure +--- grub-0.97.orig/configure 2005-05-07 19:48:12.000000000 -0700 ++++ grub-0.97/configure 2006-07-04 00:08:05.000000000 -0700 +@@ -311,7 +311,7 @@ + # include + #endif" + +-ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS INSTALL_PROGRAM INSTALL_SCRIPT INSTALL_DATA CYGPATH_W PACKAGE VERSION ACLOCAL AUTOCONF AUTOMAKE AUTOHEADER MAKEINFO install_sh STRIP ac_ct_STRIP INSTALL_STRIP_PROGRAM mkdir_p AWK SET_MAKE am__leading_dot AMTAR am__tar am__untar build build_cpu build_vendor build_os host host_cpu host_vendor host_os MAINTAINER_MODE_TRUE MAINTAINER_MODE_FALSE MAINT PERL CC ac_ct_CC CFLAGS LDFLAGS CPPFLAGS EXEEXT OBJEXT DEPDIR am__include am__quote AMDEP_TRUE AMDEP_FALSE AMDEPBACKSLASH CCDEPMODE am__fastdepCC_TRUE am__fastdepCC_FALSE CCAS RANLIB ac_ct_RANLIB STAGE1_CFLAGS STAGE2_CFLAGS GRUB_CFLAGS OBJCOPY ac_ct_OBJCOPY GRUB_LIBS CPP EGREP NETBOOT_SUPPORT_TRUE NETBOOT_SUPPORT_FALSE DISKLESS_SUPPORT_TRUE DISKLESS_SUPPORT_FALSE HERCULES_SUPPORT_TRUE HERCULES_SUPPORT_FALSE SERIAL_SUPPORT_TRUE SERIAL_SUPPORT_FALSE SERIAL_SPEED_SIMULATION_TRUE SERIAL_SPEED_SIMULATION_FALSE BUILD_EXAMPLE_KERNEL_TRUE BUILD_EXAMPLE_KERNEL_FALSE FSYS_CFLAGS NET_CFLAGS NET_EXTRAFLAGS NETBOOT_DRIVERS CCASFLAGS LIBOBJS LTLIBOBJS' ++ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS INSTALL_PROGRAM INSTALL_SCRIPT INSTALL_DATA CYGPATH_W PACKAGE VERSION ACLOCAL AUTOCONF AUTOMAKE AUTOHEADER MAKEINFO install_sh STRIP ac_ct_STRIP INSTALL_STRIP_PROGRAM mkdir_p AWK SET_MAKE am__leading_dot AMTAR am__tar am__untar build build_cpu build_vendor build_os host host_cpu host_vendor host_os MAINTAINER_MODE_TRUE MAINTAINER_MODE_FALSE MAINT PERL CC ac_ct_CC CFLAGS LDFLAGS CPPFLAGS EXEEXT OBJEXT DEPDIR am__include am__quote AMDEP_TRUE AMDEP_FALSE AMDEPBACKSLASH CCDEPMODE am__fastdepCC_TRUE am__fastdepCC_FALSE CCAS RANLIB ac_ct_RANLIB STAGE1_CFLAGS STAGE2_CFLAGS GRUB_CFLAGS OBJCOPY ac_ct_OBJCOPY GRUB_LIBS CPP EGREP NETBOOT_SUPPORT_TRUE NETBOOT_SUPPORT_FALSE DISKLESS_SUPPORT_TRUE DISKLESS_SUPPORT_FALSE GRAPHICS_SUPPORT_TRUE GRAPHICS_SUPPORT_FALSE HERCULES_SUPPORT_TRUE HERCULES_SUPPORT_FALSE SERIAL_SUPPORT_TRUE SERIAL_SUPPORT_FALSE SERIAL_SPEED_SIMULATION_TRUE SERIAL_SPEED_SIMULATION_FALSE BUILD_EXAMPLE_KERNEL_TRUE BUILD_EXAMPLE_KERNEL_FALSE FSYS_CFLAGS NET_CFLAGS NET_EXTRAFLAGS NETBOOT_DRIVERS CCASFLAGS LIBOBJS LTLIBOBJS' + ac_subst_files='' + + # Initialize some variables set by options. +@@ -914,6 +914,7 @@ + set the default memory location for WD/SMC + --enable-cs-scan=LIST probe for CS89x0 base address using LIST + --enable-diskless enable diskless support ++ --disable-graphics disable graphics terminal support + --disable-hercules disable hercules terminal support + --disable-serial disable serial terminal support + --enable-serial-speed-simulation +@@ -5966,6 +5967,22 @@ + fi + + ++# Check whether --enable-graphics or --disable-graphics was given. ++if test "${enable_graphics+set}" = set; then ++ enableval="$enable_graphics" ++ ++fi; ++ ++ ++if test "x$enable_graphics" != xno; then ++ GRAPHICS_SUPPORT_TRUE= ++ GRAPHICS_SUPPORT_FALSE='#' ++else ++ GRAPHICS_SUPPORT_TRUE='#' ++ GRAPHICS_SUPPORT_FALSE= ++fi ++ ++ + # Check whether --enable-hercules or --disable-hercules was given. + if test "${enable_hercules+set}" = set; then + enableval="$enable_hercules" +@@ -6270,6 +6287,13 @@ + Usually this means the macro was only invoked conditionally." >&2;} + { (exit 1); exit 1; }; } + fi ++if test -z "${GRAPHICS_SUPPORT_TRUE}" && test -z "${GRAPHICS_SUPPORT_FALSE}"; then ++ { { echo "$as_me:$LINENO: error: conditional \"GRAPHICS_SUPPORT\" was never defined. ++Usually this means the macro was only invoked conditionally." >&5 ++echo "$as_me: error: conditional \"GRAPHICS_SUPPORT\" was never defined. ++Usually this means the macro was only invoked conditionally." >&2;} ++ { (exit 1); exit 1; }; } ++fi + if test -z "${HERCULES_SUPPORT_TRUE}" && test -z "${HERCULES_SUPPORT_FALSE}"; then + { { echo "$as_me:$LINENO: error: conditional \"HERCULES_SUPPORT\" was never defined. + Usually this means the macro was only invoked conditionally." >&5 +@@ -6907,6 +6931,8 @@ + s,@NETBOOT_SUPPORT_FALSE@,$NETBOOT_SUPPORT_FALSE,;t t + s,@DISKLESS_SUPPORT_TRUE@,$DISKLESS_SUPPORT_TRUE,;t t + s,@DISKLESS_SUPPORT_FALSE@,$DISKLESS_SUPPORT_FALSE,;t t ++s,@GRAPHICS_SUPPORT_TRUE@,$GRAPHICS_SUPPORT_TRUE,;t t ++s,@GRAPHICS_SUPPORT_FALSE@,$GRAPHICS_SUPPORT_FALSE,;t t + s,@HERCULES_SUPPORT_TRUE@,$HERCULES_SUPPORT_TRUE,;t t + s,@HERCULES_SUPPORT_FALSE@,$HERCULES_SUPPORT_FALSE,;t t + s,@SERIAL_SUPPORT_TRUE@,$SERIAL_SUPPORT_TRUE,;t t +diff -Naur grub-0.97.orig/configure.ac grub-0.97/configure.ac +--- grub-0.97.orig/configure.ac 2005-05-07 19:36:03.000000000 -0700 ++++ grub-0.97/configure.ac 2006-07-03 23:58:41.000000000 -0700 +@@ -595,6 +595,11 @@ + [ --enable-diskless enable diskless support]) + AM_CONDITIONAL(DISKLESS_SUPPORT, test "x$enable_diskless" = xyes) + ++dnl Graphical splashscreen support ++AC_ARG_ENABLE(graphics, ++ [ --disable-graphics disable graphics terminal support]) ++AM_CONDITIONAL(GRAPHICS_SUPPORT, test "x$enable_graphics" != xno) ++ + dnl Hercules terminal + AC_ARG_ENABLE(hercules, + [ --disable-hercules disable hercules terminal support]) +diff -Naur grub-0.97.orig/docs/grub.8 grub-0.97/docs/grub.8 +--- grub-0.97.orig/docs/grub.8 2005-05-07 19:48:56.000000000 -0700 ++++ grub-0.97/docs/grub.8 2006-07-04 00:01:50.000000000 -0700 +@@ -1,5 +1,5 @@ + .\" DO NOT MODIFY THIS FILE! It was generated by help2man 1.23. +-.TH GRUB "8" "May 2005" "grub (GNU GRUB 0.97)" FSF ++.TH GRUB "8" "September 2005" "grub (GNU GRUB 0.97)" FSF + .SH NAME + grub \- the grub shell + .SH SYNOPSIS +diff -Naur grub-0.97.orig/docs/grub.texi grub-0.97/docs/grub.texi +--- grub-0.97.orig/docs/grub.texi 2005-05-07 19:59:59.000000000 -0700 ++++ grub-0.97/docs/grub.texi 2006-07-04 00:00:54.000000000 -0700 +@@ -2199,6 +2199,7 @@ + * rarp:: Initialize a network device via RARP + * serial:: Set up a serial device + * setkey:: Configure the key map ++* splashimage:: Use a splash image + * terminal:: Choose a terminal + * terminfo:: Define escape sequences for a terminal + * tftpserver:: Specify a TFTP server +@@ -2578,6 +2579,16 @@ + @end deffn + + ++@node splashimage ++@subsection splashimage ++ ++@deffn Command splashimage file ++Select an image to use as the background image. This should be ++specified using normal GRUB device naming syntax. The format of the ++file is a gzipped xpm which is 640x480 with a 14 color palette. ++@end deffn ++ ++ + @node terminal + @subsection terminal + +@@ -2685,6 +2696,7 @@ + * module:: Load a module + * modulenounzip:: Load a module without decompression + * pause:: Wait for a key press ++* print:: Print a message + * quit:: Exit from the grub shell + * reboot:: Reboot your computer + * read:: Read data from memory +@@ -3091,6 +3103,16 @@ + @end deffn + + ++@node print ++@subsection print ++ ++@deffn Command print message @dots{} ++Print the @var{message}. Note that placing @key{^G} (ASCII code 7) in the ++message will cause the speaker to emit the standard beep sound, which is ++useful for visually impaired people. ++@end deffn ++ ++ + @node quit + @subsection quit + +diff -Naur grub-0.97.orig/docs/multiboot.texi grub-0.97/docs/multiboot.texi +--- grub-0.97.orig/docs/multiboot.texi 2003-07-09 04:45:36.000000000 -0700 ++++ grub-0.97/docs/multiboot.texi 2006-07-04 00:01:50.000000000 -0700 +@@ -25,7 +25,7 @@ + @ifinfo + Copyright @copyright{} 1995, 96 Bryan Ford + Copyright @copyright{} 1995, 96 Erich Stefan Boleyn +-Copyright @copyright{} 1999, 2000, 2001, 2002 Free Software Foundation, Inc. ++Copyright @copyright{} 1999, 2000, 2001, 2002, 2005, 2006 Free Software Foundation, Inc. + + Permission is granted to make and distribute verbatim copies of + this manual provided the copyright notice and this permission notice +@@ -57,7 +57,7 @@ + @vskip 0pt plus 1filll + Copyright @copyright{} 1995, 96 Bryan Ford + Copyright @copyright{} 1995, 96 Erich Stefan Boleyn +-Copyright @copyright{} 1999, 2000, 2001, 2002 Free Software Foundation, Inc. ++Copyright @copyright{} 1999, 2000, 2001, 2002, 2005, 2006 Free Software Foundation, Inc. + + Permission is granted to make and distribute verbatim copies of + this manual provided the copyright notice and this permission notice +@@ -80,7 +80,7 @@ + @top Multiboot Specification + + This file documents Multiboot Specification, the proposal for the boot +-sequence standard. This edition documents version 0.6.93. ++sequence standard. This edition documents version 0.6.94. + @end ifnottex + + @menu +@@ -426,7 +426,7 @@ + kernel. + + If bit 16 in the @samp{flags} word is set, then the fields at offsets +-8-24 in the Multiboot header are valid, and the boot loader should use ++12-28 in the Multiboot header are valid, and the boot loader should use + them instead of the fields in the actual executable header to calculate + where to load the OS image. This information does not need to be + provided if the kernel image is in @sc{elf} format, but it @emph{must} +@@ -677,7 +677,7 @@ + @example + @group + +-------+-------+-------+-------+ +-| drive | part1 | part2 | part3 | ++| part3 | part2 | part1 | drive | + +-------+-------+-------+-------+ + @end group + @end example +@@ -1199,6 +1199,13 @@ + @email{bug-grub@@gnu.org}, from Bryan Ford and Erich Stefan Boleyn. + @end itemize + ++@item ++The byte order of the @samp{boot_device} in Multiboot information is ++reversed. This was a mistake. ++ ++@item ++The offset of the address fields were wrong. ++ + @item 0.6 + @itemize @bullet + @item +diff -Naur grub-0.97.orig/grub/asmstub.c grub-0.97/grub/asmstub.c +--- grub-0.97.orig/grub/asmstub.c 2005-02-16 12:45:14.000000000 -0800 ++++ grub-0.97/grub/asmstub.c 2006-07-04 00:01:50.000000000 -0700 +@@ -42,6 +42,12 @@ + #include + #include + #include ++#include ++ ++#include ++#ifndef PAGESIZE ++#define PAGESIZE 4096 ++#endif + + #ifdef __linux__ + # include /* ioctl */ +@@ -55,6 +61,10 @@ + # endif /* ! BLKFLSBUF */ + #endif /* __linux__ */ + ++#if defined(__FreeBSD_kernel__) || defined(__FreeBSD__) ++# include ++#endif ++ + /* We want to prevent any circularararity in our stubs, as well as + libc name clashes. */ + #define WITHOUT_LIBC_STUBS 1 +@@ -144,6 +154,22 @@ + assert (grub_scratch_mem == 0); + scratch = malloc (0x100000 + EXTENDED_MEMSIZE + 15); + assert (scratch); ++ ++ { ++ char *p; ++ int ret; ++ ++ /* Align to a multiple of PAGESIZE, assumed to be a power of two. */ ++ p = (char *) (((long) scratch) & ~(PAGESIZE - 1)); ++ ++ /* The simulated stack needs to be executable, since GCC uses stack ++ * trampolines to implement nested functions. ++ */ ++ ret = mprotect (p, 0x100000 + EXTENDED_MEMSIZE + 15, ++ PROT_READ | PROT_WRITE | PROT_EXEC); ++ assert (ret == 0); ++ } ++ + grub_scratch_mem = (char *) ((((int) scratch) >> 4) << 4); + + /* FIXME: simulate the memory holes using mprot, if available. */ +@@ -777,7 +803,39 @@ + + /* Open read/write, or read-only if that failed. */ + if (! read_only) +- disks[drive].flags = open (devname, O_RDWR); ++ { ++/* By default, kernel of FreeBSD does not allow overwriting MBR */ ++#if defined(__FreeBSD_kernel__) || defined(__FreeBSD__) ++#define GEOM_SYSCTL "kern.geom.debugflags" ++ int old_flags, flags; ++ size_t sizeof_int = sizeof (int); ++ ++ if (sysctlbyname (GEOM_SYSCTL, &old_flags, &sizeof_int, NULL, 0) != 0) ++ grub_printf ("failed to get " GEOM_SYSCTL "sysctl: %s\n", strerror (errno)); ++ ++ if ((old_flags & 0x10) == 0) ++ { ++ /* "allow foot shooting", see geom(4) */ ++ flags = old_flags | 0x10; ++ ++ if (sysctlbyname (GEOM_SYSCTL, NULL, NULL, &flags, sizeof (int)) != 0) ++ { ++ flags = old_flags; ++ grub_printf ("failed to set " GEOM_SYSCTL "sysctl: %s\n", strerror (errno)); ++ } ++ } ++ else ++ flags = old_flags; ++#endif ++ disks[drive].flags = open (devname, O_RDWR); ++#if defined(__FreeBSD_kernel__) || defined(__FreeBSD__) ++ if (flags != old_flags) ++ { ++ if (sysctlbyname (GEOM_SYSCTL, NULL, NULL, &old_flags, sizeof (int)) != 0) ++ grub_printf ("failed to set " GEOM_SYSCTL "sysctl: %s\n", strerror (errno)); ++ } ++#endif ++ } + + if (disks[drive].flags == -1) + { +diff -Naur grub-0.97.orig/grub/main.c grub-0.97/grub/main.c +--- grub-0.97.orig/grub/main.c 2003-07-09 04:45:36.000000000 -0700 ++++ grub-0.97/grub/main.c 2006-07-04 00:01:50.000000000 -0700 +@@ -32,6 +32,7 @@ + #define WITHOUT_LIBC_STUBS 1 + #include + #include ++#include + + char *program_name = 0; + int use_config_file = 1; +@@ -192,6 +193,12 @@ + perror ("strtoul"); + exit (1); + } ++ if (boot_drive >= NUM_DISKS) ++ { ++ fprintf (stderr, "boot_drive should be from 0 to %d\n", ++ NUM_DISKS - 1); ++ exit (1); ++ } + break; + + case OPT_NO_CONFIG_FILE: +diff -Naur grub-0.97.orig/lib/device.c grub-0.97/lib/device.c +--- grub-0.97.orig/lib/device.c 2005-03-27 15:14:25.000000000 -0800 ++++ grub-0.97/lib/device.c 2006-07-04 00:00:44.000000000 -0700 +@@ -131,6 +131,152 @@ + #include + #include + ++#if defined(__linux__) ++/* The 2.6 kernel has removed all of the geometry handling for IDE drives ++ * that did fixups for LBA, etc. This means that the geometry we get ++ * with the ioctl has a good chance of being wrong. So, we get to ++ * also know about partition tables and try to read what the geometry ++ * is there. *grumble* Very closely based on code from cfdisk ++ */ ++static void get_kernel_geometry(int fd, long long *cyl, int *heads, int *sectors) { ++ struct hd_geometry hdg; ++ ++ if (ioctl (fd, HDIO_GETGEO, &hdg)) ++ return; ++ ++ *cyl = hdg.cylinders; ++ *heads = hdg.heads; ++ *sectors = hdg.sectors; ++} ++ ++struct partition { ++ unsigned char boot_ind; /* 0x80 - active */ ++ unsigned char head; /* starting head */ ++ unsigned char sector; /* starting sector */ ++ unsigned char cyl; /* starting cylinder */ ++ unsigned char sys_ind; /* What partition type */ ++ unsigned char end_head; /* end head */ ++ unsigned char end_sector; /* end sector */ ++ unsigned char end_cyl; /* end cylinder */ ++ unsigned char start4[4]; /* starting sector counting from 0 */ ++ unsigned char size4[4]; /* nr of sectors in partition */ ++}; ++ ++#define ALIGNMENT 2 ++typedef union { ++ struct { ++ unsigned char align[ALIGNMENT]; ++ unsigned char b[SECTOR_SIZE]; ++ } c; ++ struct { ++ unsigned char align[ALIGNMENT]; ++ unsigned char buffer[0x1BE]; ++ struct partition part[4]; ++ unsigned char magicflag[2]; ++ } p; ++} partition_table; ++ ++#define PART_TABLE_FLAG0 0x55 ++#define PART_TABLE_FLAG1 0xAA ++ ++static void ++get_partition_table_geometry(partition_table *bufp, long long *cyl, int *heads, ++ int *sectors) { ++ struct partition *p; ++ int i,h,s,hh,ss; ++ int first = 1; ++ int bad = 0; ++ ++ if (bufp->p.magicflag[0] != PART_TABLE_FLAG0 || ++ bufp->p.magicflag[1] != PART_TABLE_FLAG1) { ++ /* Matthew Wilcox: slightly friendlier version of ++ fatal(_("Bad signature on partition table"), 3); ++ */ ++ fprintf(stderr, "Unknown partition table signature\n"); ++ return; ++ } ++ ++ hh = ss = 0; ++ for (i=0; i<4; i++) { ++ p = &(bufp->p.part[i]); ++ if (p->sys_ind != 0) { ++ h = p->end_head + 1; ++ s = (p->end_sector & 077); ++ if (first) { ++ hh = h; ++ ss = s; ++ first = 0; ++ } else if (hh != h || ss != s) ++ bad = 1; ++ } ++ } ++ ++ if (!first && !bad) { ++ *heads = hh; ++ *sectors = ss; ++ } ++} ++ ++static long long my_lseek (unsigned int fd, long long offset, ++ unsigned int origin) ++{ ++#if defined(__linux__) && (!defined(__GLIBC__) || \ ++ ((__GLIBC__ < 2) || ((__GLIBC__ == 2) && (__GLIBC_MINOR__ < 1)))) ++ /* Maybe libc doesn't have large file support. */ ++ loff_t offset, result; ++ static int _llseek (uint filedes, ulong hi, ulong lo, ++ loff_t *res, uint wh); ++ _syscall5 (int, _llseek, uint, filedes, ulong, hi, ulong, lo, ++ loff_t *, res, uint, wh); ++ ++ if (_llseek (fd, offset >> 32, offset & 0xffffffff, &result, SEEK_SET) < 0) ++ return (long long) -1; ++ return result; ++#else ++ return lseek(fd, offset, SEEK_SET); ++#endif ++} ++ ++static void get_linux_geometry (int fd, struct geometry *geom) { ++ long long kern_cyl = 0; int kern_head = 0, kern_sectors = 0; ++ long long pt_cyl = 0; int pt_head = 0, pt_sectors = 0; ++ partition_table bufp; ++ char *buff, *buf_unaligned; ++ ++ buf_unaligned = malloc(sizeof(partition_table) + 4095); ++ buff = (char *) (((unsigned long)buf_unaligned + 4096 - 1) & ++ (~(4096-1))); ++ ++ get_kernel_geometry(fd, &kern_cyl, &kern_head, &kern_sectors); ++ ++ if (my_lseek (fd, 0*SECTOR_SIZE, SEEK_SET) < 0) { ++ fprintf(stderr, "Unable to seek"); ++ } ++ ++ if (read(fd, buff, SECTOR_SIZE) == SECTOR_SIZE) { ++ memcpy(bufp.c.b, buff, SECTOR_SIZE); ++ get_partition_table_geometry(&bufp, &pt_cyl, &pt_head, &pt_sectors); ++ } else { ++ fprintf(stderr, "Unable to read partition table: %s\n", strerror(errno)); ++ } ++ ++ if (pt_head && pt_sectors) { ++ int cyl_size; ++ ++ geom->heads = pt_head; ++ geom->sectors = pt_sectors; ++ cyl_size = pt_head * pt_sectors; ++ geom->cylinders = geom->total_sectors/cyl_size; ++ } else { ++ geom->heads = kern_head; ++ geom->sectors = kern_sectors; ++ geom->cylinders = kern_cyl; ++ } ++ ++ return; ++} ++#endif ++ + /* Get the geometry of a drive DRIVE. */ + void + get_drive_geometry (struct geometry *geom, char **map, int drive) +@@ -151,21 +297,16 @@ + #if defined(__linux__) + /* Linux */ + { +- struct hd_geometry hdg; + unsigned long nr; +- +- if (ioctl (fd, HDIO_GETGEO, &hdg)) +- goto fail; + + if (ioctl (fd, BLKGETSIZE, &nr)) + goto fail; + + /* Got the geometry, so save it. */ +- geom->cylinders = hdg.cylinders; +- geom->heads = hdg.heads; +- geom->sectors = hdg.sectors; + geom->total_sectors = nr; +- ++ get_linux_geometry(fd, geom); ++ if (!geom->heads && !geom->cylinders && !geom->sectors) ++ goto fail; + goto success; + } + +@@ -403,6 +544,18 @@ + } + + static void ++get_cciss_disk_name (char *name, int controller, int drive) ++{ ++ sprintf (name, "/dev/cciss/c%dd%d", controller, drive); ++} ++ ++static void ++get_ida_disk_name (char *name, int controller, int drive) ++{ ++ sprintf (name, "/dev/ida/c%dd%d", controller, drive); ++} ++ ++static void + get_ataraid_disk_name (char *name, int unit) + { + sprintf (name, "/dev/ataraid/d%c", unit + '0'); +@@ -801,6 +954,74 @@ + } + } + } ++ ++ /* This is for CCISS, its like the DAC960 - we have ++ /dev/cciss/dp ++ ++ It currently supports up to 3 controllers, 10 logical volumes ++ and 10 partitions ++ ++ Code gratuitously copied from DAC960 above. ++ Horms 23rd July 2004 ++ */ ++ { ++ int controller, drive; ++ ++ for (controller = 0; controller < 2; controller++) ++ { ++ for (drive = 0; drive < 9; drive++) ++ { ++ char name[24]; ++ ++ get_cciss_disk_name (name, controller, drive); ++ if (check_device (name)) ++ { ++ (*map)[num_hd + 0x80] = strdup (name); ++ assert ((*map)[num_hd + 0x80]); ++ ++ /* If the device map file is opened, write the map. */ ++ if (fp) ++ fprintf (fp, "(hd%d)\t%s\n", num_hd, name); ++ ++ num_hd++; ++ } ++ } ++ } ++ } ++ ++ /* This is for Compaq Smart Array, its like the DAC960 - we have ++ /dev/ida/dp ++ ++ It currently supports up to 3 controllers, 10 logical volumes ++ and 15 partitions ++ ++ Code gratuitously copied from DAC960 above. ++ Piotr Roszatycki ++ */ ++ { ++ int controller, drive; ++ ++ for (controller = 0; controller < 2; controller++) ++ { ++ for (drive = 0; drive < 9; drive++) ++ { ++ char name[24]; ++ ++ get_ida_disk_name (name, controller, drive); ++ if (check_device (name)) ++ { ++ (*map)[num_hd + 0x80] = strdup (name); ++ assert ((*map)[num_hd + 0x80]); ++ ++ /* If the device map file is opened, write the map. */ ++ if (fp) ++ fprintf (fp, "(hd%d)\t%s\n", num_hd, name); ++ ++ num_hd++; ++ } ++ } ++ } ++ } + #endif /* __linux__ */ + + /* OK, close the device map file if opened. */ +@@ -844,6 +1065,7 @@ + { + char dev[PATH_MAX]; /* XXX */ + int fd; ++ off_t offset = (off_t) sector * (off_t) SECTOR_SIZE; + + if ((partition & 0x00FF00) != 0x00FF00) + { +@@ -861,8 +1083,14 @@ + if (strcmp (dev + strlen(dev) - 5, "/disc") == 0) + strcpy (dev + strlen(dev) - 5, "/part"); + } +- sprintf (dev + strlen(dev), "%d", ((partition >> 16) & 0xFF) + 1); +- ++ sprintf (dev + strlen(dev), "%s%d", ++ /* Compaq smart and others */ ++ (strncmp(dev, "/dev/ida/", 9) == 0 || ++ strncmp(dev, "/dev/ataraid/", 13) == 0 || ++ strncmp(dev, "/dev/cciss/", 11) == 0 || ++ strncmp(dev, "/dev/rd/", 8) == 0) ? "p" : "", ++ ((partition >> 16) & 0xFF) + 1); ++ + /* Open the partition. */ + fd = open (dev, O_RDWR); + if (fd < 0) +@@ -870,35 +1098,13 @@ + errnum = ERR_NO_PART; + return 0; + } +- +-#if defined(__linux__) && (!defined(__GLIBC__) || \ +- ((__GLIBC__ < 2) || ((__GLIBC__ == 2) && (__GLIBC_MINOR__ < 1)))) +- /* Maybe libc doesn't have large file support. */ +- { +- loff_t offset, result; +- static int _llseek (uint filedes, ulong hi, ulong lo, +- loff_t *res, uint wh); +- _syscall5 (int, _llseek, uint, filedes, ulong, hi, ulong, lo, +- loff_t *, res, uint, wh); + +- offset = (loff_t) sector * (loff_t) SECTOR_SIZE; +- if (_llseek (fd, offset >> 32, offset & 0xffffffff, &result, SEEK_SET)) +- { +- errnum = ERR_DEV_VALUES; +- return 0; +- } +- } +-#else +- { +- off_t offset = (off_t) sector * (off_t) SECTOR_SIZE; + +- if (lseek (fd, offset, SEEK_SET) != offset) +- { +- errnum = ERR_DEV_VALUES; +- return 0; +- } +- } +-#endif ++ if (my_lseek(fd, offset, SEEK_SET) != offset) ++ { ++ errnum = ERR_DEV_VALUES; ++ return 0; ++ } + + if (write (fd, buf, size * SECTOR_SIZE) != (size * SECTOR_SIZE)) + { +diff -Naur grub-0.97.orig/stage2/asm.S grub-0.97/stage2/asm.S +--- grub-0.97.orig/stage2/asm.S 2004-06-19 09:55:22.000000000 -0700 ++++ grub-0.97/stage2/asm.S 2006-07-04 00:01:19.000000000 -0700 +@@ -1651,7 +1651,29 @@ + jnz 3f + ret + +-3: /* use keyboard controller */ ++3: /* ++ * try to switch gateA20 using PORT92, the "Fast A20 and Init" ++ * register ++ */ ++ mov $0x92, %dx ++ inb %dx, %al ++ /* skip the port92 code if it's unimplemented (read returns 0xff) */ ++ cmpb $0xff, %al ++ jz 6f ++ ++ /* set or clear bit1, the ALT_A20_GATE bit */ ++ movb 4(%esp), %ah ++ testb %ah, %ah ++ jz 4f ++ orb $2, %al ++ jmp 5f ++4: and $0xfd, %al ++ ++ /* clear the INIT_NOW bit don't accidently reset the machine */ ++5: and $0xfe, %al ++ outb %al, %dx ++ ++6: /* use keyboard controller */ + pushl %eax + + call gloop1 +@@ -1661,9 +1683,12 @@ + + gloopint1: + inb $K_STATUS ++ cmpb $0xff, %al ++ jz gloopint1_done + andb $K_IBUF_FUL, %al + jnz gloopint1 + ++gloopint1_done: + movb $KB_OUTPUT_MASK, %al + cmpb $0, 0x8(%esp) + jz gdoit +@@ -1684,6 +1709,8 @@ + + gloop1: + inb $K_STATUS ++ cmpb $0xff, %al ++ jz gloop2ret + andb $K_IBUF_FUL, %al + jnz gloop1 + +@@ -1991,6 +2018,11 @@ + ENTRY(console_getkey) + push %ebp + ++wait_for_key: ++ call EXT_C(console_checkkey) ++ incl %eax ++ jz wait_for_key ++ + call EXT_C(prot_to_real) + .code16 + +@@ -2216,7 +2248,304 @@ + pop %ebx + pop %ebp + ret +- ++ ++ ++/* graphics mode functions */ ++#ifdef SUPPORT_GRAPHICS ++VARIABLE(cursorX) ++.word 0 ++VARIABLE(cursorY) ++.word 0 ++VARIABLE(cursorCount) ++.word 0 ++VARIABLE(cursorBuf) ++.byte 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ++ ++ ++/* ++ * set_int1c_handler(void) ++ */ ++ENTRY(set_int1c_handler) ++ pushl %edi ++ ++ /* save the original int1c handler */ ++ movl $0x70, %edi ++ movw (%edi), %ax ++ movw %ax, ABS(int1c_offset) ++ movw 2(%edi), %ax ++ movw %ax, ABS(int1c_segment) ++ ++ /* save the new int1c handler */ ++ movw $ABS(int1c_handler), %ax ++ movw %ax, (%edi) ++ xorw %ax, %ax ++ movw %ax, 2(%edi) ++ ++ popl %edi ++ ret ++ ++ ++/* ++ * unset_int1c_handler(void) ++ */ ++ENTRY(unset_int1c_handler) ++ pushl %edi ++ ++ /* check if int1c_handler is set */ ++ movl $0x70, %edi ++ movw $ABS(int1c_handler), %ax ++ cmpw %ax, (%edi) ++ jne int1c_1 ++ xorw %ax, %ax ++ cmpw %ax, 2(%edi) ++ jne int1c_1 ++ ++ /* restore the original */ ++ movw ABS(int1c_offset), %ax ++ movw %ax, (%edi) ++ movw ABS(int1c_segment), %ax ++ movw %ax, 2(%edi) ++ ++int1c_1: ++ popl %edi ++ ret ++ ++ ++/* ++ * blinks graphics cursor ++ */ ++ .code16 ++write_data: ++ movw $0, %ax ++ movw %ax, %ds ++ ++ mov $0xA000, %ax /* video in es:di */ ++ mov %ax, %es ++ mov $80, %ax ++ movw $ABS(cursorY), %si ++ mov %ds:(%si), %bx ++ mul %bx ++ movw $ABS(cursorX), %si ++ mov %ds:(%si), %bx ++ shr $3, %bx /* %bx /= 8 */ ++ add %bx, %ax ++ mov %ax, %di ++ ++ movw $ABS(cursorBuf), %si /* fontBuf in ds:si */ ++ ++ /* prepare for data moving */ ++ mov $16, %dx /* altura da fonte */ ++ mov $80, %bx /* bytes por linha */ ++ ++write_loop: ++ movb %ds:(%si), %al ++ xorb $0xff, %al ++ movb %al, %ds:(%si) /* invert cursorBuf */ ++ movb %al, %es:(%di) /* write to video */ ++ add %bx, %di ++ inc %si ++ dec %dx ++ jg write_loop ++ ret ++ ++int1c_handler: ++ pusha ++ mov $0, %ax ++ mov %ax, %ds ++ mov $ABS(cursorCount), %si ++ mov %ds:(%si), %ax ++ inc %ax ++ mov %ax, %ds:(%si) ++ cmp $9, %ax ++ jne int1c_done ++ ++ mov $0, %ax ++ mov %ax, %ds:(%si) ++ call write_data ++ ++int1c_done: ++ popa ++ iret ++ /* call previous int1c handler */ ++ /* ljmp */ ++ .byte 0xea ++int1c_offset: .word 0 ++int1c_segment: .word 0 ++ .code32 ++ ++ ++/* ++ * unsigned char set_videomode(unsigned char mode) ++ * BIOS call "INT 10H Function 0h" to set video mode ++ * Call with %ah = 0x0 ++ * %al = video mode ++ * Returns old videomode. ++ */ ++ENTRY(set_videomode) ++ pushl %ebp ++ movl %esp,%ebp ++ pushl %ebx ++ pushl %ecx ++ ++ movb 8(%ebp), %cl ++ ++ call EXT_C(prot_to_real) ++ .code16 ++ ++ xorb %al, %al ++ movb $0xf, %ah ++ int $0x10 /* Get Current Video mode */ ++ movb %al, %ch ++ xorb %ah, %ah ++ movb %cl, %al ++ int $0x10 /* Set Video mode */ ++ ++ DATA32 call EXT_C(real_to_prot) ++ .code32 ++ ++ xorl %eax, %eax ++ movb %ch, %al ++ ++ popl %ecx ++ popl %ebx ++ popl %ebp ++ ret ++ ++ ++/* ++ * int get_videomode() ++ * BIOS call "INT 10H Function 0Fh" to get current video mode ++ * Call with %al = 0x0 ++ * %ah = 0xF ++ * Returns current videomode. ++ */ ++ENTRY(get_videomode) ++ pushl %ebp ++ movl %esp,%ebp ++ pushl %ebx ++ pushl %ecx ++ ++ call EXT_C(prot_to_real) ++ .code16 ++ ++ xorb %al, %al ++ movb $0xF, %ah ++ int $0x10 /* Get Current Video mode */ ++ movb %al, %cl /* For now we only want display mode */ ++ ++ DATA32 call EXT_C(real_to_prot) ++ .code32 ++ ++ xorl %eax, %eax ++ movb %cl, %al ++ ++ popl %ecx ++ popl %ebx ++ popl %ebp ++ ret ++ ++ ++/* ++ * unsigned char * graphics_get_font() ++ * BIOS call "INT 10H Function 11h" to set font ++ * Call with %ah = 0x11 ++ */ ++ENTRY(graphics_get_font) ++ push %ebp ++ push %ebx ++ push %ecx ++ push %edx ++ ++ call EXT_C(prot_to_real) ++ .code16 ++ ++ movw $0x1130, %ax ++ movb $6, %bh /* font 8x16 */ ++ int $0x10 ++ movw %bp, %dx ++ movw %es, %cx ++ ++ DATA32 call EXT_C(real_to_prot) ++ .code32 ++ ++ xorl %eax, %eax ++ movw %cx, %ax ++ shll $4, %eax ++ movw %dx, %ax ++ ++ pop %edx ++ pop %ecx ++ pop %ebx ++ pop %ebp ++ ret ++ ++ ++/* ++ * graphics_set_palette(index, red, green, blue) ++ * BIOS call "INT 10H Function 10h" to set individual dac register ++ * Call with %ah = 0x10 ++ * %bx = register number ++ * %ch = new value for green (0-63) ++ * %cl = new value for blue (0-63) ++ * %dh = new value for red (0-63) ++ */ ++ ++ENTRY(graphics_set_palette) ++ push %ebp ++ push %eax ++ push %ebx ++ push %ecx ++ push %edx ++ ++ movw $0x3c8, %bx /* address write mode register */ ++ ++ /* wait vertical retrace */ ++ movw $0x3da, %dx ++l1b: ++ inb %dx, %al /* wait vertical active display */ ++ test $8, %al ++ jnz l1b ++ ++l2b: ++ inb %dx, %al /* wait vertical retrace */ ++ test $8, %al ++ jnz l2b ++ ++ mov %bx, %dx ++ movb 0x18(%esp), %al /* index */ ++ outb %al, %dx ++ inc %dx ++ ++ movb 0x1c(%esp), %al /* red */ ++ outb %al, %dx ++ ++ movb 0x20(%esp), %al /* green */ ++ outb %al, %dx ++ ++ movb 0x24(%esp), %al /* blue */ ++ outb %al, %dx ++ ++ movw 0x18(%esp), %bx ++ ++ call EXT_C(prot_to_real) ++ .code16 ++ ++ movb %bl, %bh ++ movw $0x1000, %ax ++ int $0x10 ++ ++ DATA32 call EXT_C(real_to_prot) ++ .code32 ++ ++ pop %edx ++ pop %ecx ++ pop %ebx ++ pop %eax ++ pop %ebp ++ ret ++#endif /* SUPPORT_GRAPHICS */ ++ ++ + /* + * getrtsecs() + * if a seconds value can be read, read it and return it (BCD), +diff -Naur grub-0.97.orig/stage2/boot.c grub-0.97/stage2/boot.c +--- grub-0.97.orig/stage2/boot.c 2004-03-30 03:44:08.000000000 -0800 ++++ grub-0.97/stage2/boot.c 2006-07-04 00:01:50.000000000 -0700 +@@ -1,7 +1,7 @@ + /* boot.c - load and bootstrap a kernel */ + /* + * GRUB -- GRand Unified Bootloader +- * Copyright (C) 1999,2000,2001,2002,2003,2004 Free Software Foundation, Inc. ++ * Copyright (C) 1999,2000,2001,2002,2003,2004,2005 Free Software Foundation, Inc. + * + * 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 +@@ -29,6 +29,8 @@ + entry_func entry_addr; + static struct mod_list mll[99]; + static int linux_mem_size; ++static int elf_kernel_addr; ++static int elf_kernel_size; + + /* + * The next two functions, 'load_image' and 'load_module', are the building +@@ -96,7 +98,7 @@ + lh = (struct linux_kernel_header *) buffer; + + /* ELF loading supported if multiboot, FreeBSD and NetBSD. */ +- if ((type == KERNEL_TYPE_MULTIBOOT ++ if (((type == KERNEL_TYPE_MULTIBOOT && ! (flags & MULTIBOOT_AOUT_KLUDGE)) + || pu.elf->e_ident[EI_OSABI] == ELFOSABI_FREEBSD + || grub_strcmp (pu.elf->e_ident + EI_BRAND, "FreeBSD") == 0 + || suggested_type == KERNEL_TYPE_NETBSD) +@@ -594,6 +596,7 @@ + + /* reset this to zero for now */ + cur_addr = 0; ++ elf_kernel_addr = ~0; + + /* scan for program segments */ + for (i = 0; i < pu.elf->e_phnum; i++) +@@ -630,6 +633,8 @@ + /* mark memory as used */ + if (cur_addr < memaddr + memsiz) + cur_addr = memaddr + memsiz; ++ if (elf_kernel_addr > cur_addr) ++ elf_kernel_addr = cur_addr; + printf (", <0x%x:0x%x:0x%x>", memaddr, filesiz, + memsiz - filesiz); + /* increment number of segments */ +@@ -647,6 +652,8 @@ + } + } + ++ elf_kernel_size = cur_addr - elf_kernel_addr; ++ + if (! errnum) + { + if (! loaded) +@@ -824,8 +831,11 @@ + moveto = (mbi.mem_upper + 0x400) << 10; + + moveto = (moveto - len) & 0xfffff000; +- max_addr = (lh->header == LINUX_MAGIC_SIGNATURE && lh->version >= 0x0203 +- ? lh->initrd_addr_max : LINUX_INITRD_MAX_ADDRESS); ++ max_addr = LINUX_INITRD_MAX_ADDRESS; ++ if (lh->header == LINUX_MAGIC_SIGNATURE && ++ lh->version >= 0x0203 && ++ lh->initrd_addr_max < max_addr) ++ max_addr = lh->initrd_addr_max; + if (moveto + len >= max_addr) + moveto = (max_addr - len) & 0xfffff000; + +@@ -864,6 +874,129 @@ + } + #endif + ++#define mem_align4k(p) ((p) + 0xFFF) & 0xFFFFF000 ++ ++static void ++kfreebsd_setenv (char *env, const char *var, const char *value) ++{ ++ while (1) ++ { ++ if (env[0] == '\0' && env[1] == '\0') ++ { ++ env++; ++ break; ++ } ++ else ++ env++; ++ } ++ ++ grub_sprintf (env, "%s=%s", var, value); ++ env[grub_strlen (env) + 1] = '\0'; ++} ++ ++static char * ++kfreebsd_read_hints (char *buf) ++{ ++ char *buf_end = buf; ++ ++ if (grub_open ("/boot/device.hints")) ++ { ++ char *line_start; ++ int line_len = 0; ++ char *envp; ++ int env_len; ++ ++ env_len = grub_read (buf, -1); ++ if (env_len) ++ { ++ buf_end += env_len; ++ *(buf_end++) = '\0'; ++ } ++ else ++ return buf_end; ++ ++ grub_close (); ++ ++ envp = line_start = buf; ++ while (*envp) ++ { ++ char *envp_current = envp; ++ ++ switch (*envp) ++ { ++ case ' ': ++ while (*envp == ' ') ++ { ++ envp++; ++ env_len--; ++ } ++ grub_memmove (envp_current, envp, env_len + 1); ++ envp = envp_current; ++ break; ++ case '#': ++ while (*envp != '\n') ++ { ++ envp++; ++ env_len--; ++ } ++ if (!line_len) ++ envp++; ++ grub_memmove (envp_current, envp, env_len + 1); ++ envp = envp_current; ++ break; ++ case '\n': ++ if (!line_len) ++ { ++ env_len--; ++ grub_memmove (line_start, envp, env_len + 1); ++ } ++ *(envp++) = '\0'; ++ line_len = 0; ++ line_start = envp; ++ default: ++ envp++; ++ line_len++; ++ break; ++ } ++ } ++ ++ buf_end = buf + env_len; ++ *(buf_end++) = '\0'; ++ } ++ ++ return buf_end; ++} ++ ++static u32_t * ++kfreebsd_set_module_string (u32_t type, u32_t *dst, char *src) ++{ ++ int size; ++ ++ *(dst++) = type; ++ *(dst++) = size = grub_strlen (src) + 1; ++ grub_strcpy ((void *) dst, src); ++ ++ return dst + (size + sizeof(u32_t) - 1) / sizeof(u32_t); ++} ++ ++static u32_t * ++kfreebsd_set_module_var (u32_t type, u32_t *dst, u32_t src) ++{ ++ *(dst++) = type; ++ *(dst++) = sizeof(u32_t); ++ *(dst++) = src; ++ ++ return dst; ++} ++ ++static u32_t * ++kfreebsd_set_modules (u32_t *modulep) ++{ ++ /* XXX: Need to copy the whole module structure. */ ++ /* XXX: How to pass the module name ? */ ++ ++ return modulep; ++} + + /* + * All "*_boot" commands depend on the images being loaded into memory +@@ -877,7 +1010,10 @@ + bsd_boot (kernel_t type, int bootdev, char *arg) + { + char *str; +- int clval = 0, i; ++ char *kernelname; ++ char *bsd_root; ++ int clval = 0; ++ int i; + struct bootinfo bi; + + #ifdef GRUB_UTIL +@@ -886,8 +1022,21 @@ + stop_floppy (); + #endif + ++ while (*arg != '/') ++ arg++; ++ kernelname = arg; ++ + while (*(++arg) && *arg != ' '); ++ *(arg++) = 0; + str = arg; ++ ++ bsd_root = grub_strstr (str, "root="); ++ if (bsd_root) ++ { ++ bsd_root += 5; ++ /* XXX: should copy the str or terminate it. */ ++ } ++ + while (*str) + { + if (*str == '-') +@@ -910,6 +1059,8 @@ + clval |= RB_GDB; + if (*str == 'h') + clval |= RB_SERIAL; ++ if (*str == 'p') ++ clval |= RB_PAUSE; + if (*str == 'm') + clval |= RB_MUTE; + if (*str == 'r') +@@ -927,14 +1078,17 @@ + + if (type == KERNEL_TYPE_FREEBSD) + { ++ char *envp; ++ u32_t *modp; ++ + clval |= RB_BOOTINFO; + + bi.bi_version = BOOTINFO_VERSION; + +- *arg = 0; +- while ((--arg) > (char *) MB_CMDLINE_BUF && *arg != '/'); +- if (*arg == '/') +- bi.bi_kernelname = arg + 1; ++ bi.bi_pad[0] = bi.bi_pad[1] = 0; ++ ++ if (*kernelname == '/') ++ bi.bi_kernelname = kernelname; + else + bi.bi_kernelname = 0; + +@@ -961,6 +1115,30 @@ + bi.bi_basemem = mbi.mem_lower; + bi.bi_extmem = extended_memory; + ++ /* Setup the environment. */ ++ bi.bi_envp = cur_addr = mem_align4k (cur_addr); ++ grub_memset ((void *) cur_addr, 0, 2); ++ cur_addr = (int) kfreebsd_read_hints ((void *) cur_addr); ++ ++ envp = (char *) bi.bi_envp; ++ kfreebsd_setenv (envp, "kernelname", kernelname); ++ kfreebsd_setenv (envp, "vfs.root.mountfrom", bsd_root); ++ ++ /* Setup the modules list. */ ++ bi.bi_modulep = cur_addr = mem_align4k (cur_addr); ++ modp = (u32_t *) bi.bi_modulep; ++ /* The first module is the kernel. */ ++ modp = kfreebsd_set_module_string (MODINFO_NAME, modp, kernelname); ++ modp = kfreebsd_set_module_string (MODINFO_TYPE, modp, "elf kernel"); ++ modp = kfreebsd_set_module_string (MODINFO_ARGS, modp, arg); ++ modp = kfreebsd_set_module_var (MODINFO_ADDR, modp, elf_kernel_addr); ++ modp = kfreebsd_set_module_var (MODINFO_SIZE, modp, elf_kernel_size); ++ /* Now the real modules. */ ++ modp = kfreebsd_set_modules(modp); ++ ++ /* Set the kernel end. */ ++ bi.bi_kernend = cur_addr = mem_align4k (((int) modp) + 1); ++ + if (mbi.flags & MB_INFO_AOUT_SYMS) + { + bi.bi_symtab = mbi.syms.a.addr; +@@ -970,8 +1148,9 @@ + #if 0 + else if (mbi.flags & MB_INFO_ELF_SHDR) + { +- /* FIXME: Should check if a symbol table exists and, if exists, +- pass the table to BI. */ ++ bi.bi_symtab = mbi.syms.e.addr; ++ bi.bi_esymtab = mbi.syms.e.addr ++ + mbi.syms.e.size * mbi.syms.e.num * mbi.syms.e.shndx; + } + #endif + else +diff -Naur grub-0.97.orig/stage2/builtins.c grub-0.97/stage2/builtins.c +--- grub-0.97.orig/stage2/builtins.c 2005-02-15 13:58:23.000000000 -0800 ++++ grub-0.97/stage2/builtins.c 2006-07-04 00:01:50.000000000 -0700 +@@ -28,6 +28,10 @@ + #include + #include + ++#ifdef SUPPORT_GRAPHICS ++# include ++#endif ++ + #ifdef SUPPORT_NETBOOT + # define GRUB 1 + # include +@@ -82,6 +86,10 @@ + inside other functions. */ + static int configfile_func (char *arg, int flags); + ++static int savedefault_helper (char *arg, int flags); ++ ++static int savedefault_shell (char *arg, int flags); ++ + /* Initialize the data for builtins. */ + void + init_builtins (void) +@@ -237,12 +245,22 @@ + static int + boot_func (char *arg, int flags) + { ++ struct term_entry *prev_term = current_term; + /* Clear the int15 handler if we can boot the kernel successfully. + This assumes that the boot code never fails only if KERNEL_TYPE is + not KERNEL_TYPE_NONE. Is this assumption is bad? */ + if (kernel_type != KERNEL_TYPE_NONE) + unset_int15_handler (); + ++ /* if our terminal needed initialization, we should shut it down ++ * before booting the kernel, but we want to save what it was so ++ * we can come back if needed */ ++ if (current_term->shutdown) ++ { ++ current_term->shutdown(); ++ current_term = term_table; /* assumption: console is first */ ++ } ++ + #ifdef SUPPORT_NETBOOT + /* Shut down the networking. */ + cleanup_net (); +@@ -306,6 +324,13 @@ + return 1; + } + ++ /* if we get back here, we should go back to what our term was before */ ++ current_term = prev_term; ++ if (current_term->startup) ++ /* if our terminal fails to initialize, fall back to console since ++ * it should always work */ ++ if (current_term->startup() == 0) ++ current_term = term_table; /* we know that console is first */ + return 0; + } + +@@ -852,6 +877,251 @@ + }; + #endif /* SUPPORT_NETBOOT */ + ++#ifdef SUPPORT_GRAPHICS ++ ++static int splashimage_func(char *arg, int flags) { ++ int i; ++ ++ /* filename can only be 256 characters due to our buffer size */ ++ if (grub_strlen(arg) > 256) { ++ grub_printf("Splash image filename too large\n"); ++ grub_printf("Press any key to continue..."); ++ getkey(); ++ return 1; ++ } ++ ++ /* get rid of TERM_NEED_INIT from the graphics terminal. */ ++ for (i = 0; term_table[i].name; i++) { ++ if (grub_strcmp (term_table[i].name, "graphics") == 0) { ++ term_table[i].flags &= ~TERM_NEED_INIT; ++ break; ++ } ++ } ++ ++ graphics_set_splash(arg); ++ ++ if (flags == BUILTIN_CMDLINE && graphics_inited) { ++ graphics_end(); ++ if (graphics_init() == 0) { ++ /* Fallback to default term */ ++ current_term = term_table; ++ max_lines = current_term->max_lines; ++ if (current_term->cls) ++ current_term->cls(); ++ grub_printf("Failed to set splash image and/or graphics mode\n"); ++ return 1; ++ } ++ graphics_cls(); ++ } ++ ++ if (flags == BUILTIN_MENU) ++ current_term = term_table + i; ++ ++ return 0; ++} ++ ++static struct builtin builtin_splashimage = ++{ ++ "splashimage", ++ splashimage_func, ++ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_HELP_LIST, ++ "splashimage FILE", ++ "Load FILE as the background image when in graphics mode." ++}; ++ ++ ++/* shade */ ++static int ++shade_func(char *arg, int flags) ++{ ++ int new_shade; ++ ++ if (!arg || safe_parse_maxint(&arg, &new_shade) == 0) ++ return (1); ++ ++ if (shade != new_shade) { ++ shade = new_shade; ++ if (flags == BUILTIN_CMDLINE && graphics_inited) { ++ graphics_end(); ++ graphics_init(); ++ graphics_cls(); ++ } ++ } ++ ++ return 0; ++} ++ ++static struct builtin builtin_shade = ++{ ++ "shade", ++ shade_func, ++ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_HELP_LIST, ++ "shade INTEGER", ++ "If set to 0, disables the use of shaded text, else enables it." ++}; ++ ++ ++/* foreground */ ++static int ++foreground_func(char *arg, int flags) ++{ ++ if (grub_strlen(arg) == 6) { ++ int r = ((hex(arg[0]) << 4) | hex(arg[1])) >> 2; ++ int g = ((hex(arg[2]) << 4) | hex(arg[3])) >> 2; ++ int b = ((hex(arg[4]) << 4) | hex(arg[5])) >> 2; ++ ++ foreground = (r << 16) | (g << 8) | b; ++ if (graphics_inited) ++ graphics_set_palette(15, r, g, b); ++ ++ return 0; ++ } ++ ++ return 1; ++} ++ ++static struct builtin builtin_foreground = ++{ ++ "foreground", ++ foreground_func, ++ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_HELP_LIST, ++ "foreground RRGGBB", ++ "Sets the foreground color when in graphics mode." ++ "RR is red, GG is green, and BB blue. Numbers must be in hexadecimal." ++}; ++ ++ ++/* background */ ++static int ++background_func(char *arg, int flags) ++{ ++ if (grub_strlen(arg) == 6) { ++ int r = ((hex(arg[0]) << 4) | hex(arg[1])) >> 2; ++ int g = ((hex(arg[2]) << 4) | hex(arg[3])) >> 2; ++ int b = ((hex(arg[4]) << 4) | hex(arg[5])) >> 2; ++ ++ background = (r << 16) | (g << 8) | b; ++ if (graphics_inited) ++ graphics_set_palette(0, r, g, b); ++ return 0; ++ } ++ ++ return 1; ++} ++ ++static struct builtin builtin_background = ++{ ++ "background", ++ background_func, ++ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_HELP_LIST, ++ "background RRGGBB", ++ "Sets the background color when in graphics mode." ++ "RR is red, GG is green, and BB blue. Numbers must be in hexadecimal." ++}; ++ ++ ++/* border */ ++static int ++border_func(char *arg, int flags) ++{ ++ if (grub_strlen(arg) == 6) { ++ int r = ((hex(arg[0]) << 4) | hex(arg[1])) >> 2; ++ int g = ((hex(arg[2]) << 4) | hex(arg[3])) >> 2; ++ int b = ((hex(arg[4]) << 4) | hex(arg[5])) >> 2; ++ ++ window_border = (r << 16) | (g << 8) | b; ++ if (graphics_inited) ++ graphics_set_palette(0x11, r, g, b); ++ ++ return 0; ++ } ++ ++ return 1; ++} ++ ++static struct builtin builtin_border = ++{ ++ "border", ++ border_func, ++ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_HELP_LIST, ++ "border RRGGBB", ++ "Sets the border video color when in graphics mode." ++ "RR is red, GG is green, and BB blue. Numbers must be in hexadecimal." ++}; ++ ++ ++/* viewport */ ++static int ++viewport_func (char *arg, int flags) ++{ ++ int i; ++ int x0 = 0, y0 = 0, x1 = 80, y1 = 30; ++ int *pos[4] = { &x0, &y0, &x1, &y1 }; ++ ++ if (!arg) ++ return (1); ++ for (i = 0; i < 4; i++) { ++ if (!*arg) ++ return (1); ++ while (*arg && (*arg == ' ' || *arg == '\t')) ++ ++arg; ++ if (!safe_parse_maxint(&arg, pos[i])) ++ return (1); ++ while (*arg && (*arg != ' ' && *arg != '\t')) ++ ++arg; ++ } ++ ++ /* minimum size is 65 colums and 16 rows */ ++ if (x0 > x1 - 66 || y0 > y1 - 16 || x0 < 0 || y0 < 0 || x1 > 80 || y1 > 30) ++ return 1; ++ ++ view_x0 = x0; ++ view_y0 = y0; ++ view_x1 = x1; ++ view_y1 = y1; ++ ++ if (flags == BUILTIN_CMDLINE && graphics_inited) { ++ graphics_end(); ++ graphics_init(); ++ graphics_cls(); ++ } ++ ++ return 0; ++} ++ ++static struct builtin builtin_viewport = ++{ ++ "viewport", ++ viewport_func, ++ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_HELP_LIST, ++ "viewport x0 y0 x1 y1", ++ "Changes grub internals to output text in the window defined by" ++ " four parameters. The x and y parameters are 0 based. This option" ++ " only works with the graphics interface." ++}; ++ ++#endif /* SUPPORT_GRAPHICS */ ++ ++ ++/* clear */ ++static int ++clear_func() ++{ ++ if (current_term->cls) ++ current_term->cls(); ++ ++ return 0; ++} ++ ++static struct builtin builtin_clear = ++{ ++ "clear", ++ clear_func, ++ BUILTIN_CMDLINE | BUILTIN_HELP_LIST, ++ "clear", ++ "Clear the screen" ++}; ++ + + /* displayapm */ + static int +@@ -1454,14 +1724,20 @@ + + + /* help */ +-#define MAX_SHORT_DOC_LEN 39 +-#define MAX_LONG_DOC_LEN 66 +- + static int + help_func (char *arg, int flags) + { +- int all = 0; +- ++ int all = 0, max_short_doc_len, max_long_doc_len; ++ max_short_doc_len = 39; ++ max_long_doc_len = 66; ++#ifdef SUPPORT_GRAPHICS ++ if (grub_memcmp (current_term->name, "graphics", sizeof ("graphics") - 1) == 0) ++ { ++ max_short_doc_len = (view_x1 - view_x0 + 1) / 2 - 1; ++ max_long_doc_len = (view_x1 - view_x0) - 14; ++ } ++#endif ++ + if (grub_memcmp (arg, "--all", sizeof ("--all") - 1) == 0) + { + all = 1; +@@ -1491,13 +1767,13 @@ + + len = grub_strlen ((*builtin)->short_doc); + /* If the length of SHORT_DOC is too long, truncate it. */ +- if (len > MAX_SHORT_DOC_LEN - 1) +- len = MAX_SHORT_DOC_LEN - 1; ++ if (len > max_short_doc_len - 1) ++ len = max_short_doc_len - 1; + + for (i = 0; i < len; i++) + grub_putchar ((*builtin)->short_doc[i]); + +- for (; i < MAX_SHORT_DOC_LEN; i++) ++ for (; i < max_short_doc_len; i++) + grub_putchar (' '); + + if (! left) +@@ -1546,10 +1822,10 @@ + int i; + + /* If LEN is too long, fold DOC. */ +- if (len > MAX_LONG_DOC_LEN) ++ if (len > max_long_doc_len) + { + /* Fold this line at the position of a space. */ +- for (len = MAX_LONG_DOC_LEN; len > 0; len--) ++ for (len = max_long_doc_len; len > 0; len--) + if (doc[len - 1] == ' ') + break; + } +@@ -2323,6 +2599,25 @@ + "Probe I/O ports used for the drive DRIVE." + }; + ++/* print */ ++static int ++print_func (char *arg, int flags) ++{ ++ printf("%s\n", arg); ++ ++ return 0; ++} ++ ++static struct builtin builtin_print = ++{ ++ "print", ++ print_func, ++ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_NO_ECHO, ++ "print [MESSAGE ...]", ++ "Print MESSAGE." ++}; ++ ++ + + /* kernel */ + static int +@@ -3221,7 +3516,102 @@ + static int + savedefault_func (char *arg, int flags) + { +-#if !defined(SUPPORT_DISKLESS) && !defined(GRUB_UTIL) ++#if !defined(SUPPORT_DISKLESS) ++ #if !defined(GRUB_UTIL) ++ savedefault_helper(arg, flags); ++ #else ++ savedefault_shell(arg, flags); ++ #endif ++#else /* !SUPPORT_DISKLESS */ ++ errnum = ERR_UNRECOGNIZED; ++ return 1; ++#endif /* !SUPPORT_DISKLESS */ ++} ++ ++#if !defined(SUPPORT_DISKLESS) && defined(GRUB_UTIL) ++/* savedefault_shell */ ++static int ++savedefault_shell(char *arg, int flags) ++ { ++ int once_only = 0; ++ int new_default; ++ int curr_default = -1; ++ int curr_prev_default = -1; ++ int new_prev_default = -1; ++ FILE *fp; ++ size_t bytes = 10; ++ char line[bytes]; ++ char *default_file = (char *) DEFAULT_FILE_BUF; ++ char buf[bytes]; ++ int i; ++ ++ while (1) ++ { ++ if (grub_memcmp ("--default=", arg, sizeof ("--default=") - 1) == 0) ++ { ++ char *p = arg + sizeof ("--default=") - 1; ++ if (! safe_parse_maxint (&p, &new_default)) ++ return 1; ++ arg = skip_to (0, arg); ++ } ++ else if (grub_memcmp ("--once", arg, sizeof ("--once") - 1) == 0) ++ { ++ once_only = 1; ++ arg = skip_to (0, arg); ++ } ++ else ++ break; ++ } ++ ++ *default_file = 0; ++ grub_strncat (default_file, config_file, DEFAULT_FILE_BUFLEN); ++ for (i = grub_strlen(default_file); i >= 0; i--) ++ if (default_file[i] == '/') ++ { ++ i++; ++ break; ++ } ++ default_file[i] = 0; ++ grub_strncat (default_file + i, "default", DEFAULT_FILE_BUFLEN - i); ++ ++ if(!(fp = fopen(default_file,"w"))) ++ { ++ errnum = ERR_READ; ++ goto fail; ++ } ++ ++ read(&line, -1); ++ ++ sscanf(line, "%d:%d", &curr_prev_default, &curr_default); ++ ++ if(curr_default != -1) ++ new_prev_default = curr_default; ++ else ++ { ++ if(curr_prev_default != -1) ++ new_prev_default = curr_prev_default; ++ else ++ new_prev_default = 0; ++ } ++ ++ if(once_only) ++ sprintf(buf, "%d:%d\n", new_prev_default, new_default); ++ else ++ sprintf(buf, "%d\n", new_default); ++ ++ fprintf(fp, buf); ++ ++fail: ++ fclose(fp); ++ return errnum; ++} ++#endif ++ ++/* savedefault_helper */ ++static int ++savedefault_helper (char *arg, int flags) ++{ ++#if !defined(SUPPORT_DISKLESS) + unsigned long tmp_drive = saved_drive; + unsigned long tmp_partition = saved_partition; + char *default_file = (char *) DEFAULT_FILE_BUF; +@@ -3300,19 +3690,23 @@ + disk_read_hook = 0; + grub_close (); + +- if (len != sizeof (buf)) +- { +- /* This is too small. Do not modify the file manually, please! */ +- errnum = ERR_READ; +- goto fail; +- } +- + if (sector_count > 2) + { + /* Is this possible?! Too fragmented! */ + errnum = ERR_FSYS_CORRUPT; + goto fail; + } ++ ++ char *tmp; ++ if((tmp = grub_strstr(buf, ":")) != NULL) ++ { ++ int f_len = grub_strlen(buf) - grub_strlen(tmp); ++ char *def; ++ int a; ++ for(a = 0; a < f_len; a++) ++ grub_memcpy(&def[a], &buf[a], sizeof(char)); ++ safe_parse_maxint (&def, &entryno); ++ } + + /* Set up a string to be written. */ + grub_memset (buf, '\n', sizeof (buf)); +@@ -3830,15 +4224,15 @@ + { + char tmp[16]; + grub_sprintf (tmp, ",%d", (partition >> 16) & 0xFF); +- grub_strncat (device, tmp, 256); ++ grub_strncat (device, tmp, sizeof (device)); + } + if ((partition & 0x00FF00) != 0x00FF00) + { + char tmp[16]; + grub_sprintf (tmp, ",%c", 'a' + ((partition >> 8) & 0xFF)); +- grub_strncat (device, tmp, 256); ++ grub_strncat (device, tmp, sizeof (device)); + } +- grub_strncat (device, ")", 256); ++ grub_strncat (device, ")", sizeof (device)); + } + + int embed_stage1_5 (char *stage1_5, int drive, int partition) +@@ -4085,7 +4479,7 @@ + }; + + +-#if defined(SUPPORT_SERIAL) || defined(SUPPORT_HERCULES) ++#if defined(SUPPORT_SERIAL) || defined(SUPPORT_HERCULES) || defined(SUPPORT_GRAPHICS) + /* terminal */ + static int + terminal_func (char *arg, int flags) +@@ -4244,17 +4638,29 @@ + end: + current_term = term_table + default_term; + current_term->flags = term_flags; +- ++ + if (lines) + max_lines = lines; + else +- /* 24 would be a good default value. */ +- max_lines = 24; +- ++ max_lines = current_term->max_lines; ++ + /* If the interface is currently the command-line, + restart it to repaint the screen. */ +- if (current_term != prev_term && (flags & BUILTIN_CMDLINE)) ++ if ((current_term != prev_term) && (flags & BUILTIN_CMDLINE)){ ++ if (prev_term->shutdown) ++ prev_term->shutdown(); ++ if (current_term->startup) { ++ /* If startup fails, return to previous term */ ++ if (current_term->startup() == 0) { ++ current_term = prev_term; ++ max_lines = current_term->max_lines; ++ if (current_term->cls) { ++ current_term->cls(); ++ } ++ } ++ } + grub_longjmp (restart_cmdline_env, 0); ++ } + + return 0; + } +@@ -4264,7 +4670,7 @@ + "terminal", + terminal_func, + BUILTIN_MENU | BUILTIN_CMDLINE | BUILTIN_HELP_LIST, +- "terminal [--dumb] [--no-echo] [--no-edit] [--timeout=SECS] [--lines=LINES] [--silent] [console] [serial] [hercules]", ++ "terminal [--dumb] [--no-echo] [--no-edit] [--timeout=SECS] [--lines=LINES] [--silent] [console] [serial] [hercules] [graphics]", + "Select a terminal. When multiple terminals are specified, wait until" + " you push any key to continue. If both console and serial are specified," + " the terminal to which you input a key first will be selected. If no" +@@ -4276,7 +4682,7 @@ + " seconds. The option --lines specifies the maximum number of lines." + " The option --silent is used to suppress messages." + }; +-#endif /* SUPPORT_SERIAL || SUPPORT_HERCULES */ ++#endif /* SUPPORT_SERIAL || SUPPORT_HERCULES || SUPPORT_GRAPHICS */ + + + #ifdef SUPPORT_SERIAL +@@ -4795,13 +5201,20 @@ + /* The table of builtin commands. Sorted in dictionary order. */ + struct builtin *builtin_table[] = + { ++#ifdef SUPPORT_GRAPHICS ++ &builtin_background, ++#endif + &builtin_blocklist, + &builtin_boot, + #ifdef SUPPORT_NETBOOT + &builtin_bootp, + #endif /* SUPPORT_NETBOOT */ ++#ifdef SUPPORT_GRAPHICS ++ &builtin_border, ++#endif + &builtin_cat, + &builtin_chainloader, ++ &builtin_clear, + &builtin_cmp, + &builtin_color, + &builtin_configfile, +@@ -4821,6 +5234,9 @@ + &builtin_embed, + &builtin_fallback, + &builtin_find, ++#ifdef SUPPORT_GRAPHICS ++ &builtin_foreground, ++#endif + &builtin_fstest, + &builtin_geometry, + &builtin_halt, +@@ -4848,6 +5264,7 @@ + &builtin_parttype, + &builtin_password, + &builtin_pause, ++ &builtin_print, + #ifdef GRUB_UTIL + &builtin_quit, + #endif /* GRUB_UTIL */ +@@ -4864,9 +5281,13 @@ + #endif /* SUPPORT_SERIAL */ + &builtin_setkey, + &builtin_setup, +-#if defined(SUPPORT_SERIAL) || defined(SUPPORT_HERCULES) ++#ifdef SUPPORT_GRAPHICS ++ &builtin_shade, ++ &builtin_splashimage, ++#endif /* SUPPORT_GRAPHICS */ ++#if defined(SUPPORT_SERIAL) || defined(SUPPORT_HERCULES) || defined(SUPPORT_GRAPHICS) + &builtin_terminal, +-#endif /* SUPPORT_SERIAL || SUPPORT_HERCULES */ ++#endif /* SUPPORT_SERIAL || SUPPORT_HERCULES || SUPPORT_GRAPHICS */ + #ifdef SUPPORT_SERIAL + &builtin_terminfo, + #endif /* SUPPORT_SERIAL */ +@@ -4880,5 +5301,8 @@ + &builtin_unhide, + &builtin_uppermem, + &builtin_vbeprobe, ++#ifdef SUPPORT_GRAPHICS ++ &builtin_viewport, ++#endif + 0 + }; +diff -Naur grub-0.97.orig/stage2/char_io.c grub-0.97/stage2/char_io.c +--- grub-0.97.orig/stage2/char_io.c 2005-02-01 12:51:23.000000000 -0800 ++++ grub-0.97/stage2/char_io.c 2006-07-03 23:59:27.000000000 -0700 +@@ -29,12 +29,17 @@ + # include + #endif + ++#ifdef SUPPORT_GRAPHICS ++# include ++#endif ++ + #ifndef STAGE1_5 + struct term_entry term_table[] = + { + { + "console", + 0, ++ 24, + console_putchar, + console_checkkey, + console_getkey, +@@ -43,13 +48,16 @@ + console_cls, + console_setcolorstate, + console_setcolor, +- console_setcursor ++ console_setcursor, ++ 0, ++ 0 + }, + #ifdef SUPPORT_SERIAL + { + "serial", + /* A serial device must be initialized. */ + TERM_NEED_INIT, ++ 24, + serial_putchar, + serial_checkkey, + serial_getkey, +@@ -58,6 +66,8 @@ + serial_cls, + serial_setcolorstate, + 0, ++ 0, ++ 0, + 0 + }, + #endif /* SUPPORT_SERIAL */ +@@ -65,6 +75,7 @@ + { + "hercules", + 0, ++ 24, + hercules_putchar, + console_checkkey, + console_getkey, +@@ -73,11 +84,30 @@ + hercules_cls, + hercules_setcolorstate, + hercules_setcolor, +- hercules_setcursor ++ hercules_setcursor, ++ 0, ++ 0 + }, + #endif /* SUPPORT_HERCULES */ ++#ifdef SUPPORT_GRAPHICS ++ { "graphics", ++ TERM_NEED_INIT, /* flags */ ++ 30, /* number of lines */ ++ graphics_putchar, /* putchar */ ++ console_checkkey, /* checkkey */ ++ console_getkey, /* getkey */ ++ graphics_getxy, /* getxy */ ++ graphics_gotoxy, /* gotoxy */ ++ graphics_cls, /* cls */ ++ graphics_setcolorstate, /* setcolorstate */ ++ graphics_setcolor, /* setcolor */ ++ graphics_setcursor, /* nocursor */ ++ graphics_init, /* initialize */ ++ graphics_end /* shutdown */ ++ }, ++#endif /* SUPPORT_GRAPHICS */ + /* This must be the last entry. */ +- { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } ++ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } + }; + + /* This must be console. */ +@@ -305,9 +335,10 @@ + + /* XXX: These should be defined in shared.h, but I leave these here, + until this code is freezed. */ +-#define CMDLINE_WIDTH 78 + #define CMDLINE_MARGIN 10 +- ++ ++ /* command-line limits */ ++ int cmdline_width = 78, col_start = 0; + int xpos, lpos, c, section; + /* The length of PROMPT. */ + int plen; +@@ -338,7 +369,7 @@ + + /* If the cursor is in the first section, display the first section + instead of the second. */ +- if (section == 1 && plen + lpos < CMDLINE_WIDTH) ++ if (section == 1 && plen + lpos < cmdline_width) + cl_refresh (1, 0); + else if (xpos - count < 1) + cl_refresh (1, 0); +@@ -354,7 +385,7 @@ + grub_putchar ('\b'); + } + else +- gotoxy (xpos, getxy () & 0xFF); ++ gotoxy (xpos + col_start, getxy () & 0xFF); + } + } + +@@ -364,7 +395,7 @@ + lpos += count; + + /* If the cursor goes outside, scroll the screen to the right. */ +- if (xpos + count >= CMDLINE_WIDTH) ++ if (xpos + count >= cmdline_width) + cl_refresh (1, 0); + else + { +@@ -383,7 +414,7 @@ + } + } + else +- gotoxy (xpos, getxy () & 0xFF); ++ gotoxy (xpos + col_start, getxy () & 0xFF); + } + } + +@@ -398,14 +429,14 @@ + if (full) + { + /* Recompute the section number. */ +- if (lpos + plen < CMDLINE_WIDTH) ++ if (lpos + plen < cmdline_width) + section = 0; + else +- section = ((lpos + plen - CMDLINE_WIDTH) +- / (CMDLINE_WIDTH - 1 - CMDLINE_MARGIN) + 1); ++ section = ((lpos + plen - cmdline_width) ++ / (cmdline_width - 1 - CMDLINE_MARGIN) + 1); + + /* From the start to the end. */ +- len = CMDLINE_WIDTH; ++ len = cmdline_width; + pos = 0; + grub_putchar ('\r'); + +@@ -445,8 +476,8 @@ + if (! full) + offset = xpos - 1; + +- start = ((section - 1) * (CMDLINE_WIDTH - 1 - CMDLINE_MARGIN) +- + CMDLINE_WIDTH - plen - CMDLINE_MARGIN); ++ start = ((section - 1) * (cmdline_width - 1 - CMDLINE_MARGIN) ++ + cmdline_width - plen - CMDLINE_MARGIN); + xpos = lpos + 1 - start; + start += offset; + } +@@ -471,7 +502,7 @@ + + /* If the cursor is at the last position, put `>' or a space, + depending on if there are more characters in BUF. */ +- if (pos == CMDLINE_WIDTH) ++ if (pos == cmdline_width) + { + if (start + len < llen) + grub_putchar ('>'); +@@ -488,7 +519,7 @@ + grub_putchar ('\b'); + } + else +- gotoxy (xpos, getxy () & 0xFF); ++ gotoxy (xpos + col_start, getxy () & 0xFF); + } + + /* Initialize the command-line. */ +@@ -518,10 +549,10 @@ + + llen += l; + lpos += l; +- if (xpos + l >= CMDLINE_WIDTH) ++ if (xpos + l >= cmdline_width) + cl_refresh (1, 0); +- else if (xpos + l + llen - lpos > CMDLINE_WIDTH) +- cl_refresh (0, CMDLINE_WIDTH - xpos); ++ else if (xpos + l + llen - lpos > cmdline_width) ++ cl_refresh (0, cmdline_width - xpos); + else + cl_refresh (0, l + llen - lpos); + } +@@ -533,12 +564,22 @@ + grub_memmove (buf + lpos, buf + lpos + count, llen - count + 1); + llen -= count; + +- if (xpos + llen + count - lpos > CMDLINE_WIDTH) +- cl_refresh (0, CMDLINE_WIDTH - xpos); ++ if (xpos + llen + count - lpos > cmdline_width) ++ cl_refresh (0, cmdline_width - xpos); + else + cl_refresh (0, llen + count - lpos); + } + ++ max_lines = current_term->max_lines; ++#ifdef SUPPORT_GRAPHICS ++ if (grub_memcmp (current_term->name, "graphics", sizeof ("graphics") - 1) == 0) ++ { ++ cmdline_width = (view_x1 - view_x0) - 2; ++ col_start = view_x0; ++ max_lines = view_y1 - view_y0; ++ } ++#endif ++ + plen = grub_strlen (prompt); + llen = grub_strlen (cmdline); + +@@ -1006,6 +1047,48 @@ + } + #endif /* ! STAGE1_5 */ + ++#ifndef STAGE1_5 ++/* Internal pager. */ ++int ++do_more (void) ++{ ++ if (count_lines >= 0) ++ { ++ count_lines++; ++ if (count_lines >= max_lines - 2) ++ { ++ int tmp; ++ ++ /* It's important to disable the feature temporarily, because ++ the following grub_printf call will print newlines. */ ++ count_lines = -1; ++ ++ grub_printf("\n"); ++ if (current_term->setcolorstate) ++ current_term->setcolorstate (COLOR_STATE_HIGHLIGHT); ++ ++ grub_printf ("[Hit return to continue]"); ++ ++ if (current_term->setcolorstate) ++ current_term->setcolorstate (COLOR_STATE_NORMAL); ++ ++ ++ do ++ { ++ tmp = ASCII_CHAR (getkey ()); ++ } ++ while (tmp != '\n' && tmp != '\r'); ++ grub_printf ("\r \r"); ++ ++ /* Restart to count lines. */ ++ count_lines = 0; ++ return 1; ++ } ++ } ++ return 0; ++} ++#endif ++ + /* Display an ASCII character. */ + void + grub_putchar (int c) +@@ -1034,38 +1117,11 @@ + + if (c == '\n') + { ++ int flag; + /* Internal `more'-like feature. */ +- if (count_lines >= 0) +- { +- count_lines++; +- if (count_lines >= max_lines - 2) +- { +- int tmp; +- +- /* It's important to disable the feature temporarily, because +- the following grub_printf call will print newlines. */ +- count_lines = -1; +- +- if (current_term->setcolorstate) +- current_term->setcolorstate (COLOR_STATE_HIGHLIGHT); +- +- grub_printf ("\n[Hit return to continue]"); +- +- if (current_term->setcolorstate) +- current_term->setcolorstate (COLOR_STATE_NORMAL); +- +- do +- { +- tmp = ASCII_CHAR (getkey ()); +- } +- while (tmp != '\n' && tmp != '\r'); +- grub_printf ("\r \r"); +- +- /* Restart to count lines. */ +- count_lines = 0; +- return; +- } +- } ++ flag = do_more (); ++ if (flag) ++ return; + } + + current_term->putchar (c); +@@ -1090,7 +1146,7 @@ + cls (void) + { + /* If the terminal is dumb, there is no way to clean the terminal. */ +- if (current_term->flags & TERM_DUMB) ++ if (current_term->flags & TERM_DUMB) + grub_putchar ('\n'); + else + current_term->cls (); +@@ -1175,13 +1231,13 @@ + #endif /* ! STAGE1_5 */ + + int +-memcheck (int addr, int len) ++memcheck (unsigned long int addr, unsigned long int len) + { + #ifdef GRUB_UTIL +- auto int start_addr (void); +- auto int end_addr (void); ++ auto unsigned long int start_addr (void); ++ auto int unsigned long end_addr (void); + +- auto int start_addr (void) ++ auto unsigned long int start_addr (void) + { + int ret; + # if defined(HAVE_START_SYMBOL) +@@ -1192,7 +1248,7 @@ + return ret; + } + +- auto int end_addr (void) ++ auto unsigned long int end_addr (void) + { + int ret; + # if defined(HAVE_END_SYMBOL) +@@ -1217,6 +1273,16 @@ + return ! errnum; + } + ++void ++grub_memcpy(void *dest, const void *src, int len) ++{ ++ int i; ++ register char *d = (char*)dest, *s = (char*)src; ++ ++ for (i = 0; i < len; i++) ++ d[i] = s[i]; ++} ++ + void * + grub_memmove (void *to, const void *from, int len) + { +diff -Naur grub-0.97.orig/stage2/cmdline.c grub-0.97/stage2/cmdline.c +--- grub-0.97.orig/stage2/cmdline.c 2004-08-16 16:23:01.000000000 -0700 ++++ grub-0.97/stage2/cmdline.c 2006-07-03 23:58:41.000000000 -0700 +@@ -50,10 +50,11 @@ + void + print_cmdline_message (int forever) + { +- printf (" [ Minimal BASH-like line editing is supported. For the first word, TAB\n" +- " lists possible command completions. Anywhere else TAB lists the possible\n" +- " completions of a device/filename.%s ]\n", +- (forever ? "" : " ESC at any time exits.")); ++ grub_printf(" [ Minimal BASH-like line editing is supported. For\n" ++ " the first word, TAB lists possible command\n" ++ " completions. Anywhere else TAB lists the possible\n" ++ " completions of a device/filename.%s ]\n", ++ (forever ? "" : " ESC at any time\n exits.")); + } + + /* Find the builtin whose command name is COMMAND and return the +diff -Naur grub-0.97.orig/stage2/freebsd.h grub-0.97/stage2/freebsd.h +--- grub-0.97.orig/stage2/freebsd.h 2003-07-09 04:45:52.000000000 -0700 ++++ grub-0.97/stage2/freebsd.h 2006-07-03 23:59:36.000000000 -0700 +@@ -1,7 +1,7 @@ + + /* + * GRUB -- GRand Unified Bootloader +- * Copyright (C) 2001 Free Software Foundation, Inc. ++ * Copyright (C) 2001, 2004 Free Software Foundation, Inc. + * + * 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 +@@ -35,6 +35,10 @@ + #define RB_CDROM 0x2000 /* use cdrom as root */ + #define RB_GDB 0x8000 /* use GDB remote debugger instead of DDB */ + #define RB_MUTE 0x10000 /* Come up with the console muted */ ++#define RB_SELFTEST 0x20000 /* don't complete the boot; do selftest */ ++#define RB_RESERVED1 0x40000 /* reserved for internal use of boot blocks */ ++#define RB_RESERVED2 0x80000 /* reserved for internal use of boot blocks */ ++#define RB_PAUSE 0x100000 /* pause after each output line during probe */ + #define RB_MULTIPLE 0x20000000 /* Use multiple consoles */ + + #define RB_BOOTINFO 0x80000000 /* have `struct bootinfo *' arg */ +@@ -70,6 +74,9 @@ + + #define N_BIOS_GEOM 8 + ++typedef unsigned char u8_t; ++typedef unsigned int u32_t; ++ + /* + * A zero bootinfo field often means that there is no info available. + * Flags are used to indicate the validity of fields where zero is a +@@ -77,19 +84,33 @@ + */ + struct bootinfo + { +- unsigned int bi_version; +- unsigned char *bi_kernelname; +- struct nfs_diskless *bi_nfs_diskless; ++ u32_t bi_version; ++ u8_t *bi_kernelname; ++ u32_t bi_nfs_diskless; + /* End of fields that are always present. */ + #define bi_endcommon bi_n_bios_used +- unsigned int bi_n_bios_used; +- unsigned long bi_bios_geom[N_BIOS_GEOM]; +- unsigned int bi_size; +- unsigned char bi_memsizes_valid; +- unsigned char bi_bios_dev; +- unsigned char bi_pad[2]; +- unsigned long bi_basemem; +- unsigned long bi_extmem; +- unsigned long bi_symtab; +- unsigned long bi_esymtab; ++ u32_t bi_n_bios_used; ++ u32_t bi_bios_geom[N_BIOS_GEOM]; ++ u32_t bi_size; ++ u8_t bi_memsizes_valid; ++ u8_t bi_bios_dev; ++ u8_t bi_pad[2]; ++ u32_t bi_basemem; ++ u32_t bi_extmem; ++ u32_t bi_symtab; ++ u32_t bi_esymtab; ++ /* Items below only from advanced bootloader */ ++ u32_t bi_kernend; ++ u32_t bi_envp; ++ u32_t bi_modulep; + }; ++ ++#define MODINFO_END 0x0000 /* End of list */ ++#define MODINFO_NAME 0x0001 /* Name of module (string) */ ++#define MODINFO_TYPE 0x0002 /* Type of module (string) */ ++#define MODINFO_ADDR 0x0003 /* Loaded address */ ++#define MODINFO_SIZE 0x0004 /* Size of module */ ++#define MODINFO_EMPTY 0x0005 /* Has been deleted */ ++#define MODINFO_ARGS 0x0006 /* Parameters string */ ++#define MODINFO_METADATA 0x8000 /* Module-specfic */ ++ +diff -Naur grub-0.97.orig/stage2/graphics.c grub-0.97/stage2/graphics.c +--- grub-0.97.orig/stage2/graphics.c 1969-12-31 16:00:00.000000000 -0800 ++++ grub-0.97/stage2/graphics.c 2006-07-03 23:58:41.000000000 -0700 +@@ -0,0 +1,585 @@ ++/* ++ * graphics.c - graphics mode support for GRUB ++ * Implemented as a terminal type by Jeremy Katz based ++ * on a patch by Paulo César Pereira de Andrade ++ * Options and enhancements made by Herton Ronaldo Krzesinski ++ * ++ * ++ * GRUB -- GRand Unified Bootloader ++ * Copyright (C) 2001,2002 Red Hat, Inc. ++ * Portions copyright (C) 2000 Conectiva, Inc. ++ * ++ * 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 ++ * (at your option) 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. ++ */ ++ ++#ifdef SUPPORT_GRAPHICS ++ ++#include ++#include ++#include ++ ++int saved_videomode; ++unsigned char *font8x16; ++ ++int graphics_inited = 0; ++static char splashimage[256]; ++ ++int shade = 1, no_cursor = 0; ++ ++#define VSHADOW VSHADOW1 ++unsigned char VSHADOW1[38400]; ++unsigned char VSHADOW2[38400]; ++unsigned char VSHADOW4[38400]; ++unsigned char VSHADOW8[38400]; ++ ++/* define the default viewable area */ ++int view_x0 = 0; ++int view_y0 = 0; ++int view_x1 = 80; ++int view_y1 = 30; ++ ++/* text buffer has to be kept around so that we can write things as we ++ * scroll and the like */ ++unsigned short text[80 * 30]; ++ ++/* graphics options */ ++int foreground = (63 << 16) | (63 << 8) | (63), background = 0, window_border = 0; ++ ++/* current position */ ++static int fontx = 0; ++static int fonty = 0; ++ ++/* global state so that we don't try to recursively scroll or cursor */ ++static int no_scroll = 0; ++ ++/* color state */ ++static int graphics_standard_color = A_NORMAL; ++static int graphics_normal_color = A_NORMAL; ++static int graphics_highlight_color = A_REVERSE; ++static int graphics_current_color = A_NORMAL; ++static color_state graphics_color_state = COLOR_STATE_STANDARD; ++ ++static inline void outb(unsigned short port, unsigned char val) ++{ ++ __asm __volatile ("outb %0,%1"::"a" (val), "d" (port)); ++} ++ ++static void MapMask(int value) { ++ outb(0x3c4, 2); ++ outb(0x3c5, value); ++} ++ ++/* bit mask register */ ++static void BitMask(int value) { ++ outb(0x3ce, 8); ++ outb(0x3cf, value); ++} ++ ++/* move the graphics cursor location to col, row */ ++static void graphics_setxy(int col, int row) { ++ if (col >= view_x0 && col < view_x1) { ++ fontx = col; ++ cursorX = col << 3; ++ } ++ if (row >= view_y0 && row < view_y1) { ++ fonty = row; ++ cursorY = row << 4; ++ } ++} ++ ++/* scroll the screen */ ++static void graphics_scroll() { ++ int i, j, k; ++ ++ /* we don't want to scroll recursively... that would be bad */ ++ if (no_scroll) ++ return; ++ no_scroll = 1; ++ ++ /* disable pager temporarily */ ++ k = count_lines; ++ count_lines = -1; ++ ++ /* move everything up a line */ ++ for (j = view_y0 + 1; j < view_y1; j++) { ++ graphics_gotoxy(view_x0, j - 1); ++ for (i = view_x0; i < view_x1; i++) { ++ graphics_putchar(text[j * 80 + i]); ++ } ++ } ++ ++ /* last line should be blank */ ++ graphics_gotoxy(view_x0, view_y1 - 1); ++ for (i = view_x0; i < view_x1; i++) ++ graphics_putchar(' '); ++ graphics_setxy(view_x0, view_y1 - 1); ++ ++ count_lines = k; ++ ++ no_scroll = 0; ++} ++ ++/* Set the splash image */ ++void graphics_set_splash(char *splashfile) { ++ grub_strcpy(splashimage, splashfile); ++} ++ ++/* Get the current splash image */ ++char *graphics_get_splash(void) { ++ return splashimage; ++} ++ ++/* ++ * Initialize a vga16 graphics display with the palette based off of ++ * the image in splashimage. If the image doesn't exist, leave graphics ++ * mode. The mode initiated is 12h. From "Ralf Brown's Interrupt List": ++ * text/ text pixel pixel colors disply scrn system ++ * grph resol box resolution pages addr ++ * 12h G 80x30 8x16 640x480 16/256K . A000 VGA,ATI VIP ++ * G 80x30 8x16 640x480 16/64 . A000 ATI EGA Wonder ++ * G . . 640x480 16 . . UltraVision+256K EGA ++ */ ++int graphics_init() ++{ ++ if (!graphics_inited) { ++ saved_videomode = set_videomode(0x12); ++ if (get_videomode() != 0x12) { ++ set_videomode(saved_videomode); ++ return 0; ++ } ++ graphics_inited = 1; ++ } ++ else ++ return 1; ++ ++ font8x16 = (unsigned char*)graphics_get_font(); ++ ++ /* make sure that the highlight color is set correctly */ ++ graphics_highlight_color = ((graphics_normal_color >> 4) | ++ ((graphics_normal_color & 0xf) << 4)); ++ ++ graphics_cls(); ++ ++ if (!read_image(splashimage)) { ++ grub_printf("Failed to read splash image (%s)\n", splashimage); ++ grub_printf("Press any key to continue..."); ++ getkey(); ++ set_videomode(saved_videomode); ++ graphics_inited = 0; ++ return 0; ++ } ++ ++ set_int1c_handler(); ++ ++ return 1; ++} ++ ++/* Leave graphics mode */ ++void graphics_end(void) ++{ ++ if (graphics_inited) { ++ unset_int1c_handler(); ++ set_videomode(saved_videomode); ++ graphics_inited = 0; ++ no_cursor = 0; ++ } ++} ++ ++/* Print ch on the screen. Handle any needed scrolling or the like */ ++void graphics_putchar(int ch) { ++ ch &= 0xff; ++ ++ graphics_cursor(0); ++ ++ if (ch == '\n') { ++ if (fonty + 1 < view_y1) ++ graphics_setxy(fontx, fonty + 1); ++ else ++ graphics_scroll(); ++ graphics_cursor(1); ++ return; ++ } else if (ch == '\r') { ++ graphics_setxy(view_x0, fonty); ++ graphics_cursor(1); ++ return; ++ } ++ ++ graphics_cursor(0); ++ ++ text[fonty * 80 + fontx] = ch; ++ text[fonty * 80 + fontx] &= 0x00ff; ++ if (graphics_current_color & 0xf0) ++ text[fonty * 80 + fontx] |= 0x100; ++ ++ graphics_cursor(0); ++ ++ if ((fontx + 1) >= view_x1) { ++ graphics_setxy(view_x0, fonty); ++ if (fonty + 1 < view_y1) ++ graphics_setxy(view_x0, fonty + 1); ++ else ++ graphics_scroll(); ++ graphics_cursor(1); ++ do_more (); ++ graphics_cursor(0); ++ } else { ++ graphics_setxy(fontx + 1, fonty); ++ } ++ ++ graphics_cursor(1); ++} ++ ++/* get the current location of the cursor */ ++int graphics_getxy(void) { ++ return (fontx << 8) | fonty; ++} ++ ++void graphics_gotoxy(int x, int y) { ++ graphics_cursor(0); ++ ++ graphics_setxy(x, y); ++ ++ graphics_cursor(1); ++} ++ ++void graphics_cls(void) { ++ int i; ++ unsigned char *mem, *s1, *s2, *s4, *s8; ++ ++ graphics_cursor(0); ++ graphics_gotoxy(view_x0, view_y0); ++ ++ mem = (unsigned char*)VIDEOMEM; ++ s1 = (unsigned char*)VSHADOW1; ++ s2 = (unsigned char*)VSHADOW2; ++ s4 = (unsigned char*)VSHADOW4; ++ s8 = (unsigned char*)VSHADOW8; ++ ++ for (i = 0; i < 80 * 30; i++) ++ text[i] = ' '; ++ graphics_cursor(1); ++ ++ BitMask(0xff); ++ ++ /* plane 1 */ ++ MapMask(1); ++ grub_memcpy(mem, s1, 38400); ++ ++ /* plane 2 */ ++ MapMask(2); ++ grub_memcpy(mem, s2, 38400); ++ ++ /* plane 3 */ ++ MapMask(4); ++ grub_memcpy(mem, s4, 38400); ++ ++ /* plane 4 */ ++ MapMask(8); ++ grub_memcpy(mem, s8, 38400); ++ ++ MapMask(15); ++ ++ if (no_cursor) { ++ no_cursor = 0; ++ set_int1c_handler(); ++ } ++} ++ ++void graphics_setcolorstate (color_state state) { ++ switch (state) { ++ case COLOR_STATE_STANDARD: ++ graphics_current_color = graphics_standard_color; ++ break; ++ case COLOR_STATE_NORMAL: ++ graphics_current_color = graphics_normal_color; ++ break; ++ case COLOR_STATE_HIGHLIGHT: ++ graphics_current_color = graphics_highlight_color; ++ break; ++ default: ++ graphics_current_color = graphics_standard_color; ++ break; ++ } ++ ++ graphics_color_state = state; ++} ++ ++void graphics_setcolor (int normal_color, int highlight_color) { ++ graphics_normal_color = normal_color; ++ graphics_highlight_color = highlight_color; ++ ++ graphics_setcolorstate (graphics_color_state); ++} ++ ++int graphics_setcursor (int on) { ++ if (!no_cursor && !on) { ++ no_cursor = 1; ++ unset_int1c_handler(); ++ graphics_cursor(0); ++ } ++ else if(no_cursor && on) { ++ no_cursor = 0; ++ set_int1c_handler(); ++ graphics_cursor(1); ++ } ++ return 0; ++} ++ ++/* Read in the splashscreen image and set the palette up appropriately. ++ * Format of splashscreen is an xpm (can be gzipped) with 16 colors and ++ * 640x480. */ ++int read_image(char *s) ++{ ++ char buf[32], pal[16], c; ++ unsigned char base, mask, *s1, *s2, *s4, *s8; ++ unsigned i, len, idx, colors, x, y, width, height; ++ ++ if (!grub_open(s)) ++ return 0; ++ ++ /* read header */ ++ if (!grub_read((char*)&buf, 10) || grub_memcmp(buf, "/* XPM */\n", 10)) { ++ grub_close(); ++ return 0; ++ } ++ ++ /* parse info */ ++ while (grub_read(&c, 1)) { ++ if (c == '"') ++ break; ++ } ++ ++ while (grub_read(&c, 1) && (c == ' ' || c == '\t')) ++ ; ++ ++ i = 0; ++ width = c - '0'; ++ while (grub_read(&c, 1)) { ++ if (c >= '0' && c <= '9') ++ width = width * 10 + c - '0'; ++ else ++ break; ++ } ++ while (grub_read(&c, 1) && (c == ' ' || c == '\t')) ++ ; ++ ++ height = c - '0'; ++ while (grub_read(&c, 1)) { ++ if (c >= '0' && c <= '9') ++ height = height * 10 + c - '0'; ++ else ++ break; ++ } ++ while (grub_read(&c, 1) && (c == ' ' || c == '\t')) ++ ; ++ ++ colors = c - '0'; ++ while (grub_read(&c, 1)) { ++ if (c >= '0' && c <= '9') ++ colors = colors * 10 + c - '0'; ++ else ++ break; ++ } ++ ++ base = 0; ++ while (grub_read(&c, 1) && c != '"') ++ ; ++ ++ /* palette */ ++ for (i = 0, idx = 1; i < colors; i++) { ++ len = 0; ++ ++ while (grub_read(&c, 1) && c != '"') ++ ; ++ grub_read(&c, 1); /* char */ ++ base = c; ++ grub_read(buf, 4); /* \t c # */ ++ ++ while (grub_read(&c, 1) && c != '"') { ++ if (len < sizeof(buf)) ++ buf[len++] = c; ++ } ++ ++ if (len == 6 && idx < 15) { ++ int r = ((hex(buf[0]) << 4) | hex(buf[1])) >> 2; ++ int g = ((hex(buf[2]) << 4) | hex(buf[3])) >> 2; ++ int b = ((hex(buf[4]) << 4) | hex(buf[5])) >> 2; ++ ++ pal[idx] = base; ++ graphics_set_palette(idx, r, g, b); ++ ++idx; ++ } ++ } ++ ++ x = y = len = 0; ++ ++ s1 = (unsigned char*)VSHADOW1; ++ s2 = (unsigned char*)VSHADOW2; ++ s4 = (unsigned char*)VSHADOW4; ++ s8 = (unsigned char*)VSHADOW8; ++ ++ for (i = 0; i < 38400; i++) ++ s1[i] = s2[i] = s4[i] = s8[i] = 0; ++ ++ /* parse xpm data */ ++ while (y < height) { ++ while (1) { ++ if (!grub_read(&c, 1)) { ++ grub_close(); ++ return 0; ++ } ++ if (c == '"') ++ break; ++ } ++ ++ while (grub_read(&c, 1) && c != '"') { ++ for (i = 1; i < 15; i++) ++ if (pal[i] == c) { ++ c = i; ++ break; ++ } ++ ++ mask = 0x80 >> (x & 7); ++ if (c & 1) ++ s1[len + (x >> 3)] |= mask; ++ if (c & 2) ++ s2[len + (x >> 3)] |= mask; ++ if (c & 4) ++ s4[len + (x >> 3)] |= mask; ++ if (c & 8) ++ s8[len + (x >> 3)] |= mask; ++ ++ if (++x >= 640) { ++ x = 0; ++ ++ if (y < 480) ++ len += 80; ++ ++y; ++ } ++ } ++ } ++ ++ grub_close(); ++ ++ graphics_set_palette(0, (background >> 16), (background >> 8) & 63, ++ background & 63); ++ graphics_set_palette(15, (foreground >> 16), (foreground >> 8) & 63, ++ foreground & 63); ++ graphics_set_palette(0x11, (window_border >> 16), (window_border >> 8) & 63, ++ window_border & 63); ++ ++ return 1; ++} ++ ++/* Convert a character which is a hex digit to the appropriate integer */ ++int hex(int v) ++{ ++ if (v >= 'A' && v <= 'F') ++ return (v - 'A' + 10); ++ if (v >= 'a' && v <= 'f') ++ return (v - 'a' + 10); ++ return (v - '0'); ++} ++ ++void graphics_cursor(int set) { ++ unsigned char *pat, *mem, *ptr, chr[16 << 2]; ++ int i, ch, invert, offset; ++ ++ if (set && (no_cursor || no_scroll)) ++ return; ++ ++ offset = cursorY * 80 + fontx; ++ ch = text[fonty * 80 + fontx] & 0xff; ++ invert = (text[fonty * 80 + fontx] & 0xff00) != 0; ++ pat = font8x16 + (ch << 4); ++ ++ mem = (unsigned char*)VIDEOMEM + offset; ++ ++ if (!set) { ++ for (i = 0; i < 16; i++) { ++ unsigned char mask = pat[i]; ++ ++ if (!invert) { ++ chr[i ] = ((unsigned char*)VSHADOW1)[offset]; ++ chr[16 + i] = ((unsigned char*)VSHADOW2)[offset]; ++ chr[32 + i] = ((unsigned char*)VSHADOW4)[offset]; ++ chr[48 + i] = ((unsigned char*)VSHADOW8)[offset]; ++ ++ if (shade) { ++ if (ch == DISP_VERT || ch == DISP_LL || ++ ch == DISP_UR || ch == DISP_LR) { ++ unsigned char pmask = ~(pat[i] >> 1); ++ ++ chr[i ] &= pmask; ++ chr[16 + i] &= pmask; ++ chr[32 + i] &= pmask; ++ chr[48 + i] &= pmask; ++ } ++ if (i > 0 && ch != DISP_VERT) { ++ unsigned char pmask = ~(pat[i - 1] >> 1); ++ ++ chr[i ] &= pmask; ++ chr[16 + i] &= pmask; ++ chr[32 + i] &= pmask; ++ chr[48 + i] &= pmask; ++ if (ch == DISP_HORIZ || ch == DISP_UR || ch == DISP_LR) { ++ pmask = ~pat[i - 1]; ++ ++ chr[i ] &= pmask; ++ chr[16 + i] &= pmask; ++ chr[32 + i] &= pmask; ++ chr[48 + i] &= pmask; ++ } ++ } ++ } ++ chr[i ] |= mask; ++ chr[16 + i] |= mask; ++ chr[32 + i] |= mask; ++ chr[48 + i] |= mask; ++ ++ offset += 80; ++ } ++ else { ++ chr[i ] = mask; ++ chr[16 + i] = mask; ++ chr[32 + i] = mask; ++ chr[48 + i] = mask; ++ } ++ } ++ } ++ else { ++ MapMask(15); ++ ptr = mem; ++ for (i = 0; i < 16; i++, ptr += 80) { ++ cursorBuf[i] = pat[i]; ++ *ptr = ~pat[i]; ++ } ++ return; ++ } ++ ++ offset = 0; ++ for (i = 1; i < 16; i <<= 1, offset += 16) { ++ int j; ++ ++ MapMask(i); ++ ptr = mem; ++ for (j = 0; j < 16; j++, ptr += 80) ++ *ptr = chr[j + offset]; ++ } ++ ++ MapMask(15); ++} ++ ++#endif /* SUPPORT_GRAPHICS */ +diff -Naur grub-0.97.orig/stage2/graphics.h grub-0.97/stage2/graphics.h +--- grub-0.97.orig/stage2/graphics.h 1969-12-31 16:00:00.000000000 -0800 ++++ grub-0.97/stage2/graphics.h 2006-07-03 23:58:41.000000000 -0700 +@@ -0,0 +1,44 @@ ++/* graphics.h - graphics console interface */ ++/* ++ * GRUB -- GRand Unified Bootloader ++ * Copyright (C) 2002 Free Software Foundation, Inc. ++ * ++ * 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 ++ * (at your option) 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. ++ */ ++ ++#ifndef GRAPHICS_H ++#define GRAPHICS_H ++ ++/* magic constant */ ++#define VIDEOMEM 0xA0000 ++ ++/* function prototypes */ ++char *graphics_get_splash(void); ++ ++int read_image(char *s); ++void graphics_cursor(int set); ++ ++/* function prototypes for asm functions */ ++void * graphics_get_font(); ++void graphics_set_palette(int idx, int red, int green, int blue); ++void set_int1c_handler(); ++void unset_int1c_handler(); ++ ++extern short cursorX, cursorY; ++extern char cursorBuf[16]; ++extern int shade; ++extern int view_x0, view_y0, view_x1, view_y1; ++ ++#endif /* GRAPHICS_H */ +diff -Naur grub-0.97.orig/stage2/Makefile.am grub-0.97/stage2/Makefile.am +--- grub-0.97.orig/stage2/Makefile.am 2005-02-02 12:37:35.000000000 -0800 ++++ grub-0.97/stage2/Makefile.am 2006-07-03 23:58:41.000000000 -0700 +@@ -7,7 +7,7 @@ + fat.h filesys.h freebsd.h fs.h hercules.h i386-elf.h \ + imgact_aout.h iso9660.h jfs.h mb_header.h mb_info.h md5.h \ + nbi.h pc_slice.h serial.h shared.h smp-imps.h term.h \ +- terminfo.h tparm.h nbi.h ufs2.h vstafs.h xfs.h ++ terminfo.h tparm.h nbi.h ufs2.h vstafs.h xfs.h graphics.h + EXTRA_DIST = setjmp.S apm.S $(noinst_SCRIPTS) + + # For . +@@ -19,7 +19,7 @@ + disk_io.c fsys_ext2fs.c fsys_fat.c fsys_ffs.c fsys_iso9660.c \ + fsys_jfs.c fsys_minix.c fsys_reiserfs.c fsys_ufs2.c \ + fsys_vstafs.c fsys_xfs.c gunzip.c md5.c serial.c stage2.c \ +- terminfo.c tparm.c ++ terminfo.c tparm.c graphics.c + libgrub_a_CFLAGS = $(GRUB_CFLAGS) -I$(top_srcdir)/lib \ + -DGRUB_UTIL=1 -DFSYS_EXT2FS=1 -DFSYS_FAT=1 -DFSYS_FFS=1 \ + -DFSYS_ISO9660=1 -DFSYS_JFS=1 -DFSYS_MINIX=1 -DFSYS_REISERFS=1 \ +@@ -79,8 +79,14 @@ + HERCULES_FLAGS = + endif + ++if GRAPHICS_SUPPORT ++GRAPHICS_FLAGS = -DSUPPORT_GRAPHICS=1 ++else ++GRAPHICS_FLAGS = ++endif ++ + STAGE2_COMPILE = $(STAGE2_CFLAGS) -fno-builtin -nostdinc \ +- $(NETBOOT_FLAGS) $(SERIAL_FLAGS) $(HERCULES_FLAGS) ++ $(NETBOOT_FLAGS) $(SERIAL_FLAGS) $(HERCULES_FLAGS) $(GRAPHICS_FLAGS) + + STAGE1_5_LINK = -nostdlib -Wl,-N -Wl,-Ttext -Wl,2000 + STAGE1_5_COMPILE = $(STAGE2_COMPILE) -DNO_DECOMPRESSION=1 -DSTAGE1_5=1 +@@ -90,7 +96,8 @@ + cmdline.c common.c console.c disk_io.c fsys_ext2fs.c \ + fsys_fat.c fsys_ffs.c fsys_iso9660.c fsys_jfs.c fsys_minix.c \ + fsys_reiserfs.c fsys_ufs2.c fsys_vstafs.c fsys_xfs.c gunzip.c \ +- hercules.c md5.c serial.c smp-imps.c stage2.c terminfo.c tparm.c ++ hercules.c md5.c serial.c smp-imps.c stage2.c terminfo.c tparm.c \ ++ graphics.c + pre_stage2_exec_CFLAGS = $(STAGE2_COMPILE) $(FSYS_CFLAGS) + pre_stage2_exec_CCASFLAGS = $(STAGE2_COMPILE) $(FSYS_CFLAGS) + pre_stage2_exec_LDFLAGS = $(PRE_STAGE2_LINK) +diff -Naur grub-0.97.orig/stage2/shared.h grub-0.97/stage2/shared.h +--- grub-0.97.orig/stage2/shared.h 2004-06-19 09:40:09.000000000 -0700 ++++ grub-0.97/stage2/shared.h 2006-07-04 00:01:50.000000000 -0700 +@@ -499,7 +499,11 @@ + unsigned char linear_reserved_field_position; + unsigned long max_pixel_clock; + +- unsigned char reserved3[189]; ++ /* Reserved field to make structure to be 256 bytes long, VESA BIOS ++ Extension 3.0 Specification says to reserve 189 bytes here but ++ that doesn't make structure to be 256 bytes. So additional one is ++ added here. */ ++ unsigned char reserved3[189 + 1]; + } __attribute__ ((packed)); + + +@@ -792,6 +796,11 @@ + /* Set the cursor position. */ + void gotoxy (int x, int y); + ++/* Internal pager ++ Returns 1 = if pager was used ++ 0 = if pager wasn't used */ ++int do_more (void); ++ + /* Displays an ASCII character. IBM displays will translate some + characters to special graphical ones (see the DISP_* constants). */ + void grub_putchar (int c); +@@ -871,6 +880,7 @@ + int grub_tolower (int c); + int grub_isspace (int c); + int grub_strncat (char *s1, const char *s2, int n); ++void grub_memcpy(void *dest, const void *src, int len); + void *grub_memmove (void *to, const void *from, int len); + void *grub_memset (void *start, int c, int len); + int grub_strncat (char *s1, const char *s2, int n); +@@ -911,7 +921,7 @@ + int nul_terminate (char *str); + int get_based_digit (int c, int base); + int safe_parse_maxint (char **str_ptr, int *myint_ptr); +-int memcheck (int start, int len); ++int memcheck (unsigned long int start, unsigned long int len); + void grub_putstr (const char *str); + + #ifndef NO_DECOMPRESSION +diff -Naur grub-0.97.orig/stage2/stage2.c grub-0.97/stage2/stage2.c +--- grub-0.97.orig/stage2/stage2.c 2005-03-19 09:51:57.000000000 -0800 ++++ grub-0.97/stage2/stage2.c 2006-07-04 00:01:50.000000000 -0700 +@@ -20,6 +20,12 @@ + #include + #include + ++#ifdef SUPPORT_GRAPHICS ++# include ++#endif ++ ++int col_start, col_end, row_start, box_size; ++ + grub_jmp_buf restart_env; + + #if defined(PRESET_MENU_STRING) || defined(SUPPORT_DISKLESS) +@@ -105,13 +111,13 @@ + if (highlight && current_term->setcolorstate) + current_term->setcolorstate (COLOR_STATE_HIGHLIGHT); + +- gotoxy (2, y); ++ gotoxy (2 + col_start, y); + grub_putchar (' '); +- for (x = 3; x < 75; x++) ++ for (x = 3 + col_start; x < (col_end - 5); x++) + { +- if (*entry && x <= 72) ++ if (*entry && x <= (col_end - 8)) + { +- if (x == 72) ++ if (x == (col_end - 8)) + grub_putchar (DISP_RIGHT); + else + grub_putchar (*entry++); +@@ -119,7 +125,7 @@ + else + grub_putchar (' '); + } +- gotoxy (74, y); ++ gotoxy ((col_end - 6), y); + + if (current_term->setcolorstate) + current_term->setcolorstate (COLOR_STATE_STANDARD); +@@ -131,7 +137,7 @@ + { + int i; + +- gotoxy (77, y + 1); ++ gotoxy ((col_end - 3), y + 1); + + if (first) + grub_putchar (DISP_UP); +@@ -151,14 +157,14 @@ + menu_entries++; + } + +- gotoxy (77, y + size); ++ gotoxy ((col_end - 3), y + size); + + if (*menu_entries) + grub_putchar (DISP_DOWN); + else + grub_putchar (' '); + +- gotoxy (74, y + entryno + 1); ++ gotoxy ((col_end - 6), y + entryno + 1); + } + + static void +@@ -196,30 +202,30 @@ + if (current_term->setcolorstate) + current_term->setcolorstate (COLOR_STATE_NORMAL); + +- gotoxy (1, y); ++ gotoxy (1 + col_start, y); + + grub_putchar (DISP_UL); +- for (i = 0; i < 73; i++) ++ for (i = col_start; i < (col_end - 7); i++) + grub_putchar (DISP_HORIZ); + grub_putchar (DISP_UR); + + i = 1; + while (1) + { +- gotoxy (1, y + i); ++ gotoxy (1 + col_start, y + i); + + if (i > size) + break; + + grub_putchar (DISP_VERT); +- gotoxy (75, y + i); ++ gotoxy ((col_end - 5), y + i); + grub_putchar (DISP_VERT); + + i++; + } + + grub_putchar (DISP_LL); +- for (i = 0; i < 73; i++) ++ for (i = col_start; i < (col_end - 7); i++) + grub_putchar (DISP_HORIZ); + grub_putchar (DISP_LR); + +@@ -233,6 +239,7 @@ + { + int c, time1, time2 = -1, first_entry = 0; + char *cur_entry = 0; ++ struct term_entry *prev_term = NULL; + + /* + * Main loop for menu UI. +@@ -250,6 +257,22 @@ + } + } + ++ col_start = 0; ++ col_end = 80; ++ row_start = 0; ++ box_size = 12; ++ /* if we're using viewport we need to make sure to setup ++ coordinates correctly. */ ++#ifdef SUPPORT_GRAPHICS ++ if (grub_memcmp (current_term->name, "graphics", sizeof ("graphics") - 1) == 0) ++ { ++ col_start = view_x0; ++ col_end = view_x1; ++ row_start = view_y0; ++ box_size = (view_y1 - view_y0) - 13; ++ } ++#endif ++ + /* If the timeout was expired or wasn't set, force to show the menu + interface. */ + if (grub_timeout < 0) +@@ -302,36 +325,36 @@ + if (current_term->flags & TERM_DUMB) + print_entries_raw (num_entries, first_entry, menu_entries); + else +- print_border (3, 12); ++ print_border (3 + row_start, box_size); + + grub_printf ("\n\ +- Use the %c and %c keys to select which entry is highlighted.\n", ++ Use the %c and %c keys to select which entry is highlighted.\n", + DISP_UP, DISP_DOWN); + + if (! auth && password) + { + printf ("\ +- Press enter to boot the selected OS or \'p\' to enter a\n\ +- password to unlock the next set of features."); ++ Press enter to boot the selected OS or \'p\' to enter a\n\ ++ password to unlock the next set of features."); + } + else + { + if (config_entries) + printf ("\ +- Press enter to boot the selected OS, \'e\' to edit the\n\ +- commands before booting, or \'c\' for a command-line."); ++ Press enter to boot the selected OS, \'e\' to edit the\n\ ++ commands before booting, or \'c\' for a command-line."); + else + printf ("\ +- Press \'b\' to boot, \'e\' to edit the selected command in the\n\ +- boot sequence, \'c\' for a command-line, \'o\' to open a new line\n\ +- after (\'O\' for before) the selected line, \'d\' to remove the\n\ +- selected line, or escape to go back to the main menu."); ++ Press \'b\' to boot, \'e\' to edit the selected command in the\n\ ++ boot sequence, \'c\' for a command-line, \'o\' to open a new line\n\ ++ after (\'O\' for before) the selected line, \'d\' to remove the\n\ ++ selected line, or escape to go back to the main menu."); + } + + if (current_term->flags & TERM_DUMB) + grub_printf ("\n\nThe selected entry is %d ", entryno); + else +- print_entries (3, 12, first_entry, entryno, menu_entries); ++ print_entries (3 + row_start, box_size, first_entry, entryno, menu_entries); + } + + /* XX using RT clock now, need to initialize value */ +@@ -358,10 +381,10 @@ + entryno, grub_timeout); + else + { +- gotoxy (3, 22); +- grub_printf ("The highlighted entry will be booted automatically in %d seconds. ", ++ gotoxy (3 + col_start, 10 + box_size + row_start); ++ grub_printf (" The highlighted entry will be booted automatically in %d seconds. ", + grub_timeout); +- gotoxy (74, 4 + entryno); ++ gotoxy ((col_end - 6), 4 + entryno + row_start); + } + + grub_timeout--; +@@ -387,12 +410,12 @@ + if (current_term->flags & TERM_DUMB) + grub_putchar ('\r'); + else +- gotoxy (3, 22); ++ gotoxy (3 + col_start, 10 + box_size + row_start); + printf (" "); + grub_timeout = -1; + fallback_entryno = -1; + if (! (current_term->flags & TERM_DUMB)) +- gotoxy (74, 4 + entryno); ++ gotoxy ((col_end - 6), 4 + entryno + row_start); + } + + /* We told them above (at least in SUPPORT_SERIAL) to use +@@ -408,12 +431,12 @@ + { + if (entryno > 0) + { +- print_entry (4 + entryno, 0, ++ print_entry (4 + entryno + row_start, 0, + get_entry (menu_entries, + first_entry + entryno, + 0)); + entryno--; +- print_entry (4 + entryno, 1, ++ print_entry (4 + entryno + row_start, 1, + get_entry (menu_entries, + first_entry + entryno, + 0)); +@@ -421,7 +444,7 @@ + else if (first_entry > 0) + { + first_entry--; +- print_entries (3, 12, first_entry, entryno, ++ print_entries (3 + row_start, box_size, first_entry, entryno, + menu_entries); + } + } +@@ -433,29 +456,29 @@ + entryno++; + else + { +- if (entryno < 11) ++ if (entryno < (box_size - 1)) + { +- print_entry (4 + entryno, 0, ++ print_entry (4 + entryno + row_start, 0, + get_entry (menu_entries, + first_entry + entryno, + 0)); + entryno++; +- print_entry (4 + entryno, 1, ++ print_entry (4 + entryno + row_start, 1, + get_entry (menu_entries, + first_entry + entryno, + 0)); + } +- else if (num_entries > 12 + first_entry) ++ else if (num_entries > box_size + first_entry) + { + first_entry++; +- print_entries (3, 12, first_entry, entryno, menu_entries); ++ print_entries (3 + row_start, box_size, first_entry, entryno, menu_entries); + } + } + } + else if (c == 7) + { + /* Page Up */ +- first_entry -= 12; ++ first_entry -= box_size; + if (first_entry < 0) + { + entryno += first_entry; +@@ -463,20 +486,20 @@ + if (entryno < 0) + entryno = 0; + } +- print_entries (3, 12, first_entry, entryno, menu_entries); ++ print_entries (3 + row_start, box_size, first_entry, entryno, menu_entries); + } + else if (c == 3) + { + /* Page Down */ +- first_entry += 12; ++ first_entry += box_size; + if (first_entry + entryno + 1 >= num_entries) + { +- first_entry = num_entries - 12; ++ first_entry = num_entries - box_size; + if (first_entry < 0) + first_entry = 0; + entryno = num_entries - first_entry - 1; + } +- print_entries (3, 12, first_entry, entryno, menu_entries); ++ print_entries (3 + row_start, box_size, first_entry, entryno, menu_entries); + } + + if (config_entries) +@@ -489,7 +512,7 @@ + if ((c == 'd') || (c == 'o') || (c == 'O')) + { + if (! (current_term->flags & TERM_DUMB)) +- print_entry (4 + entryno, 0, ++ print_entry (4 + entryno + row_start, 0, + get_entry (menu_entries, + first_entry + entryno, + 0)); +@@ -537,7 +560,7 @@ + + if (entryno >= num_entries) + entryno--; +- if (first_entry && num_entries < 12 + first_entry) ++ if (first_entry && num_entries < box_size + first_entry) + first_entry--; + } + +@@ -549,7 +572,7 @@ + grub_printf ("\n"); + } + else +- print_entries (3, 12, first_entry, entryno, menu_entries); ++ print_entries (3 + row_start, box_size, first_entry, entryno, menu_entries); + } + + cur_entry = menu_entries; +@@ -570,7 +593,7 @@ + if (current_term->flags & TERM_DUMB) + grub_printf ("\r "); + else +- gotoxy (1, 21); ++ gotoxy (1 + col_start, 9 + box_size + row_start); + + /* Wipe out the previously entered password */ + grub_memset (entered, 0, sizeof (entered)); +@@ -651,7 +674,10 @@ + *(new_heap++) = 0; + + if (config_entries) +- run_menu (heap, NULL, new_num_entries, new_heap, 0); ++ { ++ current_entryno = first_entry + entryno; ++ run_menu (heap, NULL, new_num_entries, new_heap, 0); ++ } + else + { + cls (); +@@ -714,6 +740,15 @@ + + cls (); + setcursor (1); ++ /* if our terminal needed initialization, we should shut it down ++ * before booting the kernel, but we want to save what it was so ++ * we can come back if needed */ ++ prev_term = current_term; ++ if (current_term->shutdown) ++ { ++ current_term->shutdown(); ++ current_term = term_table; /* assumption: console is first */ ++ } + + while (1) + { +@@ -727,7 +762,8 @@ + cur_entry = get_entry (config_entries, first_entry + entryno, 1); + + /* Set CURRENT_ENTRYNO for the command "savedefault". */ +- current_entryno = first_entry + entryno; ++ if (config_entries) ++ current_entryno = first_entry + entryno; + + if (run_script (cur_entry, heap)) + { +@@ -748,6 +784,13 @@ + break; + } + ++ /* if we get back here, we should go back to what our term was before */ ++ current_term = prev_term; ++ if (current_term->startup) ++ /* if our terminal fails to initialize, fall back to console since ++ * it should always work */ ++ if (current_term->startup() == 0) ++ current_term = term_table; /* we know that console is first */ + show_menu = 1; + goto restart; + } +@@ -891,8 +934,18 @@ + len = grub_read (buf, sizeof (buf)); + if (len > 0) + { ++ char *tmp; ++ char *def; + buf[sizeof (buf) - 1] = 0; +- safe_parse_maxint (&p, &saved_entryno); ++ ++ if((tmp = grub_strstr(p, ":")) != NULL) ++ { ++ *tmp++; ++ grub_memcpy(&def, &tmp, sizeof(p)); ++ }else ++ grub_memcpy(&def, &p, sizeof(p)); ++ ++ safe_parse_maxint (&def, &saved_entryno); + } + + grub_close (); +@@ -1050,6 +1103,16 @@ + while (is_preset); + } + ++ /* go ahead and make sure the terminal is setup */ ++ if (current_term->startup) ++ { ++ /* If initialization fails, go back to default terminal */ ++ if (current_term->startup() == 0) ++ { ++ current_term = term_table; ++ } ++ } ++ + if (! num_entries) + { + /* If no acceptable config file, goto command-line, starting +diff -Naur grub-0.97.orig/stage2/term.h grub-0.97/stage2/term.h +--- grub-0.97.orig/stage2/term.h 2003-07-09 04:45:53.000000000 -0700 ++++ grub-0.97/stage2/term.h 2006-07-03 23:58:41.000000000 -0700 +@@ -60,6 +60,8 @@ + const char *name; + /* The feature flags defined above. */ + unsigned long flags; ++ /* Default for maximum number of lines if not specified */ ++ unsigned short max_lines; + /* Put a character. */ + void (*putchar) (int c); + /* Check if any input character is available. */ +@@ -79,6 +81,10 @@ + void (*setcolor) (int normal_color, int highlight_color); + /* Turn on/off the cursor. */ + int (*setcursor) (int on); ++ /* function to start a terminal */ ++ int (*startup) (void); ++ /* function to use to shutdown a terminal */ ++ void (*shutdown) (void); + }; + + /* This lists up available terminals. */ +@@ -124,4 +130,24 @@ + int hercules_setcursor (int on); + #endif + ++#ifdef SUPPORT_GRAPHICS ++extern int foreground, background, window_border, graphics_inited, saved_videomode; ++ ++void graphics_set_splash(char *splashfile); ++int set_videomode(int mode); ++int get_videomode(void); ++void graphics_putchar (int c); ++int graphics_getxy(void); ++void graphics_gotoxy(int x, int y); ++void graphics_cls(void); ++void graphics_setcolorstate (color_state state); ++void graphics_setcolor (int normal_color, int highlight_color); ++int graphics_setcursor (int on); ++int graphics_init(void); ++void graphics_end(void); ++ ++int hex(int v); ++void graphics_set_palette(int idx, int red, int green, int blue); ++#endif /* SUPPORT_GRAPHICS */ ++ + #endif /* ! GRUB_TERM_HEADER */ +diff -Naur grub-0.97.orig/THANKS grub-0.97/THANKS +--- grub-0.97.orig/THANKS 2005-05-07 19:17:43.000000000 -0700 ++++ grub-0.97/THANKS 2006-07-04 00:01:50.000000000 -0700 +@@ -121,3 +121,4 @@ + Yedidyah Bar-David + Yury V. Umanets + Yuri Zaporogets ++Vitaly Fertman +diff -Naur grub-0.97.orig/util/grub-install.in grub-0.97/util/grub-install.in +--- grub-0.97.orig/util/grub-install.in 2004-07-24 11:57:31.000000000 -0700 ++++ grub-0.97/util/grub-install.in 2006-07-04 00:01:50.000000000 -0700 +@@ -81,6 +81,50 @@ + EOF + } + ++# Usage: getraid_mdadm mddevice ++# Routine to find a physical device from an md device ++# If found, the first grub BIOS device (from device.map) is returned ++# If no BIOS drives match the RAID devices, the first device returned ++# from mdadm -D is returned ++getraid_mdadm() { ++ device=$1 ++ mdadm=$(mdadm -D "$device") || { ++ echo "$PROG: mdadm -D $device failed" >&2 ++ exit 1 ++ } ++ eval "$( ++ echo "$mdadm" | awk ' ++ $1 == "Number" && $2 == "Major" { start = 1; next } ++ $1 == "UUID" { print "uuid=" $3; start = 0; next } ++ !start { next } ++ $2 == 0 && $3 == 0 { next } ++ { devices = devices "\n" $NF } ++ END { print "devices='\''" devices "'\''" } ++ ' ++ )" ++ ++ # Convert RAID devices list into a list of disks ++ tmp_disks=`echo "$devices" | sed -e 's%\([sh]d[a-z]\)[0-9]*$%\1%' \ ++ -e 's%\(d[0-9]*\)p[0-9]*$%\1%' \ ++ -e 's%\(fd[0-9]*\)$%\1%' \ ++ -e 's%/part[0-9]*$%/disc%' \ ++ -e 's%\(c[0-7]d[0-9]*\).*$%\1%' \ ++ -e '/^$/d' | ++ sed -n '1h;2,$H;${g;s/\n/|/g;p}'` ++ ++ # Find first BIOS disk that's a member of the RAID array ++ # Default to first RAID member if no tmp_disks are BIOS devices ++ set -- `egrep $tmp_disks $device_map | \ ++ sort | \ ++ sed -n 1p ` ++ device=${2:-${tmp_disks%%|*}} ++ ++ # Return first partition on BIOS disk that's part of the RAID ++ echo "$devices" | \ ++ sed -n "\:${device}:p" | \ ++ sed -n 1p ++} ++ + # Usage: convert os_device + # Convert an OS device to the corresponding GRUB drive. + # This part is OS-specific. +@@ -96,6 +140,10 @@ + # Break the device name into the disk part and the partition part. + case "$host_os" in + linux*) ++ # Find an actual physical device if we're passed a RAID device ++ case $1 in ++ /dev/md*) set -- `getraid_mdadm $1` ++ esac + tmp_disk=`echo "$1" | sed -e 's%\([sh]d[a-z]\)[0-9]*$%\1%' \ + -e 's%\(d[0-9]*\)p[0-9]*$%\1%' \ + -e 's%\(fd[0-9]*\)$%\1%' \ +@@ -112,8 +160,8 @@ + tmp_disk=`echo "$1" | sed 's%\([sh]d[0-9]*\).*%\1%'` + tmp_part=`echo "$1" | sed "s%$tmp_disk%%"` ;; + freebsd* | kfreebsd*-gnu) +- tmp_disk=`echo "$1" | sed 's%r\{0,1\}\([saw]d[0-9]*\).*$%r\1%' \ +- | sed 's%r\{0,1\}\(da[0-9]*\).*$%r\1%'` ++ tmp_disk=`echo "$1" | sed 's%r\{0,1\}\([saw]d[0-9]*\).*$%\1%' \ ++ | sed 's%r\{0,1\}\(da[0-9]*\).*$%\1%'` + tmp_part=`echo "$1" \ + | sed "s%.*/r\{0,1\}[saw]d[0-9]\(s[0-9]*[a-h]\)%\1%" \ + | sed "s%.*/r\{0,1\}da[0-9]\(s[0-9]*[a-h]\)%\1%"` +@@ -131,7 +179,7 @@ + + # Get the drive name. + tmp_drive=`grep -v '^#' $device_map | grep "$tmp_disk *$" \ +- | sed 's%.*\(([hf]d[0-9][a-g0-9,]*)\).*%\1%'` ++ | sed 's%.*\(([hf]d[0-9][a-z0-9,]*)\).*%\1%'` + + # If not found, print an error message and exit. + if test "x$tmp_drive" = x; then +@@ -148,13 +196,13 @@ + gnu*) + if echo $tmp_part | grep "^s" >/dev/null; then + tmp_pc_slice=`echo $tmp_part \ +- | sed "s%s\([0-9]*\)[a-g]*$%\1%"` ++ | sed "s%s\([0-9]*\)[a-z]*$%\1%"` + tmp_drive=`echo "$tmp_drive" \ + | sed "s%)%,\`expr "$tmp_pc_slice" - 1\`)%"` + fi +- if echo $tmp_part | grep "[a-g]$" >/dev/null; then ++ if echo $tmp_part | grep "[a-z]$" >/dev/null; then + tmp_bsd_partition=`echo "$tmp_part" \ +- | sed "s%[^a-g]*\([a-g]\)$%\1%"` ++ | sed "s%[^a-z]*\([a-z]\)$%\1%"` + tmp_drive=`echo "$tmp_drive" \ + | sed "s%)%,$tmp_bsd_partition)%"` + fi +@@ -336,6 +384,10 @@ + # Create a safe temporary file. + test -n "$mklog" && log_file=`$mklog` + ++ # Before all invocations of the grub shell, call sync to make sure ++ # the raw device is in sync with any bufferring in filesystems. ++ sync ++ + $grub_shell --batch $no_floppy --device-map=$device_map <$log_file + quit + EOF +@@ -450,6 +502,24 @@ + # Create a safe temporary file. + test -n "$mklog" && log_file=`$mklog` + ++# Sync to prevent GRUB from not finding stage files (notably, on XFS) ++sync ++ ++# XFS needs special magic ++xfs_frozen=false ++if which xfs_freeze > /dev/null ; then ++ cat << EOF ++Due to a bug in xfs_freeze, the following command might produce a segmentation ++fault when ${grubdir} is not in an XFS filesystem. This error is harmless and ++can be ignored. ++EOF ++ if xfs_freeze -f ${grubdir} ; then xfs_frozen=true ; fi ++fi ++ ++# Before all invocations of the grub shell, call sync to make sure ++# the raw device is in sync with any bufferring in filesystems. ++sync ++ + # Now perform the installation. + $grub_shell --batch $no_floppy --device-map=$device_map <$log_file + root $root_drive +@@ -457,6 +527,10 @@ + quit + EOF + ++if ${xfs_frozen} ; then ++ xfs_freeze -u ${grubdir} ++fi ++ + if grep "Error [0-9]*: " $log_file >/dev/null || test $debug = yes; then + cat $log_file 1>&2 + exit 1 diff --git a/target/linux/x86/image/Config.in b/target/linux/x86/image/Config.in index 4a36f63128..17deccfa72 100644 --- a/target/linux/x86/image/Config.in +++ b/target/linux/x86/image/Config.in @@ -2,6 +2,7 @@ config X86_GRUB_IMAGES bool "Build GRUB images (Linux x86 or x86_64 host only)" depends TARGET_x86 depends TARGET_ROOTFS_EXT2FS || TARGET_ROOTFS_JFFS2 || TARGET_ROOTFS_SQUASHFS || TARGET_ROOTFS_ISO + select PACKAGE_grub default y config X86_GRUB_IMAGES_PAD diff --git a/target/linux/x86/image/Makefile b/target/linux/x86/image/Makefile index d470fe1c5f..095d40240b 100644 --- a/target/linux/x86/image/Makefile +++ b/target/linux/x86/image/Makefile @@ -14,14 +14,6 @@ ROOTPART=$(strip $(subst ",, $(CONFIG_X86_GRUB_ROOTPART))) ifeq ($(CONFIG_X86_GRUB_IMAGES),y) - define Build/Compile - $(MAKE) -C grub compile - endef - - define Build/Clean - $(MAKE) -C grub clean - endef - define Image/cmdline/squashfs block2mtd.block2mtd=$(ROOTPART),65536,rootfs root=/dev/mtdblock0 rootfstype=squashfs init=/etc/preinit endef diff --git a/target/linux/x86/image/grub/Makefile b/target/linux/x86/image/grub/Makefile deleted file mode 100644 index dae74e9dc2..0000000000 --- a/target/linux/x86/image/grub/Makefile +++ /dev/null @@ -1,73 +0,0 @@ -# -# Copyright (C) 2006 OpenWrt.org -# -# This is free software, licensed under the GNU General Public License v2. -# See /LICENSE for more information. -# -# $Id: Makefile 4855 2006-09-24 20:49:31Z nico $ - -include $(TOPDIR)/rules.mk -include $(INCLUDE_DIR)/kernel.mk - -PKG_NAME:=grub -PKG_VERSION:=0.97 -PKG_RELEASE:=1 - -PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz -PKG_SOURCE_URL:=ftp://alpha.gnu.org/gnu/grub -PKG_MD5SUM:=cd3f3eb54446be6003156158d51f4884 -PKG_CAT:=zcat - -PKG_BUILD_DIR:=$(KERNEL_BUILD_DIR)/grub-$(PKG_VERSION) - -include $(INCLUDE_DIR)/package.mk - -ifeq ($(HOST_ARCH),x86_64) -CONFIGURE_FLAGS:= \ - --target=$(GNU_TARGET_NAME) \ - --host=$(GNU_TARGET_NAME) \ - --build=$(GNU_HOST_NAME) -else -CONFIGURE_FLAGS:= -endif - -define Build/Configure - (cd $(PKG_BUILD_DIR); \ - LDFLAGS="-static" \ - ./configure \ - $(CONFIGURE_FLAGS) \ - --program-prefix="" \ - --program-suffix="" \ - --prefix=/usr \ - --exec-prefix=/usr \ - --bindir=/usr/bin \ - --sbindir=/usr/sbin \ - --libexecdir=/usr/lib \ - --sysconfdir=/etc \ - --datadir=/usr/share \ - --localstatedir=/var \ - --mandir=/usr/man \ - --infodir=/usr/info \ - $(DISABLE_NLS) \ - --disable-auto-linux-mem-opt \ - ) -endef - -# -# ./configure detects whether the host compiler supports -# -fno-stack-protector but only sets STAGE2_CFLAGS accordingly -# -define Build/Compile - $(MAKE) -C $(PKG_BUILD_DIR) \ - GRUB_CFLAGS="\$$$$(STAGE2_CFLAGS)" \ - STAGE1_CFLAGS="\$$$$(STAGE2_CFLAGS)" -endef - -define Build/InstallDev - $(MAKE) -C $(PKG_BUILD_DIR) \ - DESTDIR="$(STAGING_DIR_HOST)" \ - install - mv $(STAGING_DIR_HOST)/usr/sbin/grub $(STAGING_DIR_HOST)/bin -endef - -$(eval $(call Build/DefaultTargets)) diff --git a/target/linux/x86/image/grub/menu.lst b/target/linux/x86/image/grub/menu.lst deleted file mode 100644 index cb306cc443..0000000000 --- a/target/linux/x86/image/grub/menu.lst +++ /dev/null @@ -1,15 +0,0 @@ -serial --unit=0 --speed=@BAUDRATE@ --word=8 --parity=no --stop=1 -terminal --timeout=2 console serial - -default 0 -timeout 5 - -title OpenWrt -root (hd0,0) -kernel /boot/vmlinuz @CMDLINE@ noinitrd console=tty0 console=ttyS0,@BAUDRATE@n8 reboot=bios -boot - -title OpenWrt (failsafe) -root (hd0,0) -kernel /boot/vmlinuz failsafe=true @CMDLINE@ noinitrd console=tty0 console=ttyS0,@BAUDRATE@n8 reboot=bios -boot diff --git a/target/linux/x86/image/grub/patches/010-fixes-1.patch b/target/linux/x86/image/grub/patches/010-fixes-1.patch deleted file mode 100644 index 6628b73822..0000000000 --- a/target/linux/x86/image/grub/patches/010-fixes-1.patch +++ /dev/null @@ -1,4490 +0,0 @@ -Submitted By: Jim Gifford (jim at linuxfromscratch dot org) -Date: 2006-07-04 -Initial Package Version: 0.97 -Origin: Debian -Upstream Status: Unknown -Description: Contains various fixes and enhancements - Graphics mode support - Fixes for Raid Support - XFS Filesystem Boot Freeze Fixes - Removed 2GB Memory Limitation - Freebsd support - Fixes for initrd support - Grub installation Fixes - Linux 2.6 geometry Fixes - Intel Mac Support - Autoconf and aclocal updates - -http://trac.cross-lfs.org/browser/trunk/patches/grub-0.97-fixes-1.patch - -diff -Naur grub-0.97.orig/aclocal.m4 grub-0.97/aclocal.m4 ---- grub-0.97.orig/aclocal.m4 2005-05-07 19:41:18.000000000 -0700 -+++ grub-0.97/aclocal.m4 2006-07-04 00:08:22.000000000 -0700 -@@ -1,7 +1,7 @@ --# generated automatically by aclocal 1.9.4 -*- Autoconf -*- -+# generated automatically by aclocal 1.9.6 -*- Autoconf -*- - --# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004 --# Free Software Foundation, Inc. -+# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, -+# 2005 Free Software Foundation, Inc. - # This file is free software; the Free Software Foundation - # gives unlimited permission to copy and/or distribute it, - # with or without modifications, as long as this notice is preserved. -@@ -11,23 +11,11 @@ - # even the implied warranty of MERCHANTABILITY or FITNESS FOR A - # PARTICULAR PURPOSE. - --# -*- Autoconf -*- --# Copyright (C) 2002, 2003 Free Software Foundation, Inc. --# Generated from amversion.in; do not edit by hand. -- --# 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, or (at your option) --# 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., 59 Temple Place - Suite 330, Boston, MA -+# Copyright (C) 2002, 2003, 2005 Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - - # AM_AUTOMAKE_VERSION(VERSION) - # ---------------------------- -@@ -40,26 +28,15 @@ - # Call AM_AUTOMAKE_VERSION so it can be traced. - # This function is AC_REQUIREd by AC_INIT_AUTOMAKE. - AC_DEFUN([AM_SET_CURRENT_AUTOMAKE_VERSION], -- [AM_AUTOMAKE_VERSION([1.9.4])]) -- --# AM_AUX_DIR_EXPAND -- --# Copyright (C) 2001, 2003 Free Software Foundation, Inc. -+ [AM_AUTOMAKE_VERSION([1.9.6])]) - --# 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, or (at your option) --# any later version. -+# AM_AUX_DIR_EXPAND -*- Autoconf -*- - --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -+# Copyright (C) 2001, 2003, 2005 Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - - # For projects using AC_CONFIG_AUX_DIR([foo]), Autoconf sets - # $ac_aux_dir to `$srcdir/foo'. In other projects, it is set to -@@ -106,26 +83,16 @@ - am_aux_dir=`cd $ac_aux_dir && pwd` - ]) - --# AM_CONDITIONAL -*- Autoconf -*- -+# AM_CONDITIONAL -*- Autoconf -*- - --# Copyright (C) 1997, 2000, 2001, 2003, 2004 Free Software Foundation, Inc. -- --# 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, or (at your option) --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -+# Copyright (C) 1997, 2000, 2001, 2003, 2004, 2005 -+# Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - --# serial 6 -+# serial 7 - - # AM_CONDITIONAL(NAME, SHELL-CONDITION) - # ------------------------------------- -@@ -149,26 +116,15 @@ - Usually this means the macro was only invoked conditionally.]]) - fi])]) - --# serial 7 -*- Autoconf -*- - --# Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004 -+# Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005 - # Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - --# 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, or (at your option) --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -- -+# serial 8 - - # There are a few dirty hacks below to avoid letting `AC_PROG_CC' be - # written in clear, in which case automake, when reading aclocal.m4, -@@ -177,7 +133,6 @@ - # CC etc. in the Makefile, will ask for an AC_PROG_CC use... - - -- - # _AM_DEPENDENCIES(NAME) - # ---------------------- - # See how the compiler implements dependency checking. -@@ -317,27 +272,16 @@ - AC_SUBST([AMDEPBACKSLASH]) - ]) - --# Generate code to set up dependency tracking. -*- Autoconf -*- -- --# Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004 --# Free Software Foundation, Inc. -- --# 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, or (at your option) --# any later version. -+# Generate code to set up dependency tracking. -*- Autoconf -*- - --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -+# Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005 -+# Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - --#serial 2 -+#serial 3 - - # _AM_OUTPUT_DEPENDENCY_COMMANDS - # ------------------------------ -@@ -396,30 +340,19 @@ - [AMDEP_TRUE="$AMDEP_TRUE" ac_aux_dir="$ac_aux_dir"]) - ]) - --# Do all the work for Automake. -*- Autoconf -*- -+# Do all the work for Automake. -*- Autoconf -*- - --# This macro actually does too much some checks are only needed if --# your package does certain things. But this isn't really a big deal. -- --# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004 -+# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005 - # Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - --# 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, or (at your option) --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -+# serial 12 - --# serial 11 -+# This macro actually does too much. Some checks are only needed if -+# your package does certain things. But this isn't really a big deal. - - # AM_INIT_AUTOMAKE(PACKAGE, VERSION, [NO-DEFINE]) - # AM_INIT_AUTOMAKE([OPTIONS]) -@@ -521,51 +454,27 @@ - done - echo "timestamp for $1" >`AS_DIRNAME([$1])`/stamp-h[]$_am_stamp_count]) - -+# Copyright (C) 2001, 2003, 2005 Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. -+ - # AM_PROG_INSTALL_SH - # ------------------ - # Define $install_sh. -- --# Copyright (C) 2001, 2003 Free Software Foundation, Inc. -- --# 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, or (at your option) --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -- - AC_DEFUN([AM_PROG_INSTALL_SH], - [AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl - install_sh=${install_sh-"$am_aux_dir/install-sh"} - AC_SUBST(install_sh)]) - --# -*- Autoconf -*- --# Copyright (C) 2003 Free Software Foundation, Inc. -- --# 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, or (at your option) --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -+# Copyright (C) 2003, 2005 Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - --# serial 1 -+# serial 2 - - # Check whether the underlying file-system supports filenames - # with a leading dot. For instance MS-DOS doesn't. -@@ -580,28 +489,17 @@ - rmdir .tst 2>/dev/null - AC_SUBST([am__leading_dot])]) - --# Add --enable-maintainer-mode option to configure. -+# Add --enable-maintainer-mode option to configure. -*- Autoconf -*- - # From Jim Meyering - --# Copyright (C) 1996, 1998, 2000, 2001, 2002, 2003, 2004 -+# Copyright (C) 1996, 1998, 2000, 2001, 2002, 2003, 2004, 2005 - # Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - --# 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, or (at your option) --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -- --# serial 3 -+# serial 4 - - AC_DEFUN([AM_MAINTAINER_MODE], - [AC_MSG_CHECKING([whether to enable maintainer-specific portions of Makefiles]) -@@ -620,26 +518,15 @@ - - AU_DEFUN([jm_MAINTAINER_MODE], [AM_MAINTAINER_MODE]) - --# Check to see how 'make' treats includes. -*- Autoconf -*- -- --# Copyright (C) 2001, 2002, 2003 Free Software Foundation, Inc. -+# Check to see how 'make' treats includes. -*- Autoconf -*- - --# 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, or (at your option) --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -+# Copyright (C) 2001, 2002, 2003, 2005 Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - --# serial 2 -+# serial 3 - - # AM_MAKE_INCLUDE() - # ----------------- -@@ -683,27 +570,16 @@ - rm -f confinc confmf - ]) - --# -*- Autoconf -*- -- -- --# Copyright (C) 1997, 1999, 2000, 2001, 2003 Free Software Foundation, Inc. -- --# 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, or (at your option) --# any later version. -+# Fake the existence of programs that GNU maintainers use. -*- Autoconf -*- - --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -+# Copyright (C) 1997, 1999, 2000, 2001, 2003, 2005 -+# Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - --# serial 3 -+# serial 4 - - # AM_MISSING_PROG(NAME, PROGRAM) - # ------------------------------ -@@ -729,27 +605,16 @@ - fi - ]) - -+# Copyright (C) 2003, 2004, 2005 Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. -+ - # AM_PROG_MKDIR_P - # --------------- - # Check whether `mkdir -p' is supported, fallback to mkinstalldirs otherwise. -- --# Copyright (C) 2003, 2004 Free Software Foundation, Inc. -- --# 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, or (at your option) --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -- -+# - # Automake 1.8 used `mkdir -m 0755 -p --' to ensure that directories - # created by `make install' are always world readable, even if the - # installer happens to have an overly restrictive umask (e.g. 077). -@@ -803,26 +668,15 @@ - fi - AC_SUBST([mkdir_p])]) - --# Helper functions for option handling. -*- Autoconf -*- -+# Helper functions for option handling. -*- Autoconf -*- - --# Copyright (C) 2001, 2002, 2003 Free Software Foundation, Inc. -- --# 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, or (at your option) --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -+# Copyright (C) 2001, 2002, 2003, 2005 Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - --# serial 2 -+# serial 3 - - # _AM_MANGLE_OPTION(NAME) - # ----------------------- -@@ -847,28 +701,16 @@ - AC_DEFUN([_AM_IF_OPTION], - [m4_ifset(_AM_MANGLE_OPTION([$1]), [$2], [$3])]) - --# --# Check to make sure that the build environment is sane. --# -- --# Copyright (C) 1996, 1997, 2000, 2001, 2003 Free Software Foundation, Inc. -- --# 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, or (at your option) --# any later version. -+# Check to make sure that the build environment is sane. -*- Autoconf -*- - --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -+# Copyright (C) 1996, 1997, 2000, 2001, 2003, 2005 -+# Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - --# serial 3 -+# serial 4 - - # AM_SANITY_CHECK - # --------------- -@@ -911,25 +753,14 @@ - fi - AC_MSG_RESULT(yes)]) - --# AM_PROG_INSTALL_STRIP -- --# Copyright (C) 2001, 2003 Free Software Foundation, Inc. -- --# 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, or (at your option) --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -+# Copyright (C) 2001, 2003, 2005 Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - -+# AM_PROG_INSTALL_STRIP -+# --------------------- - # One issue with vendor `install' (even GNU) is that you can't - # specify the program used to strip binaries. This is especially - # annoying in cross-compiling environments, where the build's strip -@@ -952,25 +783,13 @@ - - # Check how to create a tarball. -*- Autoconf -*- - --# Copyright (C) 2004 Free Software Foundation, Inc. -- --# 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, or (at your option) --# 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., 59 Temple Place - Suite 330, Boston, MA --# 02111-1307, USA. -- --# serial 1 -+# Copyright (C) 2004, 2005 Free Software Foundation, Inc. -+# -+# This file is free software; the Free Software Foundation -+# gives unlimited permission to copy and/or distribute it, -+# with or without modifications, as long as this notice is preserved. - -+# serial 2 - - # _AM_PROG_TAR(FORMAT) - # -------------------- -diff -Naur grub-0.97.orig/ChangeLog grub-0.97/ChangeLog ---- grub-0.97.orig/ChangeLog 2005-05-07 19:47:02.000000000 -0700 -+++ grub-0.97/ChangeLog 2006-07-04 00:01:50.000000000 -0700 -@@ -1,3 +1,51 @@ -+2006-05-02 Pavel Roskin -+ -+ * stage2/stage2.c (run_menu): Fix "savedefault" to save only top -+ level menu positions. Remember current position when calling a -+ submenu. Don't recalculate it when booting from a submenu. -+ -+ * grub/main.c (main): Make sure the boot drive number doesn't -+ exceed 255. -+ -+2006-05-02 Vesa Jaaskelainen -+ -+ * stage2/shared.h (vbe_mode): Back ported aligment fix from GRUB 2 -+ to GRUB Legacy. Problem reported by Gerardo Richarte. -+ -+2006-04-23 Robert Millan -+ -+ * grub/asmstub.c (get_diskinfo): Optimize sysctl routine. -+ -+2006-04-20 Robert Millan -+ -+ Fixes for kernel of FreeBSD: -+ * grub/asmstub.c (get_diskinfo): Toggle "kern.geom.debugflags" sysctl -+ before opening a device for writing. -+ * util/grub-install.in: Devices don't have this "r" prefix anymore. -+ -+2006-04-16 Yoshinori K. Okuji -+ -+ * docs/multiboot.texi: Correct the offset of address -+ fields. Reported by Jeroen Dekkers. -+ -+2006-03-21 Yoshinori K. Okuji -+ -+ * stage2/builtins.c (setup_func): Specify the size of DEVICE to -+ grub_strncat instead of a strange number 256. Reported by Vitaly -+ Fertman . -+ -+2005-09-29 Yoshinori K. Okuji -+ -+ * docs/multiboot.texi: Fix a bug in the byte order of -+ boot_device. I hope this won't affect any OS image. -+ Increased the version number to 0.6.94. -+ -+2005-09-28 Yoshinori K. Okuji -+ -+ * stage2/boot.c (load_image): Even if an OS image is an ELF -+ object, use the a.out kludge if MULTIBOOT_AOUT_KLUDGE is -+ specified. -+ - 2005-05-08 Yoshinori K. Okuji - - * configure.ac (AC_INIT): Upgraded to 0.97. -diff -Naur grub-0.97.orig/configure grub-0.97/configure ---- grub-0.97.orig/configure 2005-05-07 19:48:12.000000000 -0700 -+++ grub-0.97/configure 2006-07-04 00:08:05.000000000 -0700 -@@ -311,7 +311,7 @@ - # include - #endif" - --ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS INSTALL_PROGRAM INSTALL_SCRIPT INSTALL_DATA CYGPATH_W PACKAGE VERSION ACLOCAL AUTOCONF AUTOMAKE AUTOHEADER MAKEINFO install_sh STRIP ac_ct_STRIP INSTALL_STRIP_PROGRAM mkdir_p AWK SET_MAKE am__leading_dot AMTAR am__tar am__untar build build_cpu build_vendor build_os host host_cpu host_vendor host_os MAINTAINER_MODE_TRUE MAINTAINER_MODE_FALSE MAINT PERL CC ac_ct_CC CFLAGS LDFLAGS CPPFLAGS EXEEXT OBJEXT DEPDIR am__include am__quote AMDEP_TRUE AMDEP_FALSE AMDEPBACKSLASH CCDEPMODE am__fastdepCC_TRUE am__fastdepCC_FALSE CCAS RANLIB ac_ct_RANLIB STAGE1_CFLAGS STAGE2_CFLAGS GRUB_CFLAGS OBJCOPY ac_ct_OBJCOPY GRUB_LIBS CPP EGREP NETBOOT_SUPPORT_TRUE NETBOOT_SUPPORT_FALSE DISKLESS_SUPPORT_TRUE DISKLESS_SUPPORT_FALSE HERCULES_SUPPORT_TRUE HERCULES_SUPPORT_FALSE SERIAL_SUPPORT_TRUE SERIAL_SUPPORT_FALSE SERIAL_SPEED_SIMULATION_TRUE SERIAL_SPEED_SIMULATION_FALSE BUILD_EXAMPLE_KERNEL_TRUE BUILD_EXAMPLE_KERNEL_FALSE FSYS_CFLAGS NET_CFLAGS NET_EXTRAFLAGS NETBOOT_DRIVERS CCASFLAGS LIBOBJS LTLIBOBJS' -+ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS INSTALL_PROGRAM INSTALL_SCRIPT INSTALL_DATA CYGPATH_W PACKAGE VERSION ACLOCAL AUTOCONF AUTOMAKE AUTOHEADER MAKEINFO install_sh STRIP ac_ct_STRIP INSTALL_STRIP_PROGRAM mkdir_p AWK SET_MAKE am__leading_dot AMTAR am__tar am__untar build build_cpu build_vendor build_os host host_cpu host_vendor host_os MAINTAINER_MODE_TRUE MAINTAINER_MODE_FALSE MAINT PERL CC ac_ct_CC CFLAGS LDFLAGS CPPFLAGS EXEEXT OBJEXT DEPDIR am__include am__quote AMDEP_TRUE AMDEP_FALSE AMDEPBACKSLASH CCDEPMODE am__fastdepCC_TRUE am__fastdepCC_FALSE CCAS RANLIB ac_ct_RANLIB STAGE1_CFLAGS STAGE2_CFLAGS GRUB_CFLAGS OBJCOPY ac_ct_OBJCOPY GRUB_LIBS CPP EGREP NETBOOT_SUPPORT_TRUE NETBOOT_SUPPORT_FALSE DISKLESS_SUPPORT_TRUE DISKLESS_SUPPORT_FALSE GRAPHICS_SUPPORT_TRUE GRAPHICS_SUPPORT_FALSE HERCULES_SUPPORT_TRUE HERCULES_SUPPORT_FALSE SERIAL_SUPPORT_TRUE SERIAL_SUPPORT_FALSE SERIAL_SPEED_SIMULATION_TRUE SERIAL_SPEED_SIMULATION_FALSE BUILD_EXAMPLE_KERNEL_TRUE BUILD_EXAMPLE_KERNEL_FALSE FSYS_CFLAGS NET_CFLAGS NET_EXTRAFLAGS NETBOOT_DRIVERS CCASFLAGS LIBOBJS LTLIBOBJS' - ac_subst_files='' - - # Initialize some variables set by options. -@@ -914,6 +914,7 @@ - set the default memory location for WD/SMC - --enable-cs-scan=LIST probe for CS89x0 base address using LIST - --enable-diskless enable diskless support -+ --disable-graphics disable graphics terminal support - --disable-hercules disable hercules terminal support - --disable-serial disable serial terminal support - --enable-serial-speed-simulation -@@ -5966,6 +5967,22 @@ - fi - - -+# Check whether --enable-graphics or --disable-graphics was given. -+if test "${enable_graphics+set}" = set; then -+ enableval="$enable_graphics" -+ -+fi; -+ -+ -+if test "x$enable_graphics" != xno; then -+ GRAPHICS_SUPPORT_TRUE= -+ GRAPHICS_SUPPORT_FALSE='#' -+else -+ GRAPHICS_SUPPORT_TRUE='#' -+ GRAPHICS_SUPPORT_FALSE= -+fi -+ -+ - # Check whether --enable-hercules or --disable-hercules was given. - if test "${enable_hercules+set}" = set; then - enableval="$enable_hercules" -@@ -6270,6 +6287,13 @@ - Usually this means the macro was only invoked conditionally." >&2;} - { (exit 1); exit 1; }; } - fi -+if test -z "${GRAPHICS_SUPPORT_TRUE}" && test -z "${GRAPHICS_SUPPORT_FALSE}"; then -+ { { echo "$as_me:$LINENO: error: conditional \"GRAPHICS_SUPPORT\" was never defined. -+Usually this means the macro was only invoked conditionally." >&5 -+echo "$as_me: error: conditional \"GRAPHICS_SUPPORT\" was never defined. -+Usually this means the macro was only invoked conditionally." >&2;} -+ { (exit 1); exit 1; }; } -+fi - if test -z "${HERCULES_SUPPORT_TRUE}" && test -z "${HERCULES_SUPPORT_FALSE}"; then - { { echo "$as_me:$LINENO: error: conditional \"HERCULES_SUPPORT\" was never defined. - Usually this means the macro was only invoked conditionally." >&5 -@@ -6907,6 +6931,8 @@ - s,@NETBOOT_SUPPORT_FALSE@,$NETBOOT_SUPPORT_FALSE,;t t - s,@DISKLESS_SUPPORT_TRUE@,$DISKLESS_SUPPORT_TRUE,;t t - s,@DISKLESS_SUPPORT_FALSE@,$DISKLESS_SUPPORT_FALSE,;t t -+s,@GRAPHICS_SUPPORT_TRUE@,$GRAPHICS_SUPPORT_TRUE,;t t -+s,@GRAPHICS_SUPPORT_FALSE@,$GRAPHICS_SUPPORT_FALSE,;t t - s,@HERCULES_SUPPORT_TRUE@,$HERCULES_SUPPORT_TRUE,;t t - s,@HERCULES_SUPPORT_FALSE@,$HERCULES_SUPPORT_FALSE,;t t - s,@SERIAL_SUPPORT_TRUE@,$SERIAL_SUPPORT_TRUE,;t t -diff -Naur grub-0.97.orig/configure.ac grub-0.97/configure.ac ---- grub-0.97.orig/configure.ac 2005-05-07 19:36:03.000000000 -0700 -+++ grub-0.97/configure.ac 2006-07-03 23:58:41.000000000 -0700 -@@ -595,6 +595,11 @@ - [ --enable-diskless enable diskless support]) - AM_CONDITIONAL(DISKLESS_SUPPORT, test "x$enable_diskless" = xyes) - -+dnl Graphical splashscreen support -+AC_ARG_ENABLE(graphics, -+ [ --disable-graphics disable graphics terminal support]) -+AM_CONDITIONAL(GRAPHICS_SUPPORT, test "x$enable_graphics" != xno) -+ - dnl Hercules terminal - AC_ARG_ENABLE(hercules, - [ --disable-hercules disable hercules terminal support]) -diff -Naur grub-0.97.orig/docs/grub.8 grub-0.97/docs/grub.8 ---- grub-0.97.orig/docs/grub.8 2005-05-07 19:48:56.000000000 -0700 -+++ grub-0.97/docs/grub.8 2006-07-04 00:01:50.000000000 -0700 -@@ -1,5 +1,5 @@ - .\" DO NOT MODIFY THIS FILE! It was generated by help2man 1.23. --.TH GRUB "8" "May 2005" "grub (GNU GRUB 0.97)" FSF -+.TH GRUB "8" "September 2005" "grub (GNU GRUB 0.97)" FSF - .SH NAME - grub \- the grub shell - .SH SYNOPSIS -diff -Naur grub-0.97.orig/docs/grub.texi grub-0.97/docs/grub.texi ---- grub-0.97.orig/docs/grub.texi 2005-05-07 19:59:59.000000000 -0700 -+++ grub-0.97/docs/grub.texi 2006-07-04 00:00:54.000000000 -0700 -@@ -2199,6 +2199,7 @@ - * rarp:: Initialize a network device via RARP - * serial:: Set up a serial device - * setkey:: Configure the key map -+* splashimage:: Use a splash image - * terminal:: Choose a terminal - * terminfo:: Define escape sequences for a terminal - * tftpserver:: Specify a TFTP server -@@ -2578,6 +2579,16 @@ - @end deffn - - -+@node splashimage -+@subsection splashimage -+ -+@deffn Command splashimage file -+Select an image to use as the background image. This should be -+specified using normal GRUB device naming syntax. The format of the -+file is a gzipped xpm which is 640x480 with a 14 color palette. -+@end deffn -+ -+ - @node terminal - @subsection terminal - -@@ -2685,6 +2696,7 @@ - * module:: Load a module - * modulenounzip:: Load a module without decompression - * pause:: Wait for a key press -+* print:: Print a message - * quit:: Exit from the grub shell - * reboot:: Reboot your computer - * read:: Read data from memory -@@ -3091,6 +3103,16 @@ - @end deffn - - -+@node print -+@subsection print -+ -+@deffn Command print message @dots{} -+Print the @var{message}. Note that placing @key{^G} (ASCII code 7) in the -+message will cause the speaker to emit the standard beep sound, which is -+useful for visually impaired people. -+@end deffn -+ -+ - @node quit - @subsection quit - -diff -Naur grub-0.97.orig/docs/multiboot.texi grub-0.97/docs/multiboot.texi ---- grub-0.97.orig/docs/multiboot.texi 2003-07-09 04:45:36.000000000 -0700 -+++ grub-0.97/docs/multiboot.texi 2006-07-04 00:01:50.000000000 -0700 -@@ -25,7 +25,7 @@ - @ifinfo - Copyright @copyright{} 1995, 96 Bryan Ford - Copyright @copyright{} 1995, 96 Erich Stefan Boleyn --Copyright @copyright{} 1999, 2000, 2001, 2002 Free Software Foundation, Inc. -+Copyright @copyright{} 1999, 2000, 2001, 2002, 2005, 2006 Free Software Foundation, Inc. - - Permission is granted to make and distribute verbatim copies of - this manual provided the copyright notice and this permission notice -@@ -57,7 +57,7 @@ - @vskip 0pt plus 1filll - Copyright @copyright{} 1995, 96 Bryan Ford - Copyright @copyright{} 1995, 96 Erich Stefan Boleyn --Copyright @copyright{} 1999, 2000, 2001, 2002 Free Software Foundation, Inc. -+Copyright @copyright{} 1999, 2000, 2001, 2002, 2005, 2006 Free Software Foundation, Inc. - - Permission is granted to make and distribute verbatim copies of - this manual provided the copyright notice and this permission notice -@@ -80,7 +80,7 @@ - @top Multiboot Specification - - This file documents Multiboot Specification, the proposal for the boot --sequence standard. This edition documents version 0.6.93. -+sequence standard. This edition documents version 0.6.94. - @end ifnottex - - @menu -@@ -426,7 +426,7 @@ - kernel. - - If bit 16 in the @samp{flags} word is set, then the fields at offsets --8-24 in the Multiboot header are valid, and the boot loader should use -+12-28 in the Multiboot header are valid, and the boot loader should use - them instead of the fields in the actual executable header to calculate - where to load the OS image. This information does not need to be - provided if the kernel image is in @sc{elf} format, but it @emph{must} -@@ -677,7 +677,7 @@ - @example - @group - +-------+-------+-------+-------+ --| drive | part1 | part2 | part3 | -+| part3 | part2 | part1 | drive | - +-------+-------+-------+-------+ - @end group - @end example -@@ -1199,6 +1199,13 @@ - @email{bug-grub@@gnu.org}, from Bryan Ford and Erich Stefan Boleyn. - @end itemize - -+@item -+The byte order of the @samp{boot_device} in Multiboot information is -+reversed. This was a mistake. -+ -+@item -+The offset of the address fields were wrong. -+ - @item 0.6 - @itemize @bullet - @item -diff -Naur grub-0.97.orig/grub/asmstub.c grub-0.97/grub/asmstub.c ---- grub-0.97.orig/grub/asmstub.c 2005-02-16 12:45:14.000000000 -0800 -+++ grub-0.97/grub/asmstub.c 2006-07-04 00:01:50.000000000 -0700 -@@ -42,6 +42,12 @@ - #include - #include - #include -+#include -+ -+#include -+#ifndef PAGESIZE -+#define PAGESIZE 4096 -+#endif - - #ifdef __linux__ - # include /* ioctl */ -@@ -55,6 +61,10 @@ - # endif /* ! BLKFLSBUF */ - #endif /* __linux__ */ - -+#if defined(__FreeBSD_kernel__) || defined(__FreeBSD__) -+# include -+#endif -+ - /* We want to prevent any circularararity in our stubs, as well as - libc name clashes. */ - #define WITHOUT_LIBC_STUBS 1 -@@ -144,6 +154,22 @@ - assert (grub_scratch_mem == 0); - scratch = malloc (0x100000 + EXTENDED_MEMSIZE + 15); - assert (scratch); -+ -+ { -+ char *p; -+ int ret; -+ -+ /* Align to a multiple of PAGESIZE, assumed to be a power of two. */ -+ p = (char *) (((long) scratch) & ~(PAGESIZE - 1)); -+ -+ /* The simulated stack needs to be executable, since GCC uses stack -+ * trampolines to implement nested functions. -+ */ -+ ret = mprotect (p, 0x100000 + EXTENDED_MEMSIZE + 15, -+ PROT_READ | PROT_WRITE | PROT_EXEC); -+ assert (ret == 0); -+ } -+ - grub_scratch_mem = (char *) ((((int) scratch) >> 4) << 4); - - /* FIXME: simulate the memory holes using mprot, if available. */ -@@ -777,7 +803,39 @@ - - /* Open read/write, or read-only if that failed. */ - if (! read_only) -- disks[drive].flags = open (devname, O_RDWR); -+ { -+/* By default, kernel of FreeBSD does not allow overwriting MBR */ -+#if defined(__FreeBSD_kernel__) || defined(__FreeBSD__) -+#define GEOM_SYSCTL "kern.geom.debugflags" -+ int old_flags, flags; -+ size_t sizeof_int = sizeof (int); -+ -+ if (sysctlbyname (GEOM_SYSCTL, &old_flags, &sizeof_int, NULL, 0) != 0) -+ grub_printf ("failed to get " GEOM_SYSCTL "sysctl: %s\n", strerror (errno)); -+ -+ if ((old_flags & 0x10) == 0) -+ { -+ /* "allow foot shooting", see geom(4) */ -+ flags = old_flags | 0x10; -+ -+ if (sysctlbyname (GEOM_SYSCTL, NULL, NULL, &flags, sizeof (int)) != 0) -+ { -+ flags = old_flags; -+ grub_printf ("failed to set " GEOM_SYSCTL "sysctl: %s\n", strerror (errno)); -+ } -+ } -+ else -+ flags = old_flags; -+#endif -+ disks[drive].flags = open (devname, O_RDWR); -+#if defined(__FreeBSD_kernel__) || defined(__FreeBSD__) -+ if (flags != old_flags) -+ { -+ if (sysctlbyname (GEOM_SYSCTL, NULL, NULL, &old_flags, sizeof (int)) != 0) -+ grub_printf ("failed to set " GEOM_SYSCTL "sysctl: %s\n", strerror (errno)); -+ } -+#endif -+ } - - if (disks[drive].flags == -1) - { -diff -Naur grub-0.97.orig/grub/main.c grub-0.97/grub/main.c ---- grub-0.97.orig/grub/main.c 2003-07-09 04:45:36.000000000 -0700 -+++ grub-0.97/grub/main.c 2006-07-04 00:01:50.000000000 -0700 -@@ -32,6 +32,7 @@ - #define WITHOUT_LIBC_STUBS 1 - #include - #include -+#include - - char *program_name = 0; - int use_config_file = 1; -@@ -192,6 +193,12 @@ - perror ("strtoul"); - exit (1); - } -+ if (boot_drive >= NUM_DISKS) -+ { -+ fprintf (stderr, "boot_drive should be from 0 to %d\n", -+ NUM_DISKS - 1); -+ exit (1); -+ } - break; - - case OPT_NO_CONFIG_FILE: -diff -Naur grub-0.97.orig/lib/device.c grub-0.97/lib/device.c ---- grub-0.97.orig/lib/device.c 2005-03-27 15:14:25.000000000 -0800 -+++ grub-0.97/lib/device.c 2006-07-04 00:00:44.000000000 -0700 -@@ -131,6 +131,152 @@ - #include - #include - -+#if defined(__linux__) -+/* The 2.6 kernel has removed all of the geometry handling for IDE drives -+ * that did fixups for LBA, etc. This means that the geometry we get -+ * with the ioctl has a good chance of being wrong. So, we get to -+ * also know about partition tables and try to read what the geometry -+ * is there. *grumble* Very closely based on code from cfdisk -+ */ -+static void get_kernel_geometry(int fd, long long *cyl, int *heads, int *sectors) { -+ struct hd_geometry hdg; -+ -+ if (ioctl (fd, HDIO_GETGEO, &hdg)) -+ return; -+ -+ *cyl = hdg.cylinders; -+ *heads = hdg.heads; -+ *sectors = hdg.sectors; -+} -+ -+struct partition { -+ unsigned char boot_ind; /* 0x80 - active */ -+ unsigned char head; /* starting head */ -+ unsigned char sector; /* starting sector */ -+ unsigned char cyl; /* starting cylinder */ -+ unsigned char sys_ind; /* What partition type */ -+ unsigned char end_head; /* end head */ -+ unsigned char end_sector; /* end sector */ -+ unsigned char end_cyl; /* end cylinder */ -+ unsigned char start4[4]; /* starting sector counting from 0 */ -+ unsigned char size4[4]; /* nr of sectors in partition */ -+}; -+ -+#define ALIGNMENT 2 -+typedef union { -+ struct { -+ unsigned char align[ALIGNMENT]; -+ unsigned char b[SECTOR_SIZE]; -+ } c; -+ struct { -+ unsigned char align[ALIGNMENT]; -+ unsigned char buffer[0x1BE]; -+ struct partition part[4]; -+ unsigned char magicflag[2]; -+ } p; -+} partition_table; -+ -+#define PART_TABLE_FLAG0 0x55 -+#define PART_TABLE_FLAG1 0xAA -+ -+static void -+get_partition_table_geometry(partition_table *bufp, long long *cyl, int *heads, -+ int *sectors) { -+ struct partition *p; -+ int i,h,s,hh,ss; -+ int first = 1; -+ int bad = 0; -+ -+ if (bufp->p.magicflag[0] != PART_TABLE_FLAG0 || -+ bufp->p.magicflag[1] != PART_TABLE_FLAG1) { -+ /* Matthew Wilcox: slightly friendlier version of -+ fatal(_("Bad signature on partition table"), 3); -+ */ -+ fprintf(stderr, "Unknown partition table signature\n"); -+ return; -+ } -+ -+ hh = ss = 0; -+ for (i=0; i<4; i++) { -+ p = &(bufp->p.part[i]); -+ if (p->sys_ind != 0) { -+ h = p->end_head + 1; -+ s = (p->end_sector & 077); -+ if (first) { -+ hh = h; -+ ss = s; -+ first = 0; -+ } else if (hh != h || ss != s) -+ bad = 1; -+ } -+ } -+ -+ if (!first && !bad) { -+ *heads = hh; -+ *sectors = ss; -+ } -+} -+ -+static long long my_lseek (unsigned int fd, long long offset, -+ unsigned int origin) -+{ -+#if defined(__linux__) && (!defined(__GLIBC__) || \ -+ ((__GLIBC__ < 2) || ((__GLIBC__ == 2) && (__GLIBC_MINOR__ < 1)))) -+ /* Maybe libc doesn't have large file support. */ -+ loff_t offset, result; -+ static int _llseek (uint filedes, ulong hi, ulong lo, -+ loff_t *res, uint wh); -+ _syscall5 (int, _llseek, uint, filedes, ulong, hi, ulong, lo, -+ loff_t *, res, uint, wh); -+ -+ if (_llseek (fd, offset >> 32, offset & 0xffffffff, &result, SEEK_SET) < 0) -+ return (long long) -1; -+ return result; -+#else -+ return lseek(fd, offset, SEEK_SET); -+#endif -+} -+ -+static void get_linux_geometry (int fd, struct geometry *geom) { -+ long long kern_cyl = 0; int kern_head = 0, kern_sectors = 0; -+ long long pt_cyl = 0; int pt_head = 0, pt_sectors = 0; -+ partition_table bufp; -+ char *buff, *buf_unaligned; -+ -+ buf_unaligned = malloc(sizeof(partition_table) + 4095); -+ buff = (char *) (((unsigned long)buf_unaligned + 4096 - 1) & -+ (~(4096-1))); -+ -+ get_kernel_geometry(fd, &kern_cyl, &kern_head, &kern_sectors); -+ -+ if (my_lseek (fd, 0*SECTOR_SIZE, SEEK_SET) < 0) { -+ fprintf(stderr, "Unable to seek"); -+ } -+ -+ if (read(fd, buff, SECTOR_SIZE) == SECTOR_SIZE) { -+ memcpy(bufp.c.b, buff, SECTOR_SIZE); -+ get_partition_table_geometry(&bufp, &pt_cyl, &pt_head, &pt_sectors); -+ } else { -+ fprintf(stderr, "Unable to read partition table: %s\n", strerror(errno)); -+ } -+ -+ if (pt_head && pt_sectors) { -+ int cyl_size; -+ -+ geom->heads = pt_head; -+ geom->sectors = pt_sectors; -+ cyl_size = pt_head * pt_sectors; -+ geom->cylinders = geom->total_sectors/cyl_size; -+ } else { -+ geom->heads = kern_head; -+ geom->sectors = kern_sectors; -+ geom->cylinders = kern_cyl; -+ } -+ -+ return; -+} -+#endif -+ - /* Get the geometry of a drive DRIVE. */ - void - get_drive_geometry (struct geometry *geom, char **map, int drive) -@@ -151,21 +297,16 @@ - #if defined(__linux__) - /* Linux */ - { -- struct hd_geometry hdg; - unsigned long nr; -- -- if (ioctl (fd, HDIO_GETGEO, &hdg)) -- goto fail; - - if (ioctl (fd, BLKGETSIZE, &nr)) - goto fail; - - /* Got the geometry, so save it. */ -- geom->cylinders = hdg.cylinders; -- geom->heads = hdg.heads; -- geom->sectors = hdg.sectors; - geom->total_sectors = nr; -- -+ get_linux_geometry(fd, geom); -+ if (!geom->heads && !geom->cylinders && !geom->sectors) -+ goto fail; - goto success; - } - -@@ -403,6 +544,18 @@ - } - - static void -+get_cciss_disk_name (char *name, int controller, int drive) -+{ -+ sprintf (name, "/dev/cciss/c%dd%d", controller, drive); -+} -+ -+static void -+get_ida_disk_name (char *name, int controller, int drive) -+{ -+ sprintf (name, "/dev/ida/c%dd%d", controller, drive); -+} -+ -+static void - get_ataraid_disk_name (char *name, int unit) - { - sprintf (name, "/dev/ataraid/d%c", unit + '0'); -@@ -801,6 +954,74 @@ - } - } - } -+ -+ /* This is for CCISS, its like the DAC960 - we have -+ /dev/cciss/dp -+ -+ It currently supports up to 3 controllers, 10 logical volumes -+ and 10 partitions -+ -+ Code gratuitously copied from DAC960 above. -+ Horms 23rd July 2004 -+ */ -+ { -+ int controller, drive; -+ -+ for (controller = 0; controller < 2; controller++) -+ { -+ for (drive = 0; drive < 9; drive++) -+ { -+ char name[24]; -+ -+ get_cciss_disk_name (name, controller, drive); -+ if (check_device (name)) -+ { -+ (*map)[num_hd + 0x80] = strdup (name); -+ assert ((*map)[num_hd + 0x80]); -+ -+ /* If the device map file is opened, write the map. */ -+ if (fp) -+ fprintf (fp, "(hd%d)\t%s\n", num_hd, name); -+ -+ num_hd++; -+ } -+ } -+ } -+ } -+ -+ /* This is for Compaq Smart Array, its like the DAC960 - we have -+ /dev/ida/dp -+ -+ It currently supports up to 3 controllers, 10 logical volumes -+ and 15 partitions -+ -+ Code gratuitously copied from DAC960 above. -+ Piotr Roszatycki -+ */ -+ { -+ int controller, drive; -+ -+ for (controller = 0; controller < 2; controller++) -+ { -+ for (drive = 0; drive < 9; drive++) -+ { -+ char name[24]; -+ -+ get_ida_disk_name (name, controller, drive); -+ if (check_device (name)) -+ { -+ (*map)[num_hd + 0x80] = strdup (name); -+ assert ((*map)[num_hd + 0x80]); -+ -+ /* If the device map file is opened, write the map. */ -+ if (fp) -+ fprintf (fp, "(hd%d)\t%s\n", num_hd, name); -+ -+ num_hd++; -+ } -+ } -+ } -+ } - #endif /* __linux__ */ - - /* OK, close the device map file if opened. */ -@@ -844,6 +1065,7 @@ - { - char dev[PATH_MAX]; /* XXX */ - int fd; -+ off_t offset = (off_t) sector * (off_t) SECTOR_SIZE; - - if ((partition & 0x00FF00) != 0x00FF00) - { -@@ -861,8 +1083,14 @@ - if (strcmp (dev + strlen(dev) - 5, "/disc") == 0) - strcpy (dev + strlen(dev) - 5, "/part"); - } -- sprintf (dev + strlen(dev), "%d", ((partition >> 16) & 0xFF) + 1); -- -+ sprintf (dev + strlen(dev), "%s%d", -+ /* Compaq smart and others */ -+ (strncmp(dev, "/dev/ida/", 9) == 0 || -+ strncmp(dev, "/dev/ataraid/", 13) == 0 || -+ strncmp(dev, "/dev/cciss/", 11) == 0 || -+ strncmp(dev, "/dev/rd/", 8) == 0) ? "p" : "", -+ ((partition >> 16) & 0xFF) + 1); -+ - /* Open the partition. */ - fd = open (dev, O_RDWR); - if (fd < 0) -@@ -870,35 +1098,13 @@ - errnum = ERR_NO_PART; - return 0; - } -- --#if defined(__linux__) && (!defined(__GLIBC__) || \ -- ((__GLIBC__ < 2) || ((__GLIBC__ == 2) && (__GLIBC_MINOR__ < 1)))) -- /* Maybe libc doesn't have large file support. */ -- { -- loff_t offset, result; -- static int _llseek (uint filedes, ulong hi, ulong lo, -- loff_t *res, uint wh); -- _syscall5 (int, _llseek, uint, filedes, ulong, hi, ulong, lo, -- loff_t *, res, uint, wh); - -- offset = (loff_t) sector * (loff_t) SECTOR_SIZE; -- if (_llseek (fd, offset >> 32, offset & 0xffffffff, &result, SEEK_SET)) -- { -- errnum = ERR_DEV_VALUES; -- return 0; -- } -- } --#else -- { -- off_t offset = (off_t) sector * (off_t) SECTOR_SIZE; - -- if (lseek (fd, offset, SEEK_SET) != offset) -- { -- errnum = ERR_DEV_VALUES; -- return 0; -- } -- } --#endif -+ if (my_lseek(fd, offset, SEEK_SET) != offset) -+ { -+ errnum = ERR_DEV_VALUES; -+ return 0; -+ } - - if (write (fd, buf, size * SECTOR_SIZE) != (size * SECTOR_SIZE)) - { -diff -Naur grub-0.97.orig/stage2/asm.S grub-0.97/stage2/asm.S ---- grub-0.97.orig/stage2/asm.S 2004-06-19 09:55:22.000000000 -0700 -+++ grub-0.97/stage2/asm.S 2006-07-04 00:01:19.000000000 -0700 -@@ -1651,7 +1651,29 @@ - jnz 3f - ret - --3: /* use keyboard controller */ -+3: /* -+ * try to switch gateA20 using PORT92, the "Fast A20 and Init" -+ * register -+ */ -+ mov $0x92, %dx -+ inb %dx, %al -+ /* skip the port92 code if it's unimplemented (read returns 0xff) */ -+ cmpb $0xff, %al -+ jz 6f -+ -+ /* set or clear bit1, the ALT_A20_GATE bit */ -+ movb 4(%esp), %ah -+ testb %ah, %ah -+ jz 4f -+ orb $2, %al -+ jmp 5f -+4: and $0xfd, %al -+ -+ /* clear the INIT_NOW bit don't accidently reset the machine */ -+5: and $0xfe, %al -+ outb %al, %dx -+ -+6: /* use keyboard controller */ - pushl %eax - - call gloop1 -@@ -1661,9 +1683,12 @@ - - gloopint1: - inb $K_STATUS -+ cmpb $0xff, %al -+ jz gloopint1_done - andb $K_IBUF_FUL, %al - jnz gloopint1 - -+gloopint1_done: - movb $KB_OUTPUT_MASK, %al - cmpb $0, 0x8(%esp) - jz gdoit -@@ -1684,6 +1709,8 @@ - - gloop1: - inb $K_STATUS -+ cmpb $0xff, %al -+ jz gloop2ret - andb $K_IBUF_FUL, %al - jnz gloop1 - -@@ -1991,6 +2018,11 @@ - ENTRY(console_getkey) - push %ebp - -+wait_for_key: -+ call EXT_C(console_checkkey) -+ incl %eax -+ jz wait_for_key -+ - call EXT_C(prot_to_real) - .code16 - -@@ -2216,7 +2248,304 @@ - pop %ebx - pop %ebp - ret -- -+ -+ -+/* graphics mode functions */ -+#ifdef SUPPORT_GRAPHICS -+VARIABLE(cursorX) -+.word 0 -+VARIABLE(cursorY) -+.word 0 -+VARIABLE(cursorCount) -+.word 0 -+VARIABLE(cursorBuf) -+.byte 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 -+ -+ -+/* -+ * set_int1c_handler(void) -+ */ -+ENTRY(set_int1c_handler) -+ pushl %edi -+ -+ /* save the original int1c handler */ -+ movl $0x70, %edi -+ movw (%edi), %ax -+ movw %ax, ABS(int1c_offset) -+ movw 2(%edi), %ax -+ movw %ax, ABS(int1c_segment) -+ -+ /* save the new int1c handler */ -+ movw $ABS(int1c_handler), %ax -+ movw %ax, (%edi) -+ xorw %ax, %ax -+ movw %ax, 2(%edi) -+ -+ popl %edi -+ ret -+ -+ -+/* -+ * unset_int1c_handler(void) -+ */ -+ENTRY(unset_int1c_handler) -+ pushl %edi -+ -+ /* check if int1c_handler is set */ -+ movl $0x70, %edi -+ movw $ABS(int1c_handler), %ax -+ cmpw %ax, (%edi) -+ jne int1c_1 -+ xorw %ax, %ax -+ cmpw %ax, 2(%edi) -+ jne int1c_1 -+ -+ /* restore the original */ -+ movw ABS(int1c_offset), %ax -+ movw %ax, (%edi) -+ movw ABS(int1c_segment), %ax -+ movw %ax, 2(%edi) -+ -+int1c_1: -+ popl %edi -+ ret -+ -+ -+/* -+ * blinks graphics cursor -+ */ -+ .code16 -+write_data: -+ movw $0, %ax -+ movw %ax, %ds -+ -+ mov $0xA000, %ax /* video in es:di */ -+ mov %ax, %es -+ mov $80, %ax -+ movw $ABS(cursorY), %si -+ mov %ds:(%si), %bx -+ mul %bx -+ movw $ABS(cursorX), %si -+ mov %ds:(%si), %bx -+ shr $3, %bx /* %bx /= 8 */ -+ add %bx, %ax -+ mov %ax, %di -+ -+ movw $ABS(cursorBuf), %si /* fontBuf in ds:si */ -+ -+ /* prepare for data moving */ -+ mov $16, %dx /* altura da fonte */ -+ mov $80, %bx /* bytes por linha */ -+ -+write_loop: -+ movb %ds:(%si), %al -+ xorb $0xff, %al -+ movb %al, %ds:(%si) /* invert cursorBuf */ -+ movb %al, %es:(%di) /* write to video */ -+ add %bx, %di -+ inc %si -+ dec %dx -+ jg write_loop -+ ret -+ -+int1c_handler: -+ pusha -+ mov $0, %ax -+ mov %ax, %ds -+ mov $ABS(cursorCount), %si -+ mov %ds:(%si), %ax -+ inc %ax -+ mov %ax, %ds:(%si) -+ cmp $9, %ax -+ jne int1c_done -+ -+ mov $0, %ax -+ mov %ax, %ds:(%si) -+ call write_data -+ -+int1c_done: -+ popa -+ iret -+ /* call previous int1c handler */ -+ /* ljmp */ -+ .byte 0xea -+int1c_offset: .word 0 -+int1c_segment: .word 0 -+ .code32 -+ -+ -+/* -+ * unsigned char set_videomode(unsigned char mode) -+ * BIOS call "INT 10H Function 0h" to set video mode -+ * Call with %ah = 0x0 -+ * %al = video mode -+ * Returns old videomode. -+ */ -+ENTRY(set_videomode) -+ pushl %ebp -+ movl %esp,%ebp -+ pushl %ebx -+ pushl %ecx -+ -+ movb 8(%ebp), %cl -+ -+ call EXT_C(prot_to_real) -+ .code16 -+ -+ xorb %al, %al -+ movb $0xf, %ah -+ int $0x10 /* Get Current Video mode */ -+ movb %al, %ch -+ xorb %ah, %ah -+ movb %cl, %al -+ int $0x10 /* Set Video mode */ -+ -+ DATA32 call EXT_C(real_to_prot) -+ .code32 -+ -+ xorl %eax, %eax -+ movb %ch, %al -+ -+ popl %ecx -+ popl %ebx -+ popl %ebp -+ ret -+ -+ -+/* -+ * int get_videomode() -+ * BIOS call "INT 10H Function 0Fh" to get current video mode -+ * Call with %al = 0x0 -+ * %ah = 0xF -+ * Returns current videomode. -+ */ -+ENTRY(get_videomode) -+ pushl %ebp -+ movl %esp,%ebp -+ pushl %ebx -+ pushl %ecx -+ -+ call EXT_C(prot_to_real) -+ .code16 -+ -+ xorb %al, %al -+ movb $0xF, %ah -+ int $0x10 /* Get Current Video mode */ -+ movb %al, %cl /* For now we only want display mode */ -+ -+ DATA32 call EXT_C(real_to_prot) -+ .code32 -+ -+ xorl %eax, %eax -+ movb %cl, %al -+ -+ popl %ecx -+ popl %ebx -+ popl %ebp -+ ret -+ -+ -+/* -+ * unsigned char * graphics_get_font() -+ * BIOS call "INT 10H Function 11h" to set font -+ * Call with %ah = 0x11 -+ */ -+ENTRY(graphics_get_font) -+ push %ebp -+ push %ebx -+ push %ecx -+ push %edx -+ -+ call EXT_C(prot_to_real) -+ .code16 -+ -+ movw $0x1130, %ax -+ movb $6, %bh /* font 8x16 */ -+ int $0x10 -+ movw %bp, %dx -+ movw %es, %cx -+ -+ DATA32 call EXT_C(real_to_prot) -+ .code32 -+ -+ xorl %eax, %eax -+ movw %cx, %ax -+ shll $4, %eax -+ movw %dx, %ax -+ -+ pop %edx -+ pop %ecx -+ pop %ebx -+ pop %ebp -+ ret -+ -+ -+/* -+ * graphics_set_palette(index, red, green, blue) -+ * BIOS call "INT 10H Function 10h" to set individual dac register -+ * Call with %ah = 0x10 -+ * %bx = register number -+ * %ch = new value for green (0-63) -+ * %cl = new value for blue (0-63) -+ * %dh = new value for red (0-63) -+ */ -+ -+ENTRY(graphics_set_palette) -+ push %ebp -+ push %eax -+ push %ebx -+ push %ecx -+ push %edx -+ -+ movw $0x3c8, %bx /* address write mode register */ -+ -+ /* wait vertical retrace */ -+ movw $0x3da, %dx -+l1b: -+ inb %dx, %al /* wait vertical active display */ -+ test $8, %al -+ jnz l1b -+ -+l2b: -+ inb %dx, %al /* wait vertical retrace */ -+ test $8, %al -+ jnz l2b -+ -+ mov %bx, %dx -+ movb 0x18(%esp), %al /* index */ -+ outb %al, %dx -+ inc %dx -+ -+ movb 0x1c(%esp), %al /* red */ -+ outb %al, %dx -+ -+ movb 0x20(%esp), %al /* green */ -+ outb %al, %dx -+ -+ movb 0x24(%esp), %al /* blue */ -+ outb %al, %dx -+ -+ movw 0x18(%esp), %bx -+ -+ call EXT_C(prot_to_real) -+ .code16 -+ -+ movb %bl, %bh -+ movw $0x1000, %ax -+ int $0x10 -+ -+ DATA32 call EXT_C(real_to_prot) -+ .code32 -+ -+ pop %edx -+ pop %ecx -+ pop %ebx -+ pop %eax -+ pop %ebp -+ ret -+#endif /* SUPPORT_GRAPHICS */ -+ -+ - /* - * getrtsecs() - * if a seconds value can be read, read it and return it (BCD), -diff -Naur grub-0.97.orig/stage2/boot.c grub-0.97/stage2/boot.c ---- grub-0.97.orig/stage2/boot.c 2004-03-30 03:44:08.000000000 -0800 -+++ grub-0.97/stage2/boot.c 2006-07-04 00:01:50.000000000 -0700 -@@ -1,7 +1,7 @@ - /* boot.c - load and bootstrap a kernel */ - /* - * GRUB -- GRand Unified Bootloader -- * Copyright (C) 1999,2000,2001,2002,2003,2004 Free Software Foundation, Inc. -+ * Copyright (C) 1999,2000,2001,2002,2003,2004,2005 Free Software Foundation, Inc. - * - * 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 -@@ -29,6 +29,8 @@ - entry_func entry_addr; - static struct mod_list mll[99]; - static int linux_mem_size; -+static int elf_kernel_addr; -+static int elf_kernel_size; - - /* - * The next two functions, 'load_image' and 'load_module', are the building -@@ -96,7 +98,7 @@ - lh = (struct linux_kernel_header *) buffer; - - /* ELF loading supported if multiboot, FreeBSD and NetBSD. */ -- if ((type == KERNEL_TYPE_MULTIBOOT -+ if (((type == KERNEL_TYPE_MULTIBOOT && ! (flags & MULTIBOOT_AOUT_KLUDGE)) - || pu.elf->e_ident[EI_OSABI] == ELFOSABI_FREEBSD - || grub_strcmp (pu.elf->e_ident + EI_BRAND, "FreeBSD") == 0 - || suggested_type == KERNEL_TYPE_NETBSD) -@@ -594,6 +596,7 @@ - - /* reset this to zero for now */ - cur_addr = 0; -+ elf_kernel_addr = ~0; - - /* scan for program segments */ - for (i = 0; i < pu.elf->e_phnum; i++) -@@ -630,6 +633,8 @@ - /* mark memory as used */ - if (cur_addr < memaddr + memsiz) - cur_addr = memaddr + memsiz; -+ if (elf_kernel_addr > cur_addr) -+ elf_kernel_addr = cur_addr; - printf (", <0x%x:0x%x:0x%x>", memaddr, filesiz, - memsiz - filesiz); - /* increment number of segments */ -@@ -647,6 +652,8 @@ - } - } - -+ elf_kernel_size = cur_addr - elf_kernel_addr; -+ - if (! errnum) - { - if (! loaded) -@@ -824,8 +831,11 @@ - moveto = (mbi.mem_upper + 0x400) << 10; - - moveto = (moveto - len) & 0xfffff000; -- max_addr = (lh->header == LINUX_MAGIC_SIGNATURE && lh->version >= 0x0203 -- ? lh->initrd_addr_max : LINUX_INITRD_MAX_ADDRESS); -+ max_addr = LINUX_INITRD_MAX_ADDRESS; -+ if (lh->header == LINUX_MAGIC_SIGNATURE && -+ lh->version >= 0x0203 && -+ lh->initrd_addr_max < max_addr) -+ max_addr = lh->initrd_addr_max; - if (moveto + len >= max_addr) - moveto = (max_addr - len) & 0xfffff000; - -@@ -864,6 +874,129 @@ - } - #endif - -+#define mem_align4k(p) ((p) + 0xFFF) & 0xFFFFF000 -+ -+static void -+kfreebsd_setenv (char *env, const char *var, const char *value) -+{ -+ while (1) -+ { -+ if (env[0] == '\0' && env[1] == '\0') -+ { -+ env++; -+ break; -+ } -+ else -+ env++; -+ } -+ -+ grub_sprintf (env, "%s=%s", var, value); -+ env[grub_strlen (env) + 1] = '\0'; -+} -+ -+static char * -+kfreebsd_read_hints (char *buf) -+{ -+ char *buf_end = buf; -+ -+ if (grub_open ("/boot/device.hints")) -+ { -+ char *line_start; -+ int line_len = 0; -+ char *envp; -+ int env_len; -+ -+ env_len = grub_read (buf, -1); -+ if (env_len) -+ { -+ buf_end += env_len; -+ *(buf_end++) = '\0'; -+ } -+ else -+ return buf_end; -+ -+ grub_close (); -+ -+ envp = line_start = buf; -+ while (*envp) -+ { -+ char *envp_current = envp; -+ -+ switch (*envp) -+ { -+ case ' ': -+ while (*envp == ' ') -+ { -+ envp++; -+ env_len--; -+ } -+ grub_memmove (envp_current, envp, env_len + 1); -+ envp = envp_current; -+ break; -+ case '#': -+ while (*envp != '\n') -+ { -+ envp++; -+ env_len--; -+ } -+ if (!line_len) -+ envp++; -+ grub_memmove (envp_current, envp, env_len + 1); -+ envp = envp_current; -+ break; -+ case '\n': -+ if (!line_len) -+ { -+ env_len--; -+ grub_memmove (line_start, envp, env_len + 1); -+ } -+ *(envp++) = '\0'; -+ line_len = 0; -+ line_start = envp; -+ default: -+ envp++; -+ line_len++; -+ break; -+ } -+ } -+ -+ buf_end = buf + env_len; -+ *(buf_end++) = '\0'; -+ } -+ -+ return buf_end; -+} -+ -+static u32_t * -+kfreebsd_set_module_string (u32_t type, u32_t *dst, char *src) -+{ -+ int size; -+ -+ *(dst++) = type; -+ *(dst++) = size = grub_strlen (src) + 1; -+ grub_strcpy ((void *) dst, src); -+ -+ return dst + (size + sizeof(u32_t) - 1) / sizeof(u32_t); -+} -+ -+static u32_t * -+kfreebsd_set_module_var (u32_t type, u32_t *dst, u32_t src) -+{ -+ *(dst++) = type; -+ *(dst++) = sizeof(u32_t); -+ *(dst++) = src; -+ -+ return dst; -+} -+ -+static u32_t * -+kfreebsd_set_modules (u32_t *modulep) -+{ -+ /* XXX: Need to copy the whole module structure. */ -+ /* XXX: How to pass the module name ? */ -+ -+ return modulep; -+} - - /* - * All "*_boot" commands depend on the images being loaded into memory -@@ -877,7 +1010,10 @@ - bsd_boot (kernel_t type, int bootdev, char *arg) - { - char *str; -- int clval = 0, i; -+ char *kernelname; -+ char *bsd_root; -+ int clval = 0; -+ int i; - struct bootinfo bi; - - #ifdef GRUB_UTIL -@@ -886,8 +1022,21 @@ - stop_floppy (); - #endif - -+ while (*arg != '/') -+ arg++; -+ kernelname = arg; -+ - while (*(++arg) && *arg != ' '); -+ *(arg++) = 0; - str = arg; -+ -+ bsd_root = grub_strstr (str, "root="); -+ if (bsd_root) -+ { -+ bsd_root += 5; -+ /* XXX: should copy the str or terminate it. */ -+ } -+ - while (*str) - { - if (*str == '-') -@@ -910,6 +1059,8 @@ - clval |= RB_GDB; - if (*str == 'h') - clval |= RB_SERIAL; -+ if (*str == 'p') -+ clval |= RB_PAUSE; - if (*str == 'm') - clval |= RB_MUTE; - if (*str == 'r') -@@ -927,14 +1078,17 @@ - - if (type == KERNEL_TYPE_FREEBSD) - { -+ char *envp; -+ u32_t *modp; -+ - clval |= RB_BOOTINFO; - - bi.bi_version = BOOTINFO_VERSION; - -- *arg = 0; -- while ((--arg) > (char *) MB_CMDLINE_BUF && *arg != '/'); -- if (*arg == '/') -- bi.bi_kernelname = arg + 1; -+ bi.bi_pad[0] = bi.bi_pad[1] = 0; -+ -+ if (*kernelname == '/') -+ bi.bi_kernelname = kernelname; - else - bi.bi_kernelname = 0; - -@@ -961,6 +1115,30 @@ - bi.bi_basemem = mbi.mem_lower; - bi.bi_extmem = extended_memory; - -+ /* Setup the environment. */ -+ bi.bi_envp = cur_addr = mem_align4k (cur_addr); -+ grub_memset ((void *) cur_addr, 0, 2); -+ cur_addr = (int) kfreebsd_read_hints ((void *) cur_addr); -+ -+ envp = (char *) bi.bi_envp; -+ kfreebsd_setenv (envp, "kernelname", kernelname); -+ kfreebsd_setenv (envp, "vfs.root.mountfrom", bsd_root); -+ -+ /* Setup the modules list. */ -+ bi.bi_modulep = cur_addr = mem_align4k (cur_addr); -+ modp = (u32_t *) bi.bi_modulep; -+ /* The first module is the kernel. */ -+ modp = kfreebsd_set_module_string (MODINFO_NAME, modp, kernelname); -+ modp = kfreebsd_set_module_string (MODINFO_TYPE, modp, "elf kernel"); -+ modp = kfreebsd_set_module_string (MODINFO_ARGS, modp, arg); -+ modp = kfreebsd_set_module_var (MODINFO_ADDR, modp, elf_kernel_addr); -+ modp = kfreebsd_set_module_var (MODINFO_SIZE, modp, elf_kernel_size); -+ /* Now the real modules. */ -+ modp = kfreebsd_set_modules(modp); -+ -+ /* Set the kernel end. */ -+ bi.bi_kernend = cur_addr = mem_align4k (((int) modp) + 1); -+ - if (mbi.flags & MB_INFO_AOUT_SYMS) - { - bi.bi_symtab = mbi.syms.a.addr; -@@ -970,8 +1148,9 @@ - #if 0 - else if (mbi.flags & MB_INFO_ELF_SHDR) - { -- /* FIXME: Should check if a symbol table exists and, if exists, -- pass the table to BI. */ -+ bi.bi_symtab = mbi.syms.e.addr; -+ bi.bi_esymtab = mbi.syms.e.addr -+ + mbi.syms.e.size * mbi.syms.e.num * mbi.syms.e.shndx; - } - #endif - else -diff -Naur grub-0.97.orig/stage2/builtins.c grub-0.97/stage2/builtins.c ---- grub-0.97.orig/stage2/builtins.c 2005-02-15 13:58:23.000000000 -0800 -+++ grub-0.97/stage2/builtins.c 2006-07-04 00:01:50.000000000 -0700 -@@ -28,6 +28,10 @@ - #include - #include - -+#ifdef SUPPORT_GRAPHICS -+# include -+#endif -+ - #ifdef SUPPORT_NETBOOT - # define GRUB 1 - # include -@@ -82,6 +86,10 @@ - inside other functions. */ - static int configfile_func (char *arg, int flags); - -+static int savedefault_helper (char *arg, int flags); -+ -+static int savedefault_shell (char *arg, int flags); -+ - /* Initialize the data for builtins. */ - void - init_builtins (void) -@@ -237,12 +245,22 @@ - static int - boot_func (char *arg, int flags) - { -+ struct term_entry *prev_term = current_term; - /* Clear the int15 handler if we can boot the kernel successfully. - This assumes that the boot code never fails only if KERNEL_TYPE is - not KERNEL_TYPE_NONE. Is this assumption is bad? */ - if (kernel_type != KERNEL_TYPE_NONE) - unset_int15_handler (); - -+ /* if our terminal needed initialization, we should shut it down -+ * before booting the kernel, but we want to save what it was so -+ * we can come back if needed */ -+ if (current_term->shutdown) -+ { -+ current_term->shutdown(); -+ current_term = term_table; /* assumption: console is first */ -+ } -+ - #ifdef SUPPORT_NETBOOT - /* Shut down the networking. */ - cleanup_net (); -@@ -306,6 +324,13 @@ - return 1; - } - -+ /* if we get back here, we should go back to what our term was before */ -+ current_term = prev_term; -+ if (current_term->startup) -+ /* if our terminal fails to initialize, fall back to console since -+ * it should always work */ -+ if (current_term->startup() == 0) -+ current_term = term_table; /* we know that console is first */ - return 0; - } - -@@ -852,6 +877,251 @@ - }; - #endif /* SUPPORT_NETBOOT */ - -+#ifdef SUPPORT_GRAPHICS -+ -+static int splashimage_func(char *arg, int flags) { -+ int i; -+ -+ /* filename can only be 256 characters due to our buffer size */ -+ if (grub_strlen(arg) > 256) { -+ grub_printf("Splash image filename too large\n"); -+ grub_printf("Press any key to continue..."); -+ getkey(); -+ return 1; -+ } -+ -+ /* get rid of TERM_NEED_INIT from the graphics terminal. */ -+ for (i = 0; term_table[i].name; i++) { -+ if (grub_strcmp (term_table[i].name, "graphics") == 0) { -+ term_table[i].flags &= ~TERM_NEED_INIT; -+ break; -+ } -+ } -+ -+ graphics_set_splash(arg); -+ -+ if (flags == BUILTIN_CMDLINE && graphics_inited) { -+ graphics_end(); -+ if (graphics_init() == 0) { -+ /* Fallback to default term */ -+ current_term = term_table; -+ max_lines = current_term->max_lines; -+ if (current_term->cls) -+ current_term->cls(); -+ grub_printf("Failed to set splash image and/or graphics mode\n"); -+ return 1; -+ } -+ graphics_cls(); -+ } -+ -+ if (flags == BUILTIN_MENU) -+ current_term = term_table + i; -+ -+ return 0; -+} -+ -+static struct builtin builtin_splashimage = -+{ -+ "splashimage", -+ splashimage_func, -+ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_HELP_LIST, -+ "splashimage FILE", -+ "Load FILE as the background image when in graphics mode." -+}; -+ -+ -+/* shade */ -+static int -+shade_func(char *arg, int flags) -+{ -+ int new_shade; -+ -+ if (!arg || safe_parse_maxint(&arg, &new_shade) == 0) -+ return (1); -+ -+ if (shade != new_shade) { -+ shade = new_shade; -+ if (flags == BUILTIN_CMDLINE && graphics_inited) { -+ graphics_end(); -+ graphics_init(); -+ graphics_cls(); -+ } -+ } -+ -+ return 0; -+} -+ -+static struct builtin builtin_shade = -+{ -+ "shade", -+ shade_func, -+ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_HELP_LIST, -+ "shade INTEGER", -+ "If set to 0, disables the use of shaded text, else enables it." -+}; -+ -+ -+/* foreground */ -+static int -+foreground_func(char *arg, int flags) -+{ -+ if (grub_strlen(arg) == 6) { -+ int r = ((hex(arg[0]) << 4) | hex(arg[1])) >> 2; -+ int g = ((hex(arg[2]) << 4) | hex(arg[3])) >> 2; -+ int b = ((hex(arg[4]) << 4) | hex(arg[5])) >> 2; -+ -+ foreground = (r << 16) | (g << 8) | b; -+ if (graphics_inited) -+ graphics_set_palette(15, r, g, b); -+ -+ return 0; -+ } -+ -+ return 1; -+} -+ -+static struct builtin builtin_foreground = -+{ -+ "foreground", -+ foreground_func, -+ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_HELP_LIST, -+ "foreground RRGGBB", -+ "Sets the foreground color when in graphics mode." -+ "RR is red, GG is green, and BB blue. Numbers must be in hexadecimal." -+}; -+ -+ -+/* background */ -+static int -+background_func(char *arg, int flags) -+{ -+ if (grub_strlen(arg) == 6) { -+ int r = ((hex(arg[0]) << 4) | hex(arg[1])) >> 2; -+ int g = ((hex(arg[2]) << 4) | hex(arg[3])) >> 2; -+ int b = ((hex(arg[4]) << 4) | hex(arg[5])) >> 2; -+ -+ background = (r << 16) | (g << 8) | b; -+ if (graphics_inited) -+ graphics_set_palette(0, r, g, b); -+ return 0; -+ } -+ -+ return 1; -+} -+ -+static struct builtin builtin_background = -+{ -+ "background", -+ background_func, -+ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_HELP_LIST, -+ "background RRGGBB", -+ "Sets the background color when in graphics mode." -+ "RR is red, GG is green, and BB blue. Numbers must be in hexadecimal." -+}; -+ -+ -+/* border */ -+static int -+border_func(char *arg, int flags) -+{ -+ if (grub_strlen(arg) == 6) { -+ int r = ((hex(arg[0]) << 4) | hex(arg[1])) >> 2; -+ int g = ((hex(arg[2]) << 4) | hex(arg[3])) >> 2; -+ int b = ((hex(arg[4]) << 4) | hex(arg[5])) >> 2; -+ -+ window_border = (r << 16) | (g << 8) | b; -+ if (graphics_inited) -+ graphics_set_palette(0x11, r, g, b); -+ -+ return 0; -+ } -+ -+ return 1; -+} -+ -+static struct builtin builtin_border = -+{ -+ "border", -+ border_func, -+ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_HELP_LIST, -+ "border RRGGBB", -+ "Sets the border video color when in graphics mode." -+ "RR is red, GG is green, and BB blue. Numbers must be in hexadecimal." -+}; -+ -+ -+/* viewport */ -+static int -+viewport_func (char *arg, int flags) -+{ -+ int i; -+ int x0 = 0, y0 = 0, x1 = 80, y1 = 30; -+ int *pos[4] = { &x0, &y0, &x1, &y1 }; -+ -+ if (!arg) -+ return (1); -+ for (i = 0; i < 4; i++) { -+ if (!*arg) -+ return (1); -+ while (*arg && (*arg == ' ' || *arg == '\t')) -+ ++arg; -+ if (!safe_parse_maxint(&arg, pos[i])) -+ return (1); -+ while (*arg && (*arg != ' ' && *arg != '\t')) -+ ++arg; -+ } -+ -+ /* minimum size is 65 colums and 16 rows */ -+ if (x0 > x1 - 66 || y0 > y1 - 16 || x0 < 0 || y0 < 0 || x1 > 80 || y1 > 30) -+ return 1; -+ -+ view_x0 = x0; -+ view_y0 = y0; -+ view_x1 = x1; -+ view_y1 = y1; -+ -+ if (flags == BUILTIN_CMDLINE && graphics_inited) { -+ graphics_end(); -+ graphics_init(); -+ graphics_cls(); -+ } -+ -+ return 0; -+} -+ -+static struct builtin builtin_viewport = -+{ -+ "viewport", -+ viewport_func, -+ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_HELP_LIST, -+ "viewport x0 y0 x1 y1", -+ "Changes grub internals to output text in the window defined by" -+ " four parameters. The x and y parameters are 0 based. This option" -+ " only works with the graphics interface." -+}; -+ -+#endif /* SUPPORT_GRAPHICS */ -+ -+ -+/* clear */ -+static int -+clear_func() -+{ -+ if (current_term->cls) -+ current_term->cls(); -+ -+ return 0; -+} -+ -+static struct builtin builtin_clear = -+{ -+ "clear", -+ clear_func, -+ BUILTIN_CMDLINE | BUILTIN_HELP_LIST, -+ "clear", -+ "Clear the screen" -+}; -+ - - /* displayapm */ - static int -@@ -1454,14 +1724,20 @@ - - - /* help */ --#define MAX_SHORT_DOC_LEN 39 --#define MAX_LONG_DOC_LEN 66 -- - static int - help_func (char *arg, int flags) - { -- int all = 0; -- -+ int all = 0, max_short_doc_len, max_long_doc_len; -+ max_short_doc_len = 39; -+ max_long_doc_len = 66; -+#ifdef SUPPORT_GRAPHICS -+ if (grub_memcmp (current_term->name, "graphics", sizeof ("graphics") - 1) == 0) -+ { -+ max_short_doc_len = (view_x1 - view_x0 + 1) / 2 - 1; -+ max_long_doc_len = (view_x1 - view_x0) - 14; -+ } -+#endif -+ - if (grub_memcmp (arg, "--all", sizeof ("--all") - 1) == 0) - { - all = 1; -@@ -1491,13 +1767,13 @@ - - len = grub_strlen ((*builtin)->short_doc); - /* If the length of SHORT_DOC is too long, truncate it. */ -- if (len > MAX_SHORT_DOC_LEN - 1) -- len = MAX_SHORT_DOC_LEN - 1; -+ if (len > max_short_doc_len - 1) -+ len = max_short_doc_len - 1; - - for (i = 0; i < len; i++) - grub_putchar ((*builtin)->short_doc[i]); - -- for (; i < MAX_SHORT_DOC_LEN; i++) -+ for (; i < max_short_doc_len; i++) - grub_putchar (' '); - - if (! left) -@@ -1546,10 +1822,10 @@ - int i; - - /* If LEN is too long, fold DOC. */ -- if (len > MAX_LONG_DOC_LEN) -+ if (len > max_long_doc_len) - { - /* Fold this line at the position of a space. */ -- for (len = MAX_LONG_DOC_LEN; len > 0; len--) -+ for (len = max_long_doc_len; len > 0; len--) - if (doc[len - 1] == ' ') - break; - } -@@ -2323,6 +2599,25 @@ - "Probe I/O ports used for the drive DRIVE." - }; - -+/* print */ -+static int -+print_func (char *arg, int flags) -+{ -+ printf("%s\n", arg); -+ -+ return 0; -+} -+ -+static struct builtin builtin_print = -+{ -+ "print", -+ print_func, -+ BUILTIN_CMDLINE | BUILTIN_MENU | BUILTIN_NO_ECHO, -+ "print [MESSAGE ...]", -+ "Print MESSAGE." -+}; -+ -+ - - /* kernel */ - static int -@@ -3221,7 +3516,102 @@ - static int - savedefault_func (char *arg, int flags) - { --#if !defined(SUPPORT_DISKLESS) && !defined(GRUB_UTIL) -+#if !defined(SUPPORT_DISKLESS) -+ #if !defined(GRUB_UTIL) -+ savedefault_helper(arg, flags); -+ #else -+ savedefault_shell(arg, flags); -+ #endif -+#else /* !SUPPORT_DISKLESS */ -+ errnum = ERR_UNRECOGNIZED; -+ return 1; -+#endif /* !SUPPORT_DISKLESS */ -+} -+ -+#if !defined(SUPPORT_DISKLESS) && defined(GRUB_UTIL) -+/* savedefault_shell */ -+static int -+savedefault_shell(char *arg, int flags) -+ { -+ int once_only = 0; -+ int new_default; -+ int curr_default = -1; -+ int curr_prev_default = -1; -+ int new_prev_default = -1; -+ FILE *fp; -+ size_t bytes = 10; -+ char line[bytes]; -+ char *default_file = (char *) DEFAULT_FILE_BUF; -+ char buf[bytes]; -+ int i; -+ -+ while (1) -+ { -+ if (grub_memcmp ("--default=", arg, sizeof ("--default=") - 1) == 0) -+ { -+ char *p = arg + sizeof ("--default=") - 1; -+ if (! safe_parse_maxint (&p, &new_default)) -+ return 1; -+ arg = skip_to (0, arg); -+ } -+ else if (grub_memcmp ("--once", arg, sizeof ("--once") - 1) == 0) -+ { -+ once_only = 1; -+ arg = skip_to (0, arg); -+ } -+ else -+ break; -+ } -+ -+ *default_file = 0; -+ grub_strncat (default_file, config_file, DEFAULT_FILE_BUFLEN); -+ for (i = grub_strlen(default_file); i >= 0; i--) -+ if (default_file[i] == '/') -+ { -+ i++; -+ break; -+ } -+ default_file[i] = 0; -+ grub_strncat (default_file + i, "default", DEFAULT_FILE_BUFLEN - i); -+ -+ if(!(fp = fopen(default_file,"w"))) -+ { -+ errnum = ERR_READ; -+ goto fail; -+ } -+ -+ read(&line, -1); -+ -+ sscanf(line, "%d:%d", &curr_prev_default, &curr_default); -+ -+ if(curr_default != -1) -+ new_prev_default = curr_default; -+ else -+ { -+ if(curr_prev_default != -1) -+ new_prev_default = curr_prev_default; -+ else -+ new_prev_default = 0; -+ } -+ -+ if(once_only) -+ sprintf(buf, "%d:%d\n", new_prev_default, new_default); -+ else -+ sprintf(buf, "%d\n", new_default); -+ -+ fprintf(fp, buf); -+ -+fail: -+ fclose(fp); -+ return errnum; -+} -+#endif -+ -+/* savedefault_helper */ -+static int -+savedefault_helper (char *arg, int flags) -+{ -+#if !defined(SUPPORT_DISKLESS) - unsigned long tmp_drive = saved_drive; - unsigned long tmp_partition = saved_partition; - char *default_file = (char *) DEFAULT_FILE_BUF; -@@ -3300,19 +3690,23 @@ - disk_read_hook = 0; - grub_close (); - -- if (len != sizeof (buf)) -- { -- /* This is too small. Do not modify the file manually, please! */ -- errnum = ERR_READ; -- goto fail; -- } -- - if (sector_count > 2) - { - /* Is this possible?! Too fragmented! */ - errnum = ERR_FSYS_CORRUPT; - goto fail; - } -+ -+ char *tmp; -+ if((tmp = grub_strstr(buf, ":")) != NULL) -+ { -+ int f_len = grub_strlen(buf) - grub_strlen(tmp); -+ char *def; -+ int a; -+ for(a = 0; a < f_len; a++) -+ grub_memcpy(&def[a], &buf[a], sizeof(char)); -+ safe_parse_maxint (&def, &entryno); -+ } - - /* Set up a string to be written. */ - grub_memset (buf, '\n', sizeof (buf)); -@@ -3830,15 +4224,15 @@ - { - char tmp[16]; - grub_sprintf (tmp, ",%d", (partition >> 16) & 0xFF); -- grub_strncat (device, tmp, 256); -+ grub_strncat (device, tmp, sizeof (device)); - } - if ((partition & 0x00FF00) != 0x00FF00) - { - char tmp[16]; - grub_sprintf (tmp, ",%c", 'a' + ((partition >> 8) & 0xFF)); -- grub_strncat (device, tmp, 256); -+ grub_strncat (device, tmp, sizeof (device)); - } -- grub_strncat (device, ")", 256); -+ grub_strncat (device, ")", sizeof (device)); - } - - int embed_stage1_5 (char *stage1_5, int drive, int partition) -@@ -4085,7 +4479,7 @@ - }; - - --#if defined(SUPPORT_SERIAL) || defined(SUPPORT_HERCULES) -+#if defined(SUPPORT_SERIAL) || defined(SUPPORT_HERCULES) || defined(SUPPORT_GRAPHICS) - /* terminal */ - static int - terminal_func (char *arg, int flags) -@@ -4244,17 +4638,29 @@ - end: - current_term = term_table + default_term; - current_term->flags = term_flags; -- -+ - if (lines) - max_lines = lines; - else -- /* 24 would be a good default value. */ -- max_lines = 24; -- -+ max_lines = current_term->max_lines; -+ - /* If the interface is currently the command-line, - restart it to repaint the screen. */ -- if (current_term != prev_term && (flags & BUILTIN_CMDLINE)) -+ if ((current_term != prev_term) && (flags & BUILTIN_CMDLINE)){ -+ if (prev_term->shutdown) -+ prev_term->shutdown(); -+ if (current_term->startup) { -+ /* If startup fails, return to previous term */ -+ if (current_term->startup() == 0) { -+ current_term = prev_term; -+ max_lines = current_term->max_lines; -+ if (current_term->cls) { -+ current_term->cls(); -+ } -+ } -+ } - grub_longjmp (restart_cmdline_env, 0); -+ } - - return 0; - } -@@ -4264,7 +4670,7 @@ - "terminal", - terminal_func, - BUILTIN_MENU | BUILTIN_CMDLINE | BUILTIN_HELP_LIST, -- "terminal [--dumb] [--no-echo] [--no-edit] [--timeout=SECS] [--lines=LINES] [--silent] [console] [serial] [hercules]", -+ "terminal [--dumb] [--no-echo] [--no-edit] [--timeout=SECS] [--lines=LINES] [--silent] [console] [serial] [hercules] [graphics]", - "Select a terminal. When multiple terminals are specified, wait until" - " you push any key to continue. If both console and serial are specified," - " the terminal to which you input a key first will be selected. If no" -@@ -4276,7 +4682,7 @@ - " seconds. The option --lines specifies the maximum number of lines." - " The option --silent is used to suppress messages." - }; --#endif /* SUPPORT_SERIAL || SUPPORT_HERCULES */ -+#endif /* SUPPORT_SERIAL || SUPPORT_HERCULES || SUPPORT_GRAPHICS */ - - - #ifdef SUPPORT_SERIAL -@@ -4795,13 +5201,20 @@ - /* The table of builtin commands. Sorted in dictionary order. */ - struct builtin *builtin_table[] = - { -+#ifdef SUPPORT_GRAPHICS -+ &builtin_background, -+#endif - &builtin_blocklist, - &builtin_boot, - #ifdef SUPPORT_NETBOOT - &builtin_bootp, - #endif /* SUPPORT_NETBOOT */ -+#ifdef SUPPORT_GRAPHICS -+ &builtin_border, -+#endif - &builtin_cat, - &builtin_chainloader, -+ &builtin_clear, - &builtin_cmp, - &builtin_color, - &builtin_configfile, -@@ -4821,6 +5234,9 @@ - &builtin_embed, - &builtin_fallback, - &builtin_find, -+#ifdef SUPPORT_GRAPHICS -+ &builtin_foreground, -+#endif - &builtin_fstest, - &builtin_geometry, - &builtin_halt, -@@ -4848,6 +5264,7 @@ - &builtin_parttype, - &builtin_password, - &builtin_pause, -+ &builtin_print, - #ifdef GRUB_UTIL - &builtin_quit, - #endif /* GRUB_UTIL */ -@@ -4864,9 +5281,13 @@ - #endif /* SUPPORT_SERIAL */ - &builtin_setkey, - &builtin_setup, --#if defined(SUPPORT_SERIAL) || defined(SUPPORT_HERCULES) -+#ifdef SUPPORT_GRAPHICS -+ &builtin_shade, -+ &builtin_splashimage, -+#endif /* SUPPORT_GRAPHICS */ -+#if defined(SUPPORT_SERIAL) || defined(SUPPORT_HERCULES) || defined(SUPPORT_GRAPHICS) - &builtin_terminal, --#endif /* SUPPORT_SERIAL || SUPPORT_HERCULES */ -+#endif /* SUPPORT_SERIAL || SUPPORT_HERCULES || SUPPORT_GRAPHICS */ - #ifdef SUPPORT_SERIAL - &builtin_terminfo, - #endif /* SUPPORT_SERIAL */ -@@ -4880,5 +5301,8 @@ - &builtin_unhide, - &builtin_uppermem, - &builtin_vbeprobe, -+#ifdef SUPPORT_GRAPHICS -+ &builtin_viewport, -+#endif - 0 - }; -diff -Naur grub-0.97.orig/stage2/char_io.c grub-0.97/stage2/char_io.c ---- grub-0.97.orig/stage2/char_io.c 2005-02-01 12:51:23.000000000 -0800 -+++ grub-0.97/stage2/char_io.c 2006-07-03 23:59:27.000000000 -0700 -@@ -29,12 +29,17 @@ - # include - #endif - -+#ifdef SUPPORT_GRAPHICS -+# include -+#endif -+ - #ifndef STAGE1_5 - struct term_entry term_table[] = - { - { - "console", - 0, -+ 24, - console_putchar, - console_checkkey, - console_getkey, -@@ -43,13 +48,16 @@ - console_cls, - console_setcolorstate, - console_setcolor, -- console_setcursor -+ console_setcursor, -+ 0, -+ 0 - }, - #ifdef SUPPORT_SERIAL - { - "serial", - /* A serial device must be initialized. */ - TERM_NEED_INIT, -+ 24, - serial_putchar, - serial_checkkey, - serial_getkey, -@@ -58,6 +66,8 @@ - serial_cls, - serial_setcolorstate, - 0, -+ 0, -+ 0, - 0 - }, - #endif /* SUPPORT_SERIAL */ -@@ -65,6 +75,7 @@ - { - "hercules", - 0, -+ 24, - hercules_putchar, - console_checkkey, - console_getkey, -@@ -73,11 +84,30 @@ - hercules_cls, - hercules_setcolorstate, - hercules_setcolor, -- hercules_setcursor -+ hercules_setcursor, -+ 0, -+ 0 - }, - #endif /* SUPPORT_HERCULES */ -+#ifdef SUPPORT_GRAPHICS -+ { "graphics", -+ TERM_NEED_INIT, /* flags */ -+ 30, /* number of lines */ -+ graphics_putchar, /* putchar */ -+ console_checkkey, /* checkkey */ -+ console_getkey, /* getkey */ -+ graphics_getxy, /* getxy */ -+ graphics_gotoxy, /* gotoxy */ -+ graphics_cls, /* cls */ -+ graphics_setcolorstate, /* setcolorstate */ -+ graphics_setcolor, /* setcolor */ -+ graphics_setcursor, /* nocursor */ -+ graphics_init, /* initialize */ -+ graphics_end /* shutdown */ -+ }, -+#endif /* SUPPORT_GRAPHICS */ - /* This must be the last entry. */ -- { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } -+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } - }; - - /* This must be console. */ -@@ -305,9 +335,10 @@ - - /* XXX: These should be defined in shared.h, but I leave these here, - until this code is freezed. */ --#define CMDLINE_WIDTH 78 - #define CMDLINE_MARGIN 10 -- -+ -+ /* command-line limits */ -+ int cmdline_width = 78, col_start = 0; - int xpos, lpos, c, section; - /* The length of PROMPT. */ - int plen; -@@ -338,7 +369,7 @@ - - /* If the cursor is in the first section, display the first section - instead of the second. */ -- if (section == 1 && plen + lpos < CMDLINE_WIDTH) -+ if (section == 1 && plen + lpos < cmdline_width) - cl_refresh (1, 0); - else if (xpos - count < 1) - cl_refresh (1, 0); -@@ -354,7 +385,7 @@ - grub_putchar ('\b'); - } - else -- gotoxy (xpos, getxy () & 0xFF); -+ gotoxy (xpos + col_start, getxy () & 0xFF); - } - } - -@@ -364,7 +395,7 @@ - lpos += count; - - /* If the cursor goes outside, scroll the screen to the right. */ -- if (xpos + count >= CMDLINE_WIDTH) -+ if (xpos + count >= cmdline_width) - cl_refresh (1, 0); - else - { -@@ -383,7 +414,7 @@ - } - } - else -- gotoxy (xpos, getxy () & 0xFF); -+ gotoxy (xpos + col_start, getxy () & 0xFF); - } - } - -@@ -398,14 +429,14 @@ - if (full) - { - /* Recompute the section number. */ -- if (lpos + plen < CMDLINE_WIDTH) -+ if (lpos + plen < cmdline_width) - section = 0; - else -- section = ((lpos + plen - CMDLINE_WIDTH) -- / (CMDLINE_WIDTH - 1 - CMDLINE_MARGIN) + 1); -+ section = ((lpos + plen - cmdline_width) -+ / (cmdline_width - 1 - CMDLINE_MARGIN) + 1); - - /* From the start to the end. */ -- len = CMDLINE_WIDTH; -+ len = cmdline_width; - pos = 0; - grub_putchar ('\r'); - -@@ -445,8 +476,8 @@ - if (! full) - offset = xpos - 1; - -- start = ((section - 1) * (CMDLINE_WIDTH - 1 - CMDLINE_MARGIN) -- + CMDLINE_WIDTH - plen - CMDLINE_MARGIN); -+ start = ((section - 1) * (cmdline_width - 1 - CMDLINE_MARGIN) -+ + cmdline_width - plen - CMDLINE_MARGIN); - xpos = lpos + 1 - start; - start += offset; - } -@@ -471,7 +502,7 @@ - - /* If the cursor is at the last position, put `>' or a space, - depending on if there are more characters in BUF. */ -- if (pos == CMDLINE_WIDTH) -+ if (pos == cmdline_width) - { - if (start + len < llen) - grub_putchar ('>'); -@@ -488,7 +519,7 @@ - grub_putchar ('\b'); - } - else -- gotoxy (xpos, getxy () & 0xFF); -+ gotoxy (xpos + col_start, getxy () & 0xFF); - } - - /* Initialize the command-line. */ -@@ -518,10 +549,10 @@ - - llen += l; - lpos += l; -- if (xpos + l >= CMDLINE_WIDTH) -+ if (xpos + l >= cmdline_width) - cl_refresh (1, 0); -- else if (xpos + l + llen - lpos > CMDLINE_WIDTH) -- cl_refresh (0, CMDLINE_WIDTH - xpos); -+ else if (xpos + l + llen - lpos > cmdline_width) -+ cl_refresh (0, cmdline_width - xpos); - else - cl_refresh (0, l + llen - lpos); - } -@@ -533,12 +564,22 @@ - grub_memmove (buf + lpos, buf + lpos + count, llen - count + 1); - llen -= count; - -- if (xpos + llen + count - lpos > CMDLINE_WIDTH) -- cl_refresh (0, CMDLINE_WIDTH - xpos); -+ if (xpos + llen + count - lpos > cmdline_width) -+ cl_refresh (0, cmdline_width - xpos); - else - cl_refresh (0, llen + count - lpos); - } - -+ max_lines = current_term->max_lines; -+#ifdef SUPPORT_GRAPHICS -+ if (grub_memcmp (current_term->name, "graphics", sizeof ("graphics") - 1) == 0) -+ { -+ cmdline_width = (view_x1 - view_x0) - 2; -+ col_start = view_x0; -+ max_lines = view_y1 - view_y0; -+ } -+#endif -+ - plen = grub_strlen (prompt); - llen = grub_strlen (cmdline); - -@@ -1006,6 +1047,48 @@ - } - #endif /* ! STAGE1_5 */ - -+#ifndef STAGE1_5 -+/* Internal pager. */ -+int -+do_more (void) -+{ -+ if (count_lines >= 0) -+ { -+ count_lines++; -+ if (count_lines >= max_lines - 2) -+ { -+ int tmp; -+ -+ /* It's important to disable the feature temporarily, because -+ the following grub_printf call will print newlines. */ -+ count_lines = -1; -+ -+ grub_printf("\n"); -+ if (current_term->setcolorstate) -+ current_term->setcolorstate (COLOR_STATE_HIGHLIGHT); -+ -+ grub_printf ("[Hit return to continue]"); -+ -+ if (current_term->setcolorstate) -+ current_term->setcolorstate (COLOR_STATE_NORMAL); -+ -+ -+ do -+ { -+ tmp = ASCII_CHAR (getkey ()); -+ } -+ while (tmp != '\n' && tmp != '\r'); -+ grub_printf ("\r \r"); -+ -+ /* Restart to count lines. */ -+ count_lines = 0; -+ return 1; -+ } -+ } -+ return 0; -+} -+#endif -+ - /* Display an ASCII character. */ - void - grub_putchar (int c) -@@ -1034,38 +1117,11 @@ - - if (c == '\n') - { -+ int flag; - /* Internal `more'-like feature. */ -- if (count_lines >= 0) -- { -- count_lines++; -- if (count_lines >= max_lines - 2) -- { -- int tmp; -- -- /* It's important to disable the feature temporarily, because -- the following grub_printf call will print newlines. */ -- count_lines = -1; -- -- if (current_term->setcolorstate) -- current_term->setcolorstate (COLOR_STATE_HIGHLIGHT); -- -- grub_printf ("\n[Hit return to continue]"); -- -- if (current_term->setcolorstate) -- current_term->setcolorstate (COLOR_STATE_NORMAL); -- -- do -- { -- tmp = ASCII_CHAR (getkey ()); -- } -- while (tmp != '\n' && tmp != '\r'); -- grub_printf ("\r \r"); -- -- /* Restart to count lines. */ -- count_lines = 0; -- return; -- } -- } -+ flag = do_more (); -+ if (flag) -+ return; - } - - current_term->putchar (c); -@@ -1090,7 +1146,7 @@ - cls (void) - { - /* If the terminal is dumb, there is no way to clean the terminal. */ -- if (current_term->flags & TERM_DUMB) -+ if (current_term->flags & TERM_DUMB) - grub_putchar ('\n'); - else - current_term->cls (); -@@ -1175,13 +1231,13 @@ - #endif /* ! STAGE1_5 */ - - int --memcheck (int addr, int len) -+memcheck (unsigned long int addr, unsigned long int len) - { - #ifdef GRUB_UTIL -- auto int start_addr (void); -- auto int end_addr (void); -+ auto unsigned long int start_addr (void); -+ auto int unsigned long end_addr (void); - -- auto int start_addr (void) -+ auto unsigned long int start_addr (void) - { - int ret; - # if defined(HAVE_START_SYMBOL) -@@ -1192,7 +1248,7 @@ - return ret; - } - -- auto int end_addr (void) -+ auto unsigned long int end_addr (void) - { - int ret; - # if defined(HAVE_END_SYMBOL) -@@ -1217,6 +1273,16 @@ - return ! errnum; - } - -+void -+grub_memcpy(void *dest, const void *src, int len) -+{ -+ int i; -+ register char *d = (char*)dest, *s = (char*)src; -+ -+ for (i = 0; i < len; i++) -+ d[i] = s[i]; -+} -+ - void * - grub_memmove (void *to, const void *from, int len) - { -diff -Naur grub-0.97.orig/stage2/cmdline.c grub-0.97/stage2/cmdline.c ---- grub-0.97.orig/stage2/cmdline.c 2004-08-16 16:23:01.000000000 -0700 -+++ grub-0.97/stage2/cmdline.c 2006-07-03 23:58:41.000000000 -0700 -@@ -50,10 +50,11 @@ - void - print_cmdline_message (int forever) - { -- printf (" [ Minimal BASH-like line editing is supported. For the first word, TAB\n" -- " lists possible command completions. Anywhere else TAB lists the possible\n" -- " completions of a device/filename.%s ]\n", -- (forever ? "" : " ESC at any time exits.")); -+ grub_printf(" [ Minimal BASH-like line editing is supported. For\n" -+ " the first word, TAB lists possible command\n" -+ " completions. Anywhere else TAB lists the possible\n" -+ " completions of a device/filename.%s ]\n", -+ (forever ? "" : " ESC at any time\n exits.")); - } - - /* Find the builtin whose command name is COMMAND and return the -diff -Naur grub-0.97.orig/stage2/freebsd.h grub-0.97/stage2/freebsd.h ---- grub-0.97.orig/stage2/freebsd.h 2003-07-09 04:45:52.000000000 -0700 -+++ grub-0.97/stage2/freebsd.h 2006-07-03 23:59:36.000000000 -0700 -@@ -1,7 +1,7 @@ - - /* - * GRUB -- GRand Unified Bootloader -- * Copyright (C) 2001 Free Software Foundation, Inc. -+ * Copyright (C) 2001, 2004 Free Software Foundation, Inc. - * - * 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 -@@ -35,6 +35,10 @@ - #define RB_CDROM 0x2000 /* use cdrom as root */ - #define RB_GDB 0x8000 /* use GDB remote debugger instead of DDB */ - #define RB_MUTE 0x10000 /* Come up with the console muted */ -+#define RB_SELFTEST 0x20000 /* don't complete the boot; do selftest */ -+#define RB_RESERVED1 0x40000 /* reserved for internal use of boot blocks */ -+#define RB_RESERVED2 0x80000 /* reserved for internal use of boot blocks */ -+#define RB_PAUSE 0x100000 /* pause after each output line during probe */ - #define RB_MULTIPLE 0x20000000 /* Use multiple consoles */ - - #define RB_BOOTINFO 0x80000000 /* have `struct bootinfo *' arg */ -@@ -70,6 +74,9 @@ - - #define N_BIOS_GEOM 8 - -+typedef unsigned char u8_t; -+typedef unsigned int u32_t; -+ - /* - * A zero bootinfo field often means that there is no info available. - * Flags are used to indicate the validity of fields where zero is a -@@ -77,19 +84,33 @@ - */ - struct bootinfo - { -- unsigned int bi_version; -- unsigned char *bi_kernelname; -- struct nfs_diskless *bi_nfs_diskless; -+ u32_t bi_version; -+ u8_t *bi_kernelname; -+ u32_t bi_nfs_diskless; - /* End of fields that are always present. */ - #define bi_endcommon bi_n_bios_used -- unsigned int bi_n_bios_used; -- unsigned long bi_bios_geom[N_BIOS_GEOM]; -- unsigned int bi_size; -- unsigned char bi_memsizes_valid; -- unsigned char bi_bios_dev; -- unsigned char bi_pad[2]; -- unsigned long bi_basemem; -- unsigned long bi_extmem; -- unsigned long bi_symtab; -- unsigned long bi_esymtab; -+ u32_t bi_n_bios_used; -+ u32_t bi_bios_geom[N_BIOS_GEOM]; -+ u32_t bi_size; -+ u8_t bi_memsizes_valid; -+ u8_t bi_bios_dev; -+ u8_t bi_pad[2]; -+ u32_t bi_basemem; -+ u32_t bi_extmem; -+ u32_t bi_symtab; -+ u32_t bi_esymtab; -+ /* Items below only from advanced bootloader */ -+ u32_t bi_kernend; -+ u32_t bi_envp; -+ u32_t bi_modulep; - }; -+ -+#define MODINFO_END 0x0000 /* End of list */ -+#define MODINFO_NAME 0x0001 /* Name of module (string) */ -+#define MODINFO_TYPE 0x0002 /* Type of module (string) */ -+#define MODINFO_ADDR 0x0003 /* Loaded address */ -+#define MODINFO_SIZE 0x0004 /* Size of module */ -+#define MODINFO_EMPTY 0x0005 /* Has been deleted */ -+#define MODINFO_ARGS 0x0006 /* Parameters string */ -+#define MODINFO_METADATA 0x8000 /* Module-specfic */ -+ -diff -Naur grub-0.97.orig/stage2/graphics.c grub-0.97/stage2/graphics.c ---- grub-0.97.orig/stage2/graphics.c 1969-12-31 16:00:00.000000000 -0800 -+++ grub-0.97/stage2/graphics.c 2006-07-03 23:58:41.000000000 -0700 -@@ -0,0 +1,585 @@ -+/* -+ * graphics.c - graphics mode support for GRUB -+ * Implemented as a terminal type by Jeremy Katz based -+ * on a patch by Paulo César Pereira de Andrade -+ * Options and enhancements made by Herton Ronaldo Krzesinski -+ * -+ * -+ * GRUB -- GRand Unified Bootloader -+ * Copyright (C) 2001,2002 Red Hat, Inc. -+ * Portions copyright (C) 2000 Conectiva, Inc. -+ * -+ * 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 -+ * (at your option) 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. -+ */ -+ -+#ifdef SUPPORT_GRAPHICS -+ -+#include -+#include -+#include -+ -+int saved_videomode; -+unsigned char *font8x16; -+ -+int graphics_inited = 0; -+static char splashimage[256]; -+ -+int shade = 1, no_cursor = 0; -+ -+#define VSHADOW VSHADOW1 -+unsigned char VSHADOW1[38400]; -+unsigned char VSHADOW2[38400]; -+unsigned char VSHADOW4[38400]; -+unsigned char VSHADOW8[38400]; -+ -+/* define the default viewable area */ -+int view_x0 = 0; -+int view_y0 = 0; -+int view_x1 = 80; -+int view_y1 = 30; -+ -+/* text buffer has to be kept around so that we can write things as we -+ * scroll and the like */ -+unsigned short text[80 * 30]; -+ -+/* graphics options */ -+int foreground = (63 << 16) | (63 << 8) | (63), background = 0, window_border = 0; -+ -+/* current position */ -+static int fontx = 0; -+static int fonty = 0; -+ -+/* global state so that we don't try to recursively scroll or cursor */ -+static int no_scroll = 0; -+ -+/* color state */ -+static int graphics_standard_color = A_NORMAL; -+static int graphics_normal_color = A_NORMAL; -+static int graphics_highlight_color = A_REVERSE; -+static int graphics_current_color = A_NORMAL; -+static color_state graphics_color_state = COLOR_STATE_STANDARD; -+ -+static inline void outb(unsigned short port, unsigned char val) -+{ -+ __asm __volatile ("outb %0,%1"::"a" (val), "d" (port)); -+} -+ -+static void MapMask(int value) { -+ outb(0x3c4, 2); -+ outb(0x3c5, value); -+} -+ -+/* bit mask register */ -+static void BitMask(int value) { -+ outb(0x3ce, 8); -+ outb(0x3cf, value); -+} -+ -+/* move the graphics cursor location to col, row */ -+static void graphics_setxy(int col, int row) { -+ if (col >= view_x0 && col < view_x1) { -+ fontx = col; -+ cursorX = col << 3; -+ } -+ if (row >= view_y0 && row < view_y1) { -+ fonty = row; -+ cursorY = row << 4; -+ } -+} -+ -+/* scroll the screen */ -+static void graphics_scroll() { -+ int i, j, k; -+ -+ /* we don't want to scroll recursively... that would be bad */ -+ if (no_scroll) -+ return; -+ no_scroll = 1; -+ -+ /* disable pager temporarily */ -+ k = count_lines; -+ count_lines = -1; -+ -+ /* move everything up a line */ -+ for (j = view_y0 + 1; j < view_y1; j++) { -+ graphics_gotoxy(view_x0, j - 1); -+ for (i = view_x0; i < view_x1; i++) { -+ graphics_putchar(text[j * 80 + i]); -+ } -+ } -+ -+ /* last line should be blank */ -+ graphics_gotoxy(view_x0, view_y1 - 1); -+ for (i = view_x0; i < view_x1; i++) -+ graphics_putchar(' '); -+ graphics_setxy(view_x0, view_y1 - 1); -+ -+ count_lines = k; -+ -+ no_scroll = 0; -+} -+ -+/* Set the splash image */ -+void graphics_set_splash(char *splashfile) { -+ grub_strcpy(splashimage, splashfile); -+} -+ -+/* Get the current splash image */ -+char *graphics_get_splash(void) { -+ return splashimage; -+} -+ -+/* -+ * Initialize a vga16 graphics display with the palette based off of -+ * the image in splashimage. If the image doesn't exist, leave graphics -+ * mode. The mode initiated is 12h. From "Ralf Brown's Interrupt List": -+ * text/ text pixel pixel colors disply scrn system -+ * grph resol box resolution pages addr -+ * 12h G 80x30 8x16 640x480 16/256K . A000 VGA,ATI VIP -+ * G 80x30 8x16 640x480 16/64 . A000 ATI EGA Wonder -+ * G . . 640x480 16 . . UltraVision+256K EGA -+ */ -+int graphics_init() -+{ -+ if (!graphics_inited) { -+ saved_videomode = set_videomode(0x12); -+ if (get_videomode() != 0x12) { -+ set_videomode(saved_videomode); -+ return 0; -+ } -+ graphics_inited = 1; -+ } -+ else -+ return 1; -+ -+ font8x16 = (unsigned char*)graphics_get_font(); -+ -+ /* make sure that the highlight color is set correctly */ -+ graphics_highlight_color = ((graphics_normal_color >> 4) | -+ ((graphics_normal_color & 0xf) << 4)); -+ -+ graphics_cls(); -+ -+ if (!read_image(splashimage)) { -+ grub_printf("Failed to read splash image (%s)\n", splashimage); -+ grub_printf("Press any key to continue..."); -+ getkey(); -+ set_videomode(saved_videomode); -+ graphics_inited = 0; -+ return 0; -+ } -+ -+ set_int1c_handler(); -+ -+ return 1; -+} -+ -+/* Leave graphics mode */ -+void graphics_end(void) -+{ -+ if (graphics_inited) { -+ unset_int1c_handler(); -+ set_videomode(saved_videomode); -+ graphics_inited = 0; -+ no_cursor = 0; -+ } -+} -+ -+/* Print ch on the screen. Handle any needed scrolling or the like */ -+void graphics_putchar(int ch) { -+ ch &= 0xff; -+ -+ graphics_cursor(0); -+ -+ if (ch == '\n') { -+ if (fonty + 1 < view_y1) -+ graphics_setxy(fontx, fonty + 1); -+ else -+ graphics_scroll(); -+ graphics_cursor(1); -+ return; -+ } else if (ch == '\r') { -+ graphics_setxy(view_x0, fonty); -+ graphics_cursor(1); -+ return; -+ } -+ -+ graphics_cursor(0); -+ -+ text[fonty * 80 + fontx] = ch; -+ text[fonty * 80 + fontx] &= 0x00ff; -+ if (graphics_current_color & 0xf0) -+ text[fonty * 80 + fontx] |= 0x100; -+ -+ graphics_cursor(0); -+ -+ if ((fontx + 1) >= view_x1) { -+ graphics_setxy(view_x0, fonty); -+ if (fonty + 1 < view_y1) -+ graphics_setxy(view_x0, fonty + 1); -+ else -+ graphics_scroll(); -+ graphics_cursor(1); -+ do_more (); -+ graphics_cursor(0); -+ } else { -+ graphics_setxy(fontx + 1, fonty); -+ } -+ -+ graphics_cursor(1); -+} -+ -+/* get the current location of the cursor */ -+int graphics_getxy(void) { -+ return (fontx << 8) | fonty; -+} -+ -+void graphics_gotoxy(int x, int y) { -+ graphics_cursor(0); -+ -+ graphics_setxy(x, y); -+ -+ graphics_cursor(1); -+} -+ -+void graphics_cls(void) { -+ int i; -+ unsigned char *mem, *s1, *s2, *s4, *s8; -+ -+ graphics_cursor(0); -+ graphics_gotoxy(view_x0, view_y0); -+ -+ mem = (unsigned char*)VIDEOMEM; -+ s1 = (unsigned char*)VSHADOW1; -+ s2 = (unsigned char*)VSHADOW2; -+ s4 = (unsigned char*)VSHADOW4; -+ s8 = (unsigned char*)VSHADOW8; -+ -+ for (i = 0; i < 80 * 30; i++) -+ text[i] = ' '; -+ graphics_cursor(1); -+ -+ BitMask(0xff); -+ -+ /* plane 1 */ -+ MapMask(1); -+ grub_memcpy(mem, s1, 38400); -+ -+ /* plane 2 */ -+ MapMask(2); -+ grub_memcpy(mem, s2, 38400); -+ -+ /* plane 3 */ -+ MapMask(4); -+ grub_memcpy(mem, s4, 38400); -+ -+ /* plane 4 */ -+ MapMask(8); -+ grub_memcpy(mem, s8, 38400); -+ -+ MapMask(15); -+ -+ if (no_cursor) { -+ no_cursor = 0; -+ set_int1c_handler(); -+ } -+} -+ -+void graphics_setcolorstate (color_state state) { -+ switch (state) { -+ case COLOR_STATE_STANDARD: -+ graphics_current_color = graphics_standard_color; -+ break; -+ case COLOR_STATE_NORMAL: -+ graphics_current_color = graphics_normal_color; -+ break; -+ case COLOR_STATE_HIGHLIGHT: -+ graphics_current_color = graphics_highlight_color; -+ break; -+ default: -+ graphics_current_color = graphics_standard_color; -+ break; -+ } -+ -+ graphics_color_state = state; -+} -+ -+void graphics_setcolor (int normal_color, int highlight_color) { -+ graphics_normal_color = normal_color; -+ graphics_highlight_color = highlight_color; -+ -+ graphics_setcolorstate (graphics_color_state); -+} -+ -+int graphics_setcursor (int on) { -+ if (!no_cursor && !on) { -+ no_cursor = 1; -+ unset_int1c_handler(); -+ graphics_cursor(0); -+ } -+ else if(no_cursor && on) { -+ no_cursor = 0; -+ set_int1c_handler(); -+ graphics_cursor(1); -+ } -+ return 0; -+} -+ -+/* Read in the splashscreen image and set the palette up appropriately. -+ * Format of splashscreen is an xpm (can be gzipped) with 16 colors and -+ * 640x480. */ -+int read_image(char *s) -+{ -+ char buf[32], pal[16], c; -+ unsigned char base, mask, *s1, *s2, *s4, *s8; -+ unsigned i, len, idx, colors, x, y, width, height; -+ -+ if (!grub_open(s)) -+ return 0; -+ -+ /* read header */ -+ if (!grub_read((char*)&buf, 10) || grub_memcmp(buf, "/* XPM */\n", 10)) { -+ grub_close(); -+ return 0; -+ } -+ -+ /* parse info */ -+ while (grub_read(&c, 1)) { -+ if (c == '"') -+ break; -+ } -+ -+ while (grub_read(&c, 1) && (c == ' ' || c == '\t')) -+ ; -+ -+ i = 0; -+ width = c - '0'; -+ while (grub_read(&c, 1)) { -+ if (c >= '0' && c <= '9') -+ width = width * 10 + c - '0'; -+ else -+ break; -+ } -+ while (grub_read(&c, 1) && (c == ' ' || c == '\t')) -+ ; -+ -+ height = c - '0'; -+ while (grub_read(&c, 1)) { -+ if (c >= '0' && c <= '9') -+ height = height * 10 + c - '0'; -+ else -+ break; -+ } -+ while (grub_read(&c, 1) && (c == ' ' || c == '\t')) -+ ; -+ -+ colors = c - '0'; -+ while (grub_read(&c, 1)) { -+ if (c >= '0' && c <= '9') -+ colors = colors * 10 + c - '0'; -+ else -+ break; -+ } -+ -+ base = 0; -+ while (grub_read(&c, 1) && c != '"') -+ ; -+ -+ /* palette */ -+ for (i = 0, idx = 1; i < colors; i++) { -+ len = 0; -+ -+ while (grub_read(&c, 1) && c != '"') -+ ; -+ grub_read(&c, 1); /* char */ -+ base = c; -+ grub_read(buf, 4); /* \t c # */ -+ -+ while (grub_read(&c, 1) && c != '"') { -+ if (len < sizeof(buf)) -+ buf[len++] = c; -+ } -+ -+ if (len == 6 && idx < 15) { -+ int r = ((hex(buf[0]) << 4) | hex(buf[1])) >> 2; -+ int g = ((hex(buf[2]) << 4) | hex(buf[3])) >> 2; -+ int b = ((hex(buf[4]) << 4) | hex(buf[5])) >> 2; -+ -+ pal[idx] = base; -+ graphics_set_palette(idx, r, g, b); -+ ++idx; -+ } -+ } -+ -+ x = y = len = 0; -+ -+ s1 = (unsigned char*)VSHADOW1; -+ s2 = (unsigned char*)VSHADOW2; -+ s4 = (unsigned char*)VSHADOW4; -+ s8 = (unsigned char*)VSHADOW8; -+ -+ for (i = 0; i < 38400; i++) -+ s1[i] = s2[i] = s4[i] = s8[i] = 0; -+ -+ /* parse xpm data */ -+ while (y < height) { -+ while (1) { -+ if (!grub_read(&c, 1)) { -+ grub_close(); -+ return 0; -+ } -+ if (c == '"') -+ break; -+ } -+ -+ while (grub_read(&c, 1) && c != '"') { -+ for (i = 1; i < 15; i++) -+ if (pal[i] == c) { -+ c = i; -+ break; -+ } -+ -+ mask = 0x80 >> (x & 7); -+ if (c & 1) -+ s1[len + (x >> 3)] |= mask; -+ if (c & 2) -+ s2[len + (x >> 3)] |= mask; -+ if (c & 4) -+ s4[len + (x >> 3)] |= mask; -+ if (c & 8) -+ s8[len + (x >> 3)] |= mask; -+ -+ if (++x >= 640) { -+ x = 0; -+ -+ if (y < 480) -+ len += 80; -+ ++y; -+ } -+ } -+ } -+ -+ grub_close(); -+ -+ graphics_set_palette(0, (background >> 16), (background >> 8) & 63, -+ background & 63); -+ graphics_set_palette(15, (foreground >> 16), (foreground >> 8) & 63, -+ foreground & 63); -+ graphics_set_palette(0x11, (window_border >> 16), (window_border >> 8) & 63, -+ window_border & 63); -+ -+ return 1; -+} -+ -+/* Convert a character which is a hex digit to the appropriate integer */ -+int hex(int v) -+{ -+ if (v >= 'A' && v <= 'F') -+ return (v - 'A' + 10); -+ if (v >= 'a' && v <= 'f') -+ return (v - 'a' + 10); -+ return (v - '0'); -+} -+ -+void graphics_cursor(int set) { -+ unsigned char *pat, *mem, *ptr, chr[16 << 2]; -+ int i, ch, invert, offset; -+ -+ if (set && (no_cursor || no_scroll)) -+ return; -+ -+ offset = cursorY * 80 + fontx; -+ ch = text[fonty * 80 + fontx] & 0xff; -+ invert = (text[fonty * 80 + fontx] & 0xff00) != 0; -+ pat = font8x16 + (ch << 4); -+ -+ mem = (unsigned char*)VIDEOMEM + offset; -+ -+ if (!set) { -+ for (i = 0; i < 16; i++) { -+ unsigned char mask = pat[i]; -+ -+ if (!invert) { -+ chr[i ] = ((unsigned char*)VSHADOW1)[offset]; -+ chr[16 + i] = ((unsigned char*)VSHADOW2)[offset]; -+ chr[32 + i] = ((unsigned char*)VSHADOW4)[offset]; -+ chr[48 + i] = ((unsigned char*)VSHADOW8)[offset]; -+ -+ if (shade) { -+ if (ch == DISP_VERT || ch == DISP_LL || -+ ch == DISP_UR || ch == DISP_LR) { -+ unsigned char pmask = ~(pat[i] >> 1); -+ -+ chr[i ] &= pmask; -+ chr[16 + i] &= pmask; -+ chr[32 + i] &= pmask; -+ chr[48 + i] &= pmask; -+ } -+ if (i > 0 && ch != DISP_VERT) { -+ unsigned char pmask = ~(pat[i - 1] >> 1); -+ -+ chr[i ] &= pmask; -+ chr[16 + i] &= pmask; -+ chr[32 + i] &= pmask; -+ chr[48 + i] &= pmask; -+ if (ch == DISP_HORIZ || ch == DISP_UR || ch == DISP_LR) { -+ pmask = ~pat[i - 1]; -+ -+ chr[i ] &= pmask; -+ chr[16 + i] &= pmask; -+ chr[32 + i] &= pmask; -+ chr[48 + i] &= pmask; -+ } -+ } -+ } -+ chr[i ] |= mask; -+ chr[16 + i] |= mask; -+ chr[32 + i] |= mask; -+ chr[48 + i] |= mask; -+ -+ offset += 80; -+ } -+ else { -+ chr[i ] = mask; -+ chr[16 + i] = mask; -+ chr[32 + i] = mask; -+ chr[48 + i] = mask; -+ } -+ } -+ } -+ else { -+ MapMask(15); -+ ptr = mem; -+ for (i = 0; i < 16; i++, ptr += 80) { -+ cursorBuf[i] = pat[i]; -+ *ptr = ~pat[i]; -+ } -+ return; -+ } -+ -+ offset = 0; -+ for (i = 1; i < 16; i <<= 1, offset += 16) { -+ int j; -+ -+ MapMask(i); -+ ptr = mem; -+ for (j = 0; j < 16; j++, ptr += 80) -+ *ptr = chr[j + offset]; -+ } -+ -+ MapMask(15); -+} -+ -+#endif /* SUPPORT_GRAPHICS */ -diff -Naur grub-0.97.orig/stage2/graphics.h grub-0.97/stage2/graphics.h ---- grub-0.97.orig/stage2/graphics.h 1969-12-31 16:00:00.000000000 -0800 -+++ grub-0.97/stage2/graphics.h 2006-07-03 23:58:41.000000000 -0700 -@@ -0,0 +1,44 @@ -+/* graphics.h - graphics console interface */ -+/* -+ * GRUB -- GRand Unified Bootloader -+ * Copyright (C) 2002 Free Software Foundation, Inc. -+ * -+ * 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 -+ * (at your option) 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. -+ */ -+ -+#ifndef GRAPHICS_H -+#define GRAPHICS_H -+ -+/* magic constant */ -+#define VIDEOMEM 0xA0000 -+ -+/* function prototypes */ -+char *graphics_get_splash(void); -+ -+int read_image(char *s); -+void graphics_cursor(int set); -+ -+/* function prototypes for asm functions */ -+void * graphics_get_font(); -+void graphics_set_palette(int idx, int red, int green, int blue); -+void set_int1c_handler(); -+void unset_int1c_handler(); -+ -+extern short cursorX, cursorY; -+extern char cursorBuf[16]; -+extern int shade; -+extern int view_x0, view_y0, view_x1, view_y1; -+ -+#endif /* GRAPHICS_H */ -diff -Naur grub-0.97.orig/stage2/Makefile.am grub-0.97/stage2/Makefile.am ---- grub-0.97.orig/stage2/Makefile.am 2005-02-02 12:37:35.000000000 -0800 -+++ grub-0.97/stage2/Makefile.am 2006-07-03 23:58:41.000000000 -0700 -@@ -7,7 +7,7 @@ - fat.h filesys.h freebsd.h fs.h hercules.h i386-elf.h \ - imgact_aout.h iso9660.h jfs.h mb_header.h mb_info.h md5.h \ - nbi.h pc_slice.h serial.h shared.h smp-imps.h term.h \ -- terminfo.h tparm.h nbi.h ufs2.h vstafs.h xfs.h -+ terminfo.h tparm.h nbi.h ufs2.h vstafs.h xfs.h graphics.h - EXTRA_DIST = setjmp.S apm.S $(noinst_SCRIPTS) - - # For . -@@ -19,7 +19,7 @@ - disk_io.c fsys_ext2fs.c fsys_fat.c fsys_ffs.c fsys_iso9660.c \ - fsys_jfs.c fsys_minix.c fsys_reiserfs.c fsys_ufs2.c \ - fsys_vstafs.c fsys_xfs.c gunzip.c md5.c serial.c stage2.c \ -- terminfo.c tparm.c -+ terminfo.c tparm.c graphics.c - libgrub_a_CFLAGS = $(GRUB_CFLAGS) -I$(top_srcdir)/lib \ - -DGRUB_UTIL=1 -DFSYS_EXT2FS=1 -DFSYS_FAT=1 -DFSYS_FFS=1 \ - -DFSYS_ISO9660=1 -DFSYS_JFS=1 -DFSYS_MINIX=1 -DFSYS_REISERFS=1 \ -@@ -79,8 +79,14 @@ - HERCULES_FLAGS = - endif - -+if GRAPHICS_SUPPORT -+GRAPHICS_FLAGS = -DSUPPORT_GRAPHICS=1 -+else -+GRAPHICS_FLAGS = -+endif -+ - STAGE2_COMPILE = $(STAGE2_CFLAGS) -fno-builtin -nostdinc \ -- $(NETBOOT_FLAGS) $(SERIAL_FLAGS) $(HERCULES_FLAGS) -+ $(NETBOOT_FLAGS) $(SERIAL_FLAGS) $(HERCULES_FLAGS) $(GRAPHICS_FLAGS) - - STAGE1_5_LINK = -nostdlib -Wl,-N -Wl,-Ttext -Wl,2000 - STAGE1_5_COMPILE = $(STAGE2_COMPILE) -DNO_DECOMPRESSION=1 -DSTAGE1_5=1 -@@ -90,7 +96,8 @@ - cmdline.c common.c console.c disk_io.c fsys_ext2fs.c \ - fsys_fat.c fsys_ffs.c fsys_iso9660.c fsys_jfs.c fsys_minix.c \ - fsys_reiserfs.c fsys_ufs2.c fsys_vstafs.c fsys_xfs.c gunzip.c \ -- hercules.c md5.c serial.c smp-imps.c stage2.c terminfo.c tparm.c -+ hercules.c md5.c serial.c smp-imps.c stage2.c terminfo.c tparm.c \ -+ graphics.c - pre_stage2_exec_CFLAGS = $(STAGE2_COMPILE) $(FSYS_CFLAGS) - pre_stage2_exec_CCASFLAGS = $(STAGE2_COMPILE) $(FSYS_CFLAGS) - pre_stage2_exec_LDFLAGS = $(PRE_STAGE2_LINK) -diff -Naur grub-0.97.orig/stage2/shared.h grub-0.97/stage2/shared.h ---- grub-0.97.orig/stage2/shared.h 2004-06-19 09:40:09.000000000 -0700 -+++ grub-0.97/stage2/shared.h 2006-07-04 00:01:50.000000000 -0700 -@@ -499,7 +499,11 @@ - unsigned char linear_reserved_field_position; - unsigned long max_pixel_clock; - -- unsigned char reserved3[189]; -+ /* Reserved field to make structure to be 256 bytes long, VESA BIOS -+ Extension 3.0 Specification says to reserve 189 bytes here but -+ that doesn't make structure to be 256 bytes. So additional one is -+ added here. */ -+ unsigned char reserved3[189 + 1]; - } __attribute__ ((packed)); - - -@@ -792,6 +796,11 @@ - /* Set the cursor position. */ - void gotoxy (int x, int y); - -+/* Internal pager -+ Returns 1 = if pager was used -+ 0 = if pager wasn't used */ -+int do_more (void); -+ - /* Displays an ASCII character. IBM displays will translate some - characters to special graphical ones (see the DISP_* constants). */ - void grub_putchar (int c); -@@ -871,6 +880,7 @@ - int grub_tolower (int c); - int grub_isspace (int c); - int grub_strncat (char *s1, const char *s2, int n); -+void grub_memcpy(void *dest, const void *src, int len); - void *grub_memmove (void *to, const void *from, int len); - void *grub_memset (void *start, int c, int len); - int grub_strncat (char *s1, const char *s2, int n); -@@ -911,7 +921,7 @@ - int nul_terminate (char *str); - int get_based_digit (int c, int base); - int safe_parse_maxint (char **str_ptr, int *myint_ptr); --int memcheck (int start, int len); -+int memcheck (unsigned long int start, unsigned long int len); - void grub_putstr (const char *str); - - #ifndef NO_DECOMPRESSION -diff -Naur grub-0.97.orig/stage2/stage2.c grub-0.97/stage2/stage2.c ---- grub-0.97.orig/stage2/stage2.c 2005-03-19 09:51:57.000000000 -0800 -+++ grub-0.97/stage2/stage2.c 2006-07-04 00:01:50.000000000 -0700 -@@ -20,6 +20,12 @@ - #include - #include - -+#ifdef SUPPORT_GRAPHICS -+# include -+#endif -+ -+int col_start, col_end, row_start, box_size; -+ - grub_jmp_buf restart_env; - - #if defined(PRESET_MENU_STRING) || defined(SUPPORT_DISKLESS) -@@ -105,13 +111,13 @@ - if (highlight && current_term->setcolorstate) - current_term->setcolorstate (COLOR_STATE_HIGHLIGHT); - -- gotoxy (2, y); -+ gotoxy (2 + col_start, y); - grub_putchar (' '); -- for (x = 3; x < 75; x++) -+ for (x = 3 + col_start; x < (col_end - 5); x++) - { -- if (*entry && x <= 72) -+ if (*entry && x <= (col_end - 8)) - { -- if (x == 72) -+ if (x == (col_end - 8)) - grub_putchar (DISP_RIGHT); - else - grub_putchar (*entry++); -@@ -119,7 +125,7 @@ - else - grub_putchar (' '); - } -- gotoxy (74, y); -+ gotoxy ((col_end - 6), y); - - if (current_term->setcolorstate) - current_term->setcolorstate (COLOR_STATE_STANDARD); -@@ -131,7 +137,7 @@ - { - int i; - -- gotoxy (77, y + 1); -+ gotoxy ((col_end - 3), y + 1); - - if (first) - grub_putchar (DISP_UP); -@@ -151,14 +157,14 @@ - menu_entries++; - } - -- gotoxy (77, y + size); -+ gotoxy ((col_end - 3), y + size); - - if (*menu_entries) - grub_putchar (DISP_DOWN); - else - grub_putchar (' '); - -- gotoxy (74, y + entryno + 1); -+ gotoxy ((col_end - 6), y + entryno + 1); - } - - static void -@@ -196,30 +202,30 @@ - if (current_term->setcolorstate) - current_term->setcolorstate (COLOR_STATE_NORMAL); - -- gotoxy (1, y); -+ gotoxy (1 + col_start, y); - - grub_putchar (DISP_UL); -- for (i = 0; i < 73; i++) -+ for (i = col_start; i < (col_end - 7); i++) - grub_putchar (DISP_HORIZ); - grub_putchar (DISP_UR); - - i = 1; - while (1) - { -- gotoxy (1, y + i); -+ gotoxy (1 + col_start, y + i); - - if (i > size) - break; - - grub_putchar (DISP_VERT); -- gotoxy (75, y + i); -+ gotoxy ((col_end - 5), y + i); - grub_putchar (DISP_VERT); - - i++; - } - - grub_putchar (DISP_LL); -- for (i = 0; i < 73; i++) -+ for (i = col_start; i < (col_end - 7); i++) - grub_putchar (DISP_HORIZ); - grub_putchar (DISP_LR); - -@@ -233,6 +239,7 @@ - { - int c, time1, time2 = -1, first_entry = 0; - char *cur_entry = 0; -+ struct term_entry *prev_term = NULL; - - /* - * Main loop for menu UI. -@@ -250,6 +257,22 @@ - } - } - -+ col_start = 0; -+ col_end = 80; -+ row_start = 0; -+ box_size = 12; -+ /* if we're using viewport we need to make sure to setup -+ coordinates correctly. */ -+#ifdef SUPPORT_GRAPHICS -+ if (grub_memcmp (current_term->name, "graphics", sizeof ("graphics") - 1) == 0) -+ { -+ col_start = view_x0; -+ col_end = view_x1; -+ row_start = view_y0; -+ box_size = (view_y1 - view_y0) - 13; -+ } -+#endif -+ - /* If the timeout was expired or wasn't set, force to show the menu - interface. */ - if (grub_timeout < 0) -@@ -302,36 +325,36 @@ - if (current_term->flags & TERM_DUMB) - print_entries_raw (num_entries, first_entry, menu_entries); - else -- print_border (3, 12); -+ print_border (3 + row_start, box_size); - - grub_printf ("\n\ -- Use the %c and %c keys to select which entry is highlighted.\n", -+ Use the %c and %c keys to select which entry is highlighted.\n", - DISP_UP, DISP_DOWN); - - if (! auth && password) - { - printf ("\ -- Press enter to boot the selected OS or \'p\' to enter a\n\ -- password to unlock the next set of features."); -+ Press enter to boot the selected OS or \'p\' to enter a\n\ -+ password to unlock the next set of features."); - } - else - { - if (config_entries) - printf ("\ -- Press enter to boot the selected OS, \'e\' to edit the\n\ -- commands before booting, or \'c\' for a command-line."); -+ Press enter to boot the selected OS, \'e\' to edit the\n\ -+ commands before booting, or \'c\' for a command-line."); - else - printf ("\ -- Press \'b\' to boot, \'e\' to edit the selected command in the\n\ -- boot sequence, \'c\' for a command-line, \'o\' to open a new line\n\ -- after (\'O\' for before) the selected line, \'d\' to remove the\n\ -- selected line, or escape to go back to the main menu."); -+ Press \'b\' to boot, \'e\' to edit the selected command in the\n\ -+ boot sequence, \'c\' for a command-line, \'o\' to open a new line\n\ -+ after (\'O\' for before) the selected line, \'d\' to remove the\n\ -+ selected line, or escape to go back to the main menu."); - } - - if (current_term->flags & TERM_DUMB) - grub_printf ("\n\nThe selected entry is %d ", entryno); - else -- print_entries (3, 12, first_entry, entryno, menu_entries); -+ print_entries (3 + row_start, box_size, first_entry, entryno, menu_entries); - } - - /* XX using RT clock now, need to initialize value */ -@@ -358,10 +381,10 @@ - entryno, grub_timeout); - else - { -- gotoxy (3, 22); -- grub_printf ("The highlighted entry will be booted automatically in %d seconds. ", -+ gotoxy (3 + col_start, 10 + box_size + row_start); -+ grub_printf (" The highlighted entry will be booted automatically in %d seconds. ", - grub_timeout); -- gotoxy (74, 4 + entryno); -+ gotoxy ((col_end - 6), 4 + entryno + row_start); - } - - grub_timeout--; -@@ -387,12 +410,12 @@ - if (current_term->flags & TERM_DUMB) - grub_putchar ('\r'); - else -- gotoxy (3, 22); -+ gotoxy (3 + col_start, 10 + box_size + row_start); - printf (" "); - grub_timeout = -1; - fallback_entryno = -1; - if (! (current_term->flags & TERM_DUMB)) -- gotoxy (74, 4 + entryno); -+ gotoxy ((col_end - 6), 4 + entryno + row_start); - } - - /* We told them above (at least in SUPPORT_SERIAL) to use -@@ -408,12 +431,12 @@ - { - if (entryno > 0) - { -- print_entry (4 + entryno, 0, -+ print_entry (4 + entryno + row_start, 0, - get_entry (menu_entries, - first_entry + entryno, - 0)); - entryno--; -- print_entry (4 + entryno, 1, -+ print_entry (4 + entryno + row_start, 1, - get_entry (menu_entries, - first_entry + entryno, - 0)); -@@ -421,7 +444,7 @@ - else if (first_entry > 0) - { - first_entry--; -- print_entries (3, 12, first_entry, entryno, -+ print_entries (3 + row_start, box_size, first_entry, entryno, - menu_entries); - } - } -@@ -433,29 +456,29 @@ - entryno++; - else - { -- if (entryno < 11) -+ if (entryno < (box_size - 1)) - { -- print_entry (4 + entryno, 0, -+ print_entry (4 + entryno + row_start, 0, - get_entry (menu_entries, - first_entry + entryno, - 0)); - entryno++; -- print_entry (4 + entryno, 1, -+ print_entry (4 + entryno + row_start, 1, - get_entry (menu_entries, - first_entry + entryno, - 0)); - } -- else if (num_entries > 12 + first_entry) -+ else if (num_entries > box_size + first_entry) - { - first_entry++; -- print_entries (3, 12, first_entry, entryno, menu_entries); -+ print_entries (3 + row_start, box_size, first_entry, entryno, menu_entries); - } - } - } - else if (c == 7) - { - /* Page Up */ -- first_entry -= 12; -+ first_entry -= box_size; - if (first_entry < 0) - { - entryno += first_entry; -@@ -463,20 +486,20 @@ - if (entryno < 0) - entryno = 0; - } -- print_entries (3, 12, first_entry, entryno, menu_entries); -+ print_entries (3 + row_start, box_size, first_entry, entryno, menu_entries); - } - else if (c == 3) - { - /* Page Down */ -- first_entry += 12; -+ first_entry += box_size; - if (first_entry + entryno + 1 >= num_entries) - { -- first_entry = num_entries - 12; -+ first_entry = num_entries - box_size; - if (first_entry < 0) - first_entry = 0; - entryno = num_entries - first_entry - 1; - } -- print_entries (3, 12, first_entry, entryno, menu_entries); -+ print_entries (3 + row_start, box_size, first_entry, entryno, menu_entries); - } - - if (config_entries) -@@ -489,7 +512,7 @@ - if ((c == 'd') || (c == 'o') || (c == 'O')) - { - if (! (current_term->flags & TERM_DUMB)) -- print_entry (4 + entryno, 0, -+ print_entry (4 + entryno + row_start, 0, - get_entry (menu_entries, - first_entry + entryno, - 0)); -@@ -537,7 +560,7 @@ - - if (entryno >= num_entries) - entryno--; -- if (first_entry && num_entries < 12 + first_entry) -+ if (first_entry && num_entries < box_size + first_entry) - first_entry--; - } - -@@ -549,7 +572,7 @@ - grub_printf ("\n"); - } - else -- print_entries (3, 12, first_entry, entryno, menu_entries); -+ print_entries (3 + row_start, box_size, first_entry, entryno, menu_entries); - } - - cur_entry = menu_entries; -@@ -570,7 +593,7 @@ - if (current_term->flags & TERM_DUMB) - grub_printf ("\r "); - else -- gotoxy (1, 21); -+ gotoxy (1 + col_start, 9 + box_size + row_start); - - /* Wipe out the previously entered password */ - grub_memset (entered, 0, sizeof (entered)); -@@ -651,7 +674,10 @@ - *(new_heap++) = 0; - - if (config_entries) -- run_menu (heap, NULL, new_num_entries, new_heap, 0); -+ { -+ current_entryno = first_entry + entryno; -+ run_menu (heap, NULL, new_num_entries, new_heap, 0); -+ } - else - { - cls (); -@@ -714,6 +740,15 @@ - - cls (); - setcursor (1); -+ /* if our terminal needed initialization, we should shut it down -+ * before booting the kernel, but we want to save what it was so -+ * we can come back if needed */ -+ prev_term = current_term; -+ if (current_term->shutdown) -+ { -+ current_term->shutdown(); -+ current_term = term_table; /* assumption: console is first */ -+ } - - while (1) - { -@@ -727,7 +762,8 @@ - cur_entry = get_entry (config_entries, first_entry + entryno, 1); - - /* Set CURRENT_ENTRYNO for the command "savedefault". */ -- current_entryno = first_entry + entryno; -+ if (config_entries) -+ current_entryno = first_entry + entryno; - - if (run_script (cur_entry, heap)) - { -@@ -748,6 +784,13 @@ - break; - } - -+ /* if we get back here, we should go back to what our term was before */ -+ current_term = prev_term; -+ if (current_term->startup) -+ /* if our terminal fails to initialize, fall back to console since -+ * it should always work */ -+ if (current_term->startup() == 0) -+ current_term = term_table; /* we know that console is first */ - show_menu = 1; - goto restart; - } -@@ -891,8 +934,18 @@ - len = grub_read (buf, sizeof (buf)); - if (len > 0) - { -+ char *tmp; -+ char *def; - buf[sizeof (buf) - 1] = 0; -- safe_parse_maxint (&p, &saved_entryno); -+ -+ if((tmp = grub_strstr(p, ":")) != NULL) -+ { -+ *tmp++; -+ grub_memcpy(&def, &tmp, sizeof(p)); -+ }else -+ grub_memcpy(&def, &p, sizeof(p)); -+ -+ safe_parse_maxint (&def, &saved_entryno); - } - - grub_close (); -@@ -1050,6 +1103,16 @@ - while (is_preset); - } - -+ /* go ahead and make sure the terminal is setup */ -+ if (current_term->startup) -+ { -+ /* If initialization fails, go back to default terminal */ -+ if (current_term->startup() == 0) -+ { -+ current_term = term_table; -+ } -+ } -+ - if (! num_entries) - { - /* If no acceptable config file, goto command-line, starting -diff -Naur grub-0.97.orig/stage2/term.h grub-0.97/stage2/term.h ---- grub-0.97.orig/stage2/term.h 2003-07-09 04:45:53.000000000 -0700 -+++ grub-0.97/stage2/term.h 2006-07-03 23:58:41.000000000 -0700 -@@ -60,6 +60,8 @@ - const char *name; - /* The feature flags defined above. */ - unsigned long flags; -+ /* Default for maximum number of lines if not specified */ -+ unsigned short max_lines; - /* Put a character. */ - void (*putchar) (int c); - /* Check if any input character is available. */ -@@ -79,6 +81,10 @@ - void (*setcolor) (int normal_color, int highlight_color); - /* Turn on/off the cursor. */ - int (*setcursor) (int on); -+ /* function to start a terminal */ -+ int (*startup) (void); -+ /* function to use to shutdown a terminal */ -+ void (*shutdown) (void); - }; - - /* This lists up available terminals. */ -@@ -124,4 +130,24 @@ - int hercules_setcursor (int on); - #endif - -+#ifdef SUPPORT_GRAPHICS -+extern int foreground, background, window_border, graphics_inited, saved_videomode; -+ -+void graphics_set_splash(char *splashfile); -+int set_videomode(int mode); -+int get_videomode(void); -+void graphics_putchar (int c); -+int graphics_getxy(void); -+void graphics_gotoxy(int x, int y); -+void graphics_cls(void); -+void graphics_setcolorstate (color_state state); -+void graphics_setcolor (int normal_color, int highlight_color); -+int graphics_setcursor (int on); -+int graphics_init(void); -+void graphics_end(void); -+ -+int hex(int v); -+void graphics_set_palette(int idx, int red, int green, int blue); -+#endif /* SUPPORT_GRAPHICS */ -+ - #endif /* ! GRUB_TERM_HEADER */ -diff -Naur grub-0.97.orig/THANKS grub-0.97/THANKS ---- grub-0.97.orig/THANKS 2005-05-07 19:17:43.000000000 -0700 -+++ grub-0.97/THANKS 2006-07-04 00:01:50.000000000 -0700 -@@ -121,3 +121,4 @@ - Yedidyah Bar-David - Yury V. Umanets - Yuri Zaporogets -+Vitaly Fertman -diff -Naur grub-0.97.orig/util/grub-install.in grub-0.97/util/grub-install.in ---- grub-0.97.orig/util/grub-install.in 2004-07-24 11:57:31.000000000 -0700 -+++ grub-0.97/util/grub-install.in 2006-07-04 00:01:50.000000000 -0700 -@@ -81,6 +81,50 @@ - EOF - } - -+# Usage: getraid_mdadm mddevice -+# Routine to find a physical device from an md device -+# If found, the first grub BIOS device (from device.map) is returned -+# If no BIOS drives match the RAID devices, the first device returned -+# from mdadm -D is returned -+getraid_mdadm() { -+ device=$1 -+ mdadm=$(mdadm -D "$device") || { -+ echo "$PROG: mdadm -D $device failed" >&2 -+ exit 1 -+ } -+ eval "$( -+ echo "$mdadm" | awk ' -+ $1 == "Number" && $2 == "Major" { start = 1; next } -+ $1 == "UUID" { print "uuid=" $3; start = 0; next } -+ !start { next } -+ $2 == 0 && $3 == 0 { next } -+ { devices = devices "\n" $NF } -+ END { print "devices='\''" devices "'\''" } -+ ' -+ )" -+ -+ # Convert RAID devices list into a list of disks -+ tmp_disks=`echo "$devices" | sed -e 's%\([sh]d[a-z]\)[0-9]*$%\1%' \ -+ -e 's%\(d[0-9]*\)p[0-9]*$%\1%' \ -+ -e 's%\(fd[0-9]*\)$%\1%' \ -+ -e 's%/part[0-9]*$%/disc%' \ -+ -e 's%\(c[0-7]d[0-9]*\).*$%\1%' \ -+ -e '/^$/d' | -+ sed -n '1h;2,$H;${g;s/\n/|/g;p}'` -+ -+ # Find first BIOS disk that's a member of the RAID array -+ # Default to first RAID member if no tmp_disks are BIOS devices -+ set -- `egrep $tmp_disks $device_map | \ -+ sort | \ -+ sed -n 1p ` -+ device=${2:-${tmp_disks%%|*}} -+ -+ # Return first partition on BIOS disk that's part of the RAID -+ echo "$devices" | \ -+ sed -n "\:${device}:p" | \ -+ sed -n 1p -+} -+ - # Usage: convert os_device - # Convert an OS device to the corresponding GRUB drive. - # This part is OS-specific. -@@ -96,6 +140,10 @@ - # Break the device name into the disk part and the partition part. - case "$host_os" in - linux*) -+ # Find an actual physical device if we're passed a RAID device -+ case $1 in -+ /dev/md*) set -- `getraid_mdadm $1` -+ esac - tmp_disk=`echo "$1" | sed -e 's%\([sh]d[a-z]\)[0-9]*$%\1%' \ - -e 's%\(d[0-9]*\)p[0-9]*$%\1%' \ - -e 's%\(fd[0-9]*\)$%\1%' \ -@@ -112,8 +160,8 @@ - tmp_disk=`echo "$1" | sed 's%\([sh]d[0-9]*\).*%\1%'` - tmp_part=`echo "$1" | sed "s%$tmp_disk%%"` ;; - freebsd* | kfreebsd*-gnu) -- tmp_disk=`echo "$1" | sed 's%r\{0,1\}\([saw]d[0-9]*\).*$%r\1%' \ -- | sed 's%r\{0,1\}\(da[0-9]*\).*$%r\1%'` -+ tmp_disk=`echo "$1" | sed 's%r\{0,1\}\([saw]d[0-9]*\).*$%\1%' \ -+ | sed 's%r\{0,1\}\(da[0-9]*\).*$%\1%'` - tmp_part=`echo "$1" \ - | sed "s%.*/r\{0,1\}[saw]d[0-9]\(s[0-9]*[a-h]\)%\1%" \ - | sed "s%.*/r\{0,1\}da[0-9]\(s[0-9]*[a-h]\)%\1%"` -@@ -131,7 +179,7 @@ - - # Get the drive name. - tmp_drive=`grep -v '^#' $device_map | grep "$tmp_disk *$" \ -- | sed 's%.*\(([hf]d[0-9][a-g0-9,]*)\).*%\1%'` -+ | sed 's%.*\(([hf]d[0-9][a-z0-9,]*)\).*%\1%'` - - # If not found, print an error message and exit. - if test "x$tmp_drive" = x; then -@@ -148,13 +196,13 @@ - gnu*) - if echo $tmp_part | grep "^s" >/dev/null; then - tmp_pc_slice=`echo $tmp_part \ -- | sed "s%s\([0-9]*\)[a-g]*$%\1%"` -+ | sed "s%s\([0-9]*\)[a-z]*$%\1%"` - tmp_drive=`echo "$tmp_drive" \ - | sed "s%)%,\`expr "$tmp_pc_slice" - 1\`)%"` - fi -- if echo $tmp_part | grep "[a-g]$" >/dev/null; then -+ if echo $tmp_part | grep "[a-z]$" >/dev/null; then - tmp_bsd_partition=`echo "$tmp_part" \ -- | sed "s%[^a-g]*\([a-g]\)$%\1%"` -+ | sed "s%[^a-z]*\([a-z]\)$%\1%"` - tmp_drive=`echo "$tmp_drive" \ - | sed "s%)%,$tmp_bsd_partition)%"` - fi -@@ -336,6 +384,10 @@ - # Create a safe temporary file. - test -n "$mklog" && log_file=`$mklog` - -+ # Before all invocations of the grub shell, call sync to make sure -+ # the raw device is in sync with any bufferring in filesystems. -+ sync -+ - $grub_shell --batch $no_floppy --device-map=$device_map <$log_file - quit - EOF -@@ -450,6 +502,24 @@ - # Create a safe temporary file. - test -n "$mklog" && log_file=`$mklog` - -+# Sync to prevent GRUB from not finding stage files (notably, on XFS) -+sync -+ -+# XFS needs special magic -+xfs_frozen=false -+if which xfs_freeze > /dev/null ; then -+ cat << EOF -+Due to a bug in xfs_freeze, the following command might produce a segmentation -+fault when ${grubdir} is not in an XFS filesystem. This error is harmless and -+can be ignored. -+EOF -+ if xfs_freeze -f ${grubdir} ; then xfs_frozen=true ; fi -+fi -+ -+# Before all invocations of the grub shell, call sync to make sure -+# the raw device is in sync with any bufferring in filesystems. -+sync -+ - # Now perform the installation. - $grub_shell --batch $no_floppy --device-map=$device_map <$log_file - root $root_drive -@@ -457,6 +527,10 @@ - quit - EOF - -+if ${xfs_frozen} ; then -+ xfs_freeze -u ${grubdir} -+fi -+ - if grep "Error [0-9]*: " $log_file >/dev/null || test $debug = yes; then - cat $log_file 1>&2 - exit 1