mirror of
https://codeberg.org/libreboot/grub.git
synced 2025-07-07 01:12:15 +00:00
Compare commits
No commits in common. "master" and "grub-2.12-rc1" have entirely different histories.
master
...
grub-2.12-
334 changed files with 1979 additions and 32527 deletions
5
.gitignore
vendored
5
.gitignore
vendored
|
@ -104,7 +104,6 @@ widthspec.bin
|
|||
/docs/version-dev.texi
|
||||
/docs/version.texi
|
||||
/ehci_test
|
||||
/erofs_test
|
||||
/example_grub_script_test
|
||||
/example_scripted_test
|
||||
/example_unit_test
|
||||
|
@ -141,12 +140,10 @@ widthspec.bin
|
|||
/grub-core/kernel.img.bin
|
||||
/grub-core/lib/gnulib
|
||||
/grub-core/lib/libgcrypt-grub
|
||||
/grub-core/lib/libtasn1-grub
|
||||
/grub-core/modinfo.sh
|
||||
/grub-core/rs_decoder.h
|
||||
/grub-core/symlist.c
|
||||
/grub-core/symlist.h
|
||||
/grub-core/tests/asn1/tests
|
||||
/grub-core/trigtables.c
|
||||
/grub-core/unidata.c
|
||||
/grub-editenv
|
||||
|
@ -171,8 +168,6 @@ widthspec.bin
|
|||
/grub-ofpathname.exe
|
||||
/grub-probe
|
||||
/grub-probe.exe
|
||||
/grub-protect
|
||||
/grub-protect.exe
|
||||
/grub-reboot
|
||||
/grub-render-label
|
||||
/grub-render-label.exe
|
||||
|
|
11
INSTALL
11
INSTALL
|
@ -20,7 +20,7 @@ configuring the GRUB.
|
|||
for i386, x86_64, arm (including thumb), arm64, mips(el), powerpc, sparc64
|
||||
* GNU Make
|
||||
* GNU Bison 2.3 or later
|
||||
* GNU gettext
|
||||
* GNU gettext 0.17 or later
|
||||
* GNU binutils 2.9.1.0.23 or later
|
||||
* Flex 2.5.35 or later
|
||||
* pkg-config
|
||||
|
@ -74,19 +74,18 @@ Prerequisites for make-check:
|
|||
* wamerican, for grub-fs-tester
|
||||
* mtools, FAT tools for EFI platforms
|
||||
* xfonts-unifont, for the functional tests
|
||||
* swtpm-tools and tpm2-tools, for TPM2 key protector tests
|
||||
|
||||
* If running a Linux kernel the following modules must be loaded:
|
||||
- fuse, loop
|
||||
- btrfs, erofs, ext4, f2fs, fat, hfs, hfsplus, jfs, mac-roman, minix, nilfs2,
|
||||
- btrfs, ext4, f2fs, fat, hfs, hfsplus, jfs, mac-roman, minix, nilfs2,
|
||||
reiserfs, udf, xfs
|
||||
- On newer kernels, the exfat kernel modules may be used instead of the
|
||||
exfat FUSE filesystem
|
||||
* The following are Debian named packages required mostly for the full
|
||||
suite of filesystem testing (but some are needed by other tests as well):
|
||||
- btrfs-progs, dosfstools, e2fsprogs, erofs-utils, exfatprogs, exfat-fuse,
|
||||
f2fs-tools, genromfs, hfsprogs, jfsutils, nilfs-tools, ntfs-3g,
|
||||
reiserfsprogs, squashfs-tools, reiserfsprogs, udftools, xfsprogs, zfs-fuse
|
||||
- btrfs-progs, dosfstools, e2fsprogs, exfat-utils, f2fs-tools, genromfs,
|
||||
hfsprogs, jfsutils, nilfs-tools, ntfs-3g, reiserfsprogs, squashfs-tools,
|
||||
reiserfsprogs, udftools, xfsprogs, zfs-fuse
|
||||
- exfat-fuse, if not using the exfat kernel module
|
||||
- gzip, lzop, xz-utils
|
||||
- attr, cpio, g++, gawk, parted, recode, tar, util-linux
|
||||
|
|
|
@ -40,7 +40,6 @@ library = {
|
|||
common = grub-core/disk/luks.c;
|
||||
common = grub-core/disk/luks2.c;
|
||||
common = grub-core/disk/geli.c;
|
||||
common = grub-core/disk/key_protector.c;
|
||||
common = grub-core/disk/cryptodisk.c;
|
||||
common = grub-core/disk/AFSplitter.c;
|
||||
common = grub-core/lib/pbkdf2.c;
|
||||
|
@ -56,7 +55,7 @@ library = {
|
|||
|
||||
library = {
|
||||
name = libgrubmods.a;
|
||||
cflags = '-fno-builtin -Wno-undef -Wno-unused-but-set-variable';
|
||||
cflags = '-fno-builtin -Wno-undef';
|
||||
cppflags = '-I$(srcdir)/grub-core/lib/minilzo -I$(srcdir)/grub-core/lib/xzembed -I$(srcdir)/grub-core/lib/zstd -DMINILZO_HAVE_CONFIG_H';
|
||||
|
||||
common_nodist = grub_script.tab.c;
|
||||
|
@ -99,7 +98,6 @@ library = {
|
|||
common = grub-core/fs/cpio_be.c;
|
||||
common = grub-core/fs/odc.c;
|
||||
common = grub-core/fs/newc.c;
|
||||
common = grub-core/fs/erofs.c;
|
||||
common = grub-core/fs/ext2.c;
|
||||
common = grub-core/fs/fat.c;
|
||||
common = grub-core/fs/exfat.c;
|
||||
|
@ -208,32 +206,6 @@ program = {
|
|||
ldadd = '$(LIBINTL) $(LIBDEVMAPPER) $(LIBZFS) $(LIBNVPAIR) $(LIBGEOM)';
|
||||
};
|
||||
|
||||
program = {
|
||||
name = grub-protect;
|
||||
mansection = 1;
|
||||
|
||||
common = grub-core/kern/emu/argp_common.c;
|
||||
common = grub-core/osdep/init.c;
|
||||
common = grub-core/lib/tss2/buffer.c;
|
||||
common = grub-core/lib/tss2/tss2_mu.c;
|
||||
common = grub-core/lib/tss2/tpm2_cmd.c;
|
||||
common = grub-core/commands/tpm2_key_protector/args.c;
|
||||
common = grub-core/commands/tpm2_key_protector/tpm2key_asn1_tab.c;
|
||||
common = util/grub-protect.c;
|
||||
common = util/probe.c;
|
||||
|
||||
cflags = '-I$(srcdir)/grub-core/lib/tss2 -I$(srcdir)/grub-core/commands/tpm2_key_protector';
|
||||
|
||||
ldadd = libgrubmods.a;
|
||||
ldadd = libgrubgcry.a;
|
||||
ldadd = libgrubkern.a;
|
||||
ldadd = grub-core/lib/gnulib/libgnu.a;
|
||||
ldadd = '$(LIBTASN1)';
|
||||
ldadd = '$(LIBINTL) $(LIBDEVMAPPER) $(LIBUTIL) $(LIBZFS) $(LIBNVPAIR) $(LIBGEOM)';
|
||||
|
||||
condition = COND_GRUB_PROTECT;
|
||||
};
|
||||
|
||||
program = {
|
||||
name = grub-mkrelpath;
|
||||
mansection = 1;
|
||||
|
@ -791,12 +763,6 @@ script = {
|
|||
dependencies = 'garbage-gen$(BUILD_EXEEXT)';
|
||||
};
|
||||
|
||||
script = {
|
||||
testcase = native;
|
||||
name = erofs_test;
|
||||
common = tests/erofs_test.in;
|
||||
};
|
||||
|
||||
script = {
|
||||
testcase = native;
|
||||
name = ext234_test;
|
||||
|
@ -1164,12 +1130,6 @@ script = {
|
|||
common = tests/netboot_test.in;
|
||||
};
|
||||
|
||||
script = {
|
||||
testcase = nonnative;
|
||||
name = serial_test;
|
||||
common = tests/serial_test.in;
|
||||
};
|
||||
|
||||
script = {
|
||||
testcase = nonnative;
|
||||
name = pseries_test;
|
||||
|
@ -1284,18 +1244,6 @@ script = {
|
|||
common = tests/luks2_test.in;
|
||||
};
|
||||
|
||||
script = {
|
||||
testcase = native;
|
||||
name = asn1_test;
|
||||
common = tests/asn1_test.in;
|
||||
};
|
||||
|
||||
script = {
|
||||
testcase = native;
|
||||
name = tpm2_key_protector_test;
|
||||
common = tests/tpm2_key_protector_test.in;
|
||||
};
|
||||
|
||||
program = {
|
||||
testcase = native;
|
||||
name = example_unit_test;
|
||||
|
|
20
NEWS
20
NEWS
|
@ -1,23 +1,3 @@
|
|||
New in 2.12:
|
||||
|
||||
* GCC 13 support.
|
||||
* clang 14 support.
|
||||
* binutils 2.38 support.
|
||||
* Unification of EFI Linux kernel loader across architectures.
|
||||
* Transition to EFI Linux kernel stub loader for x86 architecture.
|
||||
* Initial support for Boot Loader Interface.
|
||||
* Support for dynamic GRUB runtime memory addition using firmware calls.
|
||||
* PCI and MMIO UARTs support.
|
||||
* SDL2 support.
|
||||
* LoongArch support.
|
||||
* TPM driver fixes.
|
||||
* Many filesystems fixes.
|
||||
* Many CVE and Coverity fixes.
|
||||
* Debugging support improvements.
|
||||
* Tests improvements.
|
||||
* Documentation improvements.
|
||||
* ...and tons of other fixes and cleanups...
|
||||
|
||||
New in 2.06:
|
||||
|
||||
* GCC 10 support.
|
||||
|
|
35
autogen.sh
35
autogen.sh
|
@ -9,7 +9,7 @@ fi
|
|||
|
||||
# Detect python
|
||||
if [ -z "$PYTHON" ]; then
|
||||
for i in python3 python3.10 python; do
|
||||
for i in python3 python; do
|
||||
if command -v "$i" > /dev/null 2>&1; then
|
||||
PYTHON="$i"
|
||||
echo "Using $PYTHON..."
|
||||
|
@ -51,39 +51,6 @@ for x in mpi-asm-defs.h mpih-add1.c mpih-sub1.c mpih-mul1.c mpih-mul2.c mpih-mul
|
|||
cp grub-core/lib/libgcrypt-grub/mpi/generic/"$x" grub-core/lib/libgcrypt-grub/mpi/"$x"
|
||||
done
|
||||
|
||||
echo "Importing libtasn1..."
|
||||
if [ -d grub-core/lib/libtasn1-grub ]; then
|
||||
rm -rf grub-core/lib/libtasn1-grub
|
||||
fi
|
||||
|
||||
mkdir -p grub-core/lib/libtasn1-grub/lib
|
||||
cp grub-core/lib/libtasn1/lib/*.[ch] grub-core/lib/libtasn1-grub/lib
|
||||
cp grub-core/lib/libtasn1/libtasn1.h grub-core/lib/libtasn1-grub/
|
||||
|
||||
if [ -d grub-core/tests/asn1/tests ]; then
|
||||
rm -rf grub-core/tests/asn1/tests
|
||||
fi
|
||||
|
||||
mkdir grub-core/tests/asn1/tests
|
||||
cp grub-core/lib/libtasn1/tests/*.[ch] grub-core/tests/asn1/tests
|
||||
|
||||
for patch in \
|
||||
0001-libtasn1-disable-code-not-needed-in-grub.patch \
|
||||
0002-libtasn1-replace-strcat-with-strcpy-in-_asn1_str_cat.patch \
|
||||
0003-libtasn1-replace-strcat-with-_asn1_str_cat.patch \
|
||||
0004-libtasn1-adjust-the-header-paths-in-libtasn1.h.patch \
|
||||
0005-libtasn1-Use-grub_divmod64-for-division.patch \
|
||||
0006-libtasn1-fix-the-potential-buffer-overrun.patch \
|
||||
0007-asn1_test-include-asn1_test.h-only.patch \
|
||||
0008-asn1_test-rename-the-main-functions-to-the-test-name.patch \
|
||||
0009-asn1_test-return-either-0-or-1-to-reflect-the-result.patch \
|
||||
0010-asn1_test-remove-verbose-and-the-unnecessary-printf.patch \
|
||||
0011-asn1_test-print-the-error-messages-with-grub_printf.patch \
|
||||
0012-asn1_test-use-the-grub-specific-functions-and-types.patch \
|
||||
0013-asn1_test-enable-the-testcase-only-when-GRUB_LONG_MA.patch ; do
|
||||
patch -p1 -i grub-core/lib/libtasn1-patches/$patch
|
||||
done
|
||||
|
||||
echo "Generating Automake input..."
|
||||
|
||||
# Automake doesn't like including files from a path outside the project.
|
||||
|
|
|
@ -68,7 +68,7 @@ SKIP_PO=t
|
|||
buildreq="\
|
||||
autoconf 2.64
|
||||
automake 1.14
|
||||
gettext -
|
||||
gettext 0.18.3
|
||||
git 1.5.5
|
||||
patch -
|
||||
tar -
|
||||
|
@ -84,14 +84,7 @@ bootstrap_post_import_hook () {
|
|||
# Instead of patching our gnulib and therefore maintaining a fork, submit
|
||||
# changes to gnulib and update the hash above when they've merged. Do not
|
||||
# add new patches here.
|
||||
for patchname in fix-width \
|
||||
fix-regcomp-resource-leak \
|
||||
fix-regexec-resource-leak \
|
||||
fix-gcc-15-compile \
|
||||
fix-unused-value; do
|
||||
patch -d grub-core/lib/gnulib -p2 \
|
||||
< "grub-core/lib/gnulib-patches/$patchname.patch"
|
||||
done
|
||||
patch -d grub-core/lib/gnulib -p2 < grub-core/lib/gnulib-patches/fix-width.patch
|
||||
|
||||
for patchname in \
|
||||
0001-Support-POTFILES-shell \
|
||||
|
|
|
@ -75,7 +75,7 @@ grubconfdir = $(sysconfdir)/grub.d
|
|||
platformdir = $(pkglibdir)/$(target_cpu)-$(platform)
|
||||
starfielddir = $(pkgdatadir)/themes/starfield
|
||||
|
||||
CFLAGS_GNULIB = -Wno-undef -Wno-sign-compare -Wno-unused -Wno-unused-parameter -Wno-redundant-decls -Wno-unreachable-code -Wno-conversion -Wno-error=attributes
|
||||
CFLAGS_GNULIB = -Wno-undef -Wno-sign-compare -Wno-unused -Wno-unused-parameter -Wno-redundant-decls -Wno-unreachable-code -Wno-conversion
|
||||
CPPFLAGS_GNULIB = -I$(top_builddir)/grub-core/lib/gnulib -I$(top_srcdir)/grub-core/lib/gnulib
|
||||
|
||||
CFLAGS_POSIX = -fno-builtin
|
||||
|
@ -111,7 +111,6 @@ MOD_FILES =
|
|||
MODULE_FILES =
|
||||
MARKER_FILES =
|
||||
KERNEL_HEADER_FILES =
|
||||
EXTRA_DEPS =
|
||||
|
||||
bin_SCRIPTS =
|
||||
bin_PROGRAMS =
|
||||
|
|
|
@ -29,19 +29,12 @@ EXTRA_DIST += grub-core/genemuinit.sh
|
|||
EXTRA_DIST += grub-core/genemuinitheader.sh
|
||||
|
||||
EXTRA_DIST += grub-core/lib/gnulib-patches/fix-width.patch
|
||||
EXTRA_DIST += grub-core/lib/gnulib-patches/fix-regcomp-resource-leak.patch
|
||||
EXTRA_DIST += grub-core/lib/gnulib-patches/fix-regexec-resource-leak.patch
|
||||
EXTRA_DIST += grub-core/lib/gnulib-patches/fix-gcc-15-compile.patch
|
||||
EXTRA_DIST += grub-core/lib/gnulib-patches/fix-unused-value.patch
|
||||
|
||||
EXTRA_DIST += grub-core/lib/libgcrypt
|
||||
EXTRA_DIST += grub-core/lib/libgcrypt-grub/mpi/generic
|
||||
EXTRA_DIST += $(shell find $(top_srcdir)/include -name '*.h')
|
||||
EXTRA_DIST += $(shell find $(top_srcdir)/grub-core/lib -name '*.h')
|
||||
EXTRA_DIST += grub-core/efiemu/runtime/config.h
|
||||
EXTRA_DIST += grub-core/tests/asn1/asn1_test.h
|
||||
EXTRA_DIST += $(shell find $(top_srcdir)/grub-core/tests/asn1/tests -name '*.h')
|
||||
EXTRA_DIST += $(shell find $(top_srcdir)/grub-core/commands/tpm2_key_protector -name '*.h')
|
||||
|
||||
EXTRA_DIST += grub-core/lib/LzmaDec.c
|
||||
|
||||
|
|
|
@ -64,8 +64,6 @@
|
|||
# define GRUB_TARGET_CPU "@GRUB_TARGET_CPU@"
|
||||
# define GRUB_PLATFORM "@GRUB_PLATFORM@"
|
||||
|
||||
# define GRUB_STACK_PROTECTOR_INIT @GRUB_STACK_PROTECTOR_INIT@
|
||||
|
||||
# define RE_ENABLE_I18N 1
|
||||
|
||||
# define _GNU_SOURCE 1
|
||||
|
|
201
configure.ac
201
configure.ac
|
@ -34,7 +34,7 @@ dnl "TARGET_" (such as TARGET_CC, TARGET_CFLAGS, etc.) are used for
|
|||
dnl the target type. See INSTALL for full list of variables and
|
||||
dnl description of the relationships between them.
|
||||
|
||||
AC_INIT([GRUB],[2.13],[bug-grub@gnu.org])
|
||||
AC_INIT([GRUB],[2.12~rc1],[bug-grub@gnu.org])
|
||||
|
||||
AS_CASE(["$ERROR_PLATFORM_NOT_SUPPORT_SSP"],
|
||||
[n | no | nO | N | No | NO], [ERROR_PLATFORM_NOT_SUPPORT_SSP=no],
|
||||
|
@ -76,7 +76,6 @@ grub_TRANSFORM([grub-mkpasswd-pbkdf2])
|
|||
grub_TRANSFORM([grub-mkrelpath])
|
||||
grub_TRANSFORM([grub-mkrescue])
|
||||
grub_TRANSFORM([grub-probe])
|
||||
grub_TRANSFORM([grub-protect])
|
||||
grub_TRANSFORM([grub-reboot])
|
||||
grub_TRANSFORM([grub-script-check])
|
||||
grub_TRANSFORM([grub-set-default])
|
||||
|
@ -803,17 +802,6 @@ if test "x$target_cpu" = xmips || test "x$target_cpu" = xmipsel ; then
|
|||
if test "x$grub_cv_cc_mflush_func" = xyes; then
|
||||
TARGET_CFLAGS="$TARGET_CFLAGS -mflush-func=grub_red_herring"
|
||||
fi
|
||||
|
||||
AC_CACHE_CHECK([whether -mno-gpopt works], [grub_cv_cc_mno_gpopt], [
|
||||
CFLAGS="$TARGET_CFLAGS -mno-gpopt -Werror"
|
||||
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[]], [[]])],
|
||||
[grub_cv_cc_mno_gpopt=yes],
|
||||
[grub_cv_cc_mno_gpopt=no])
|
||||
])
|
||||
|
||||
if test "x$grub_cv_cc_mno_gpopt" = xyes; then
|
||||
TARGET_CFLAGS="$TARGET_CFLAGS -mno-gpopt"
|
||||
fi
|
||||
fi
|
||||
|
||||
|
||||
|
@ -913,31 +901,6 @@ if test "x$target_cpu" = xloongarch64; then
|
|||
TARGET_CCASFLAGS="$TARGET_CCASFLAGS -Wa,-mla-global-with-abs"
|
||||
fi
|
||||
|
||||
if test "x$target_cpu" = xriscv64 || test "x$target_cpu" = xriscv32; then
|
||||
AC_CACHE_CHECK([for no-relax options], grub_cv_target_cc_mno_relax, [
|
||||
grub_cv_target_cc_mno_relax=no
|
||||
for cand in "-mno-relax" "-Wa,-mno-relax"; do
|
||||
if test x"$grub_cv_target_cc_mno_relax" != xno ; then
|
||||
break
|
||||
fi
|
||||
CFLAGS="$TARGET_CFLAGS $cand -Werror"
|
||||
AC_LINK_IFELSE([AC_LANG_PROGRAM([[
|
||||
asm (".globl start; start:");
|
||||
void __main (void);
|
||||
void __main (void) {}
|
||||
int main (void);
|
||||
]], [[]])], [grub_cv_target_cc_mno_relax="$cand"], [])
|
||||
done
|
||||
])
|
||||
|
||||
CFLAGS="$TARGET_CFLAGS"
|
||||
|
||||
if test x"$grub_cv_target_cc_mno_relax" != xno ; then
|
||||
TARGET_CFLAGS="$TARGET_CFLAGS $grub_cv_target_cc_mno_relax"
|
||||
TARGET_CCASFLAGS="$TARGET_CCASFLAGS $grub_cv_target_cc_mno_relax"
|
||||
fi
|
||||
fi
|
||||
|
||||
# GRUB doesn't use float or doubles at all. Yet some toolchains may decide
|
||||
# that floats are a good fit to run instead of what's written in the code.
|
||||
# Given that floating point unit is disabled (if present to begin with)
|
||||
|
@ -1057,19 +1020,6 @@ if test x"$target_cpu" = xsparc64 ; then
|
|||
TARGET_LDFLAGS="$TARGET_LDFLAGS $grub_cv_target_cc_mno_relax"
|
||||
fi
|
||||
|
||||
# The backtrace module relies on frame pointers and the default optimization
|
||||
# level, -Os, omits them. Make sure they are enabled.
|
||||
AC_CACHE_CHECK([whether -fno-omit-frame-pointer works], [grub_cv_cc_fno_omit_frame_pointer], [
|
||||
CFLAGS="$TARGET_CFLAGS -fno-omit-frame-pointer"
|
||||
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[]], [[]])],
|
||||
[grub_cv_cc_fno_omit_frame_pointer=yes],
|
||||
[grub_cv_cc_fno_omit_frame_pointer=no])
|
||||
])
|
||||
|
||||
if test "x$grub_cv_cc_fno_omit_frame_pointer" = xyes; then
|
||||
TARGET_CFLAGS="$TARGET_CFLAGS -fno-omit-frame-pointer"
|
||||
fi
|
||||
|
||||
# By default, GCC 4.4 generates .eh_frame sections containing unwind
|
||||
# information in some cases where it previously did not. GRUB doesn't need
|
||||
# these and they just use up vital space. Restore the old compiler
|
||||
|
@ -1312,7 +1262,8 @@ AC_SUBST(TARGET_LDFLAGS_OLDMAGIC)
|
|||
|
||||
LDFLAGS="$TARGET_LDFLAGS"
|
||||
|
||||
if test "$target_cpu" = x86_64 || test "$target_cpu" = sparc64 || test "$target_cpu" = riscv64 ; then
|
||||
if test "$target_cpu" = x86_64 || test "$target_cpu" = sparc64 || test "$target_cpu" = riscv64 \
|
||||
|| test "$target_cpu" = loongarch64 ; then
|
||||
# Use large model to support 4G memory
|
||||
AC_CACHE_CHECK([whether option -mcmodel=large works], grub_cv_cc_mcmodel, [
|
||||
CFLAGS="$TARGET_CFLAGS -mcmodel=large"
|
||||
|
@ -1475,28 +1426,6 @@ else
|
|||
AC_MSG_ERROR([invalid value $enable_stack_protector for --enable-stack-protector])
|
||||
fi
|
||||
TARGET_CPPFLAGS="$TARGET_CPPFLAGS -DGRUB_STACK_PROTECTOR=1"
|
||||
|
||||
if test -n "$SOURCE_DATE_EPOCH"; then
|
||||
GRUB_STACK_PROTECTOR_INIT="0x00f2b7e2$(printf "%x" "$SOURCE_DATE_EPOCH" | sed 's/.*\(........\)$/\1/')"
|
||||
elif test -r /dev/urandom; then
|
||||
# Generate the 8 byte stack protector canary at build time if /dev/urandom
|
||||
# is able to be read. The first byte should be NUL to filter out string
|
||||
# buffer overflow attacks.
|
||||
GRUB_STACK_PROTECTOR_INIT="$($PYTHON -c 'import codecs; rf=open("/dev/urandom", "rb"); print("0x00"+codecs.encode(rf.read(7), "hex").decode("ascii"))')"
|
||||
else
|
||||
# Some hosts may not have a urandom, e.g. Windows, so use statically
|
||||
# generated random bytes
|
||||
GRUB_STACK_PROTECTOR_INIT="0x00f2b7e2f193b25c"
|
||||
fi
|
||||
|
||||
if test x"$target_m32" = x1 ; then
|
||||
# Make sure that the canary default value is 24-bits by only using the
|
||||
# lower 3 bytes on 32 bit systems. This allows the upper byte to be NUL
|
||||
# to filter out string buffer overflow attacks.
|
||||
GRUB_STACK_PROTECTOR_INIT="0x00$(echo "$GRUB_STACK_PROTECTOR_INIT" | sed 's/.*\(......\)$/\1/')"
|
||||
fi
|
||||
|
||||
AC_SUBST([GRUB_STACK_PROTECTOR_INIT])
|
||||
fi
|
||||
|
||||
CFLAGS="$TARGET_CFLAGS"
|
||||
|
@ -1680,7 +1609,7 @@ if test "$platform" = emu; then
|
|||
AC_SUBST(HAVE_SDL2)],
|
||||
[grub_emu_sdl2_excuse="libSDL2 libraries are required to build \`grub-emu' with SDL2 support"])
|
||||
[fi]
|
||||
if test x"$enable_grub_emu_sdl2" = xyes && test x"$grub_emu_sdl2_excuse" != x ; then
|
||||
if test x"enable_grub_emu_sdl2" = xyes && test x"$grub_emu_sdl2_excuse" != x ; then
|
||||
AC_MSG_ERROR([SDL2 support for grub-emu was explicitly requested but can't be compiled ($grub_emu_sdl2_excuse)])
|
||||
fi
|
||||
if test x"$grub_emu_sdl2_excuse" = x ; then
|
||||
|
@ -1775,9 +1704,6 @@ if test x"$grub_mkfont_excuse" = x ; then
|
|||
CPPFLAGS="$SAVED_CPPFLAGS"
|
||||
LIBS="$SAVED_LIBS"
|
||||
], [grub_mkfont_excuse=["need freetype2 library"]])
|
||||
if test x"$grub_mkfont_excuse" = x && test x"$host_kernel" = xnetbsd ; then
|
||||
FREETYPE_LIBS="$FREETYPE_LIBS -Wl,-R,/usr/pkg/lib" ;
|
||||
fi
|
||||
fi
|
||||
|
||||
if test x"$enable_grub_mkfont" = xyes && test x"$grub_mkfont_excuse" != x ; then
|
||||
|
@ -1832,11 +1758,6 @@ if test x"$grub_build_mkfont_excuse" = x ; then
|
|||
LIBS="$SAVED_LIBS"
|
||||
CPPFLAGS="$SAVED_CPPFLAGS_2"
|
||||
], [grub_build_mkfont_excuse=["need freetype2 library"]])
|
||||
if test x"$grub_build_mkfont_excuse" = x ; then
|
||||
case x"$build_os" in
|
||||
xnetbsd*) BUILD_FREETYPE_LIBS="$BUILD_FREETYPE_LIBS -Wl,-R,/usr/pkg/lib" ;;
|
||||
esac
|
||||
fi
|
||||
PKG_CONFIG="$SAVED_PKG_CONFIG"
|
||||
fi
|
||||
|
||||
|
@ -1863,6 +1784,8 @@ CPPFLAGS="$SAVED_CPPFLAGS"
|
|||
LDFLAGS="$SAVED_LDFLAGS"
|
||||
|
||||
|
||||
DJVU_FONT_SOURCE=
|
||||
|
||||
starfield_excuse=
|
||||
|
||||
AC_ARG_ENABLE([grub-themes],
|
||||
|
@ -1876,28 +1799,19 @@ if test x"$starfield_excuse" = x && test x"$enable_build_grub_mkfont" = xno ; th
|
|||
starfield_excuse="No build-time grub-mkfont"
|
||||
fi
|
||||
|
||||
AC_ARG_WITH([dejavufont],
|
||||
AS_HELP_STRING([--with-dejavufont=FILE],
|
||||
[set the DejeVu source [[guessed]]]))
|
||||
|
||||
if test "x$with_dejavufont" = x; then
|
||||
# search in well-known directories
|
||||
if test x"$starfield_excuse" = x; then
|
||||
for ext in pcf pcf.gz bdf bdf.gz ttf ttf.gz; do
|
||||
for dir in . /usr/src /usr/share/fonts/X11/misc /usr/share/fonts/truetype/ttf-dejavu /usr/share/fonts/dejavu /usr/share/fonts/truetype /usr/pkg/share/fonts/X11/TTF /usr/local/share/fonts/dejavu /usr/X11R6/lib/X11/fonts/TTF /usr/share/fonts/dejavu-sans-fonts /usr/share/fonts/truetype/dejavu; do
|
||||
if test -f "$dir/DejaVuSans.$ext"; then
|
||||
DJVU_FONT_SOURCE="$dir/DejaVuSans.$ext"
|
||||
break 2
|
||||
fi
|
||||
done
|
||||
if test x"$starfield_excuse" = x; then
|
||||
for ext in pcf pcf.gz bdf bdf.gz ttf ttf.gz; do
|
||||
for dir in . /usr/src /usr/share/fonts/X11/misc /usr/share/fonts/truetype/ttf-dejavu /usr/share/fonts/dejavu /usr/share/fonts/truetype; do
|
||||
if test -f "$dir/DejaVuSans.$ext"; then
|
||||
DJVU_FONT_SOURCE="$dir/DejaVuSans.$ext"
|
||||
break 2
|
||||
fi
|
||||
done
|
||||
done
|
||||
|
||||
if test "x$DJVU_FONT_SOURCE" = x; then
|
||||
starfield_excuse="No DejaVu found"
|
||||
fi
|
||||
fi
|
||||
else
|
||||
DJVU_FONT_SOURCE="$with_dejavufont"
|
||||
if test "x$DJVU_FONT_SOURCE" = x; then
|
||||
starfield_excuse="No DejaVu found"
|
||||
fi
|
||||
fi
|
||||
|
||||
if test x"$enable_grub_themes" = xyes && test x"$starfield_excuse" != x; then
|
||||
|
@ -1906,28 +1820,21 @@ fi
|
|||
|
||||
AC_SUBST([DJVU_FONT_SOURCE])
|
||||
|
||||
AC_ARG_WITH([unifont],
|
||||
AS_HELP_STRING([--with-unifont=FILE],
|
||||
[set the unifont source [[guessed]]]))
|
||||
FONT_SOURCE=
|
||||
|
||||
if test "x$with_unifont" = x; then
|
||||
# search in well-known directories
|
||||
for ext in pcf pcf.gz bdf bdf.gz ttf ttf.gz otf otf.gz; do
|
||||
for dir in . /usr/src /usr/share/fonts/X11/misc /usr/share/fonts/unifont /usr/share/fonts/uni /usr/share/fonts/truetype/unifont /usr/share/fonts/misc /usr/pkg/share/fonts/X11/misc /usr/local/share/fonts/gnu-unifont /usr/local/share/fonts/unifont; do
|
||||
if test -f "$dir/unifont.$ext"; then
|
||||
md5="$(md5sum "$dir/unifont.$ext"|awk '{ print $1; }')"
|
||||
# PCF and BDF from version 6.3 isn't hanled properly by libfreetype.
|
||||
if test "$md5" = 0a54834d2788c83886a3e1785a6a1e61 || test "$md5" = 28f2565c7a41d8d407e2551159385edb || test "$md5" = dae5e588461b3b92b87b6ffee734f936 || test "$md5" = 4a3d687aa5bb329ed05f4263a1016791 ; then
|
||||
continue
|
||||
fi
|
||||
FONT_SOURCE="$dir/unifont.$ext"
|
||||
break 2
|
||||
for ext in pcf pcf.gz bdf bdf.gz ttf ttf.gz; do
|
||||
for dir in . /usr/src /usr/share/fonts/X11/misc /usr/share/fonts/unifont /usr/share/fonts/uni /usr/share/fonts/truetype/unifont /usr/share/fonts/misc; do
|
||||
if test -f "$dir/unifont.$ext"; then
|
||||
md5="$(md5sum "$dir/unifont.$ext"|awk '{ print $1; }')"
|
||||
# PCF and BDF from version 6.3 isn't hanled properly by libfreetype.
|
||||
if test "$md5" = 0a54834d2788c83886a3e1785a6a1e61 || test "$md5" = 28f2565c7a41d8d407e2551159385edb || test "$md5" = dae5e588461b3b92b87b6ffee734f936 || test "$md5" = 4a3d687aa5bb329ed05f4263a1016791 ; then
|
||||
continue
|
||||
fi
|
||||
done
|
||||
FONT_SOURCE="$dir/unifont.$ext"
|
||||
break 2
|
||||
fi
|
||||
done
|
||||
else
|
||||
FONT_SOURCE="$with_unifont"
|
||||
fi
|
||||
done
|
||||
|
||||
if test x"$enable_build_grub_mkfont" = xno ; then
|
||||
FONT_SOURCE=
|
||||
|
@ -2064,19 +1971,8 @@ fi
|
|||
|
||||
if test x"$libzfs_excuse" = x ; then
|
||||
AC_CHECK_LIB([nvpair], [nvlist_lookup_string],
|
||||
[have_normal_nvpair=yes],
|
||||
[have_normal_nvpair=no])
|
||||
if test x"$have_normal_nvpair" = xno ; then
|
||||
AC_CHECK_LIB([nvpair], [opensolaris_nvlist_lookup_string],
|
||||
[have_prefixed_nvpair=yes],
|
||||
[have_prefixed_nvpair=no])
|
||||
if test x"$have_prefixed_nvpair" = xyes ; then
|
||||
AC_DEFINE([GRUB_UTIL_NVPAIR_IS_PREFIXED], [1],
|
||||
[Define to 1 if libnvpair symbols are prefixed with opensolaris_.])
|
||||
else
|
||||
libzfs_excuse="need nvpair library"
|
||||
fi
|
||||
fi
|
||||
[],
|
||||
[libzfs_excuse="need nvpair library"])
|
||||
fi
|
||||
|
||||
if test x"$enable_libzfs" = xyes && test x"$libzfs_excuse" != x ; then
|
||||
|
@ -2086,37 +1982,16 @@ fi
|
|||
if test x"$libzfs_excuse" = x ; then
|
||||
# We need both libzfs and libnvpair for a successful build.
|
||||
LIBZFS="-lzfs"
|
||||
AC_DEFINE([HAVE_LIBZFS], [1],
|
||||
[Define to 1 if you have the ZFS library.])
|
||||
LIBNVPAIR="-lnvpair"
|
||||
AC_DEFINE([USE_LIBZFS], [1],
|
||||
[Define to 1 if ZFS library should be used.])
|
||||
AC_DEFINE([HAVE_LIBNVPAIR], [1],
|
||||
[Define to 1 if you have the NVPAIR library.])
|
||||
fi
|
||||
|
||||
AC_SUBST([LIBZFS])
|
||||
AC_SUBST([LIBNVPAIR])
|
||||
|
||||
AC_ARG_ENABLE([grub-protect],
|
||||
[AS_HELP_STRING([--enable-grub-protect],
|
||||
[build and install the `grub-protect' utility (default=guessed)])])
|
||||
if test x"$enable_grub_protect" = xno ; then
|
||||
grub_protect_excuse="explicitly disabled"
|
||||
fi
|
||||
|
||||
LIBTASN1=
|
||||
if test x"$grub_protect_excuse" = x ; then
|
||||
AC_CHECK_LIB([tasn1], [asn1_write_value], [LIBTASN1="-ltasn1"], [grub_protect_excuse="need libtasn1 library"])
|
||||
fi
|
||||
AC_SUBST([LIBTASN1])
|
||||
|
||||
if test x"$enable_grub_protect" = xyes && test x"$grub_protect_excuse" != x ; then
|
||||
AC_MSG_ERROR([grub-protect was explicitly requested but can't be compiled ($grub_protect_excuse)])
|
||||
fi
|
||||
if test x"$grub_protect_excuse" = x ; then
|
||||
enable_grub_protect=yes
|
||||
else
|
||||
enable_grub_protect=no
|
||||
fi
|
||||
AC_SUBST([enable_grub_protect])
|
||||
|
||||
LIBS=""
|
||||
|
||||
AC_SUBST([FONT_SOURCE])
|
||||
|
@ -2233,7 +2108,6 @@ AM_CONDITIONAL([COND_GRUB_EMU_SDL], [test x$enable_grub_emu_sdl = xyes])
|
|||
AM_CONDITIONAL([COND_GRUB_EMU_PCI], [test x$enable_grub_emu_pci = xyes])
|
||||
AM_CONDITIONAL([COND_GRUB_MKFONT], [test x$enable_grub_mkfont = xyes])
|
||||
AM_CONDITIONAL([COND_GRUB_MOUNT], [test x$enable_grub_mount = xyes])
|
||||
AM_CONDITIONAL([COND_GRUB_PROTECT], [test x$enable_grub_protect = xyes])
|
||||
AM_CONDITIONAL([COND_HAVE_FONT_SOURCE], [test x$FONT_SOURCE != x])
|
||||
if test x$FONT_SOURCE != x ; then
|
||||
HAVE_FONT_SOURCE=1
|
||||
|
@ -2361,11 +2235,6 @@ echo grub-mount: Yes
|
|||
else
|
||||
echo grub-mount: No "($grub_mount_excuse)"
|
||||
fi
|
||||
if [ x"$grub_protect_excuse" = x ]; then
|
||||
echo grub-protect: Yes
|
||||
else
|
||||
echo grub-protect: No "($grub_protect_excuse)"
|
||||
fi
|
||||
if [ x"$starfield_excuse" = x ]; then
|
||||
echo starfield theme: Yes
|
||||
echo With DejaVuSans font from $DJVU_FONT_SOURCE
|
||||
|
|
|
@ -506,7 +506,6 @@ to update it.
|
|||
* Gnulib::
|
||||
* jsmn::
|
||||
* minilzo::
|
||||
* libtasn1::
|
||||
@end menu
|
||||
|
||||
@node Gnulib
|
||||
|
@ -597,40 +596,6 @@ cp minilzo-2.10/*.[hc] grub-core/lib/minilzo
|
|||
rm -r minilzo-2.10*
|
||||
@end example
|
||||
|
||||
@node libtasn1
|
||||
@section libtasn1
|
||||
|
||||
libtasn1 is a library providing Abstract Syntax Notation One (ASN.1, as
|
||||
specified by the X.680 ITU-T recommendation) parsing and structures management,
|
||||
and Distinguished Encoding Rules (DER, as per X.690) encoding and decoding
|
||||
functions.
|
||||
|
||||
To upgrade to a new version of the libtasn1 library, download the release
|
||||
tarball and copy the files into the target directory:
|
||||
|
||||
@example
|
||||
curl -L -O https://ftp.gnu.org/gnu/libtasn1/libtasn1-4.19.0.tar.gz
|
||||
tar xvzf libtasn1-4.19.0.tar.gz
|
||||
rm -rf grub-core/lib/libtasn1
|
||||
mkdir -p grub-core/lib/libtasn1/lib
|
||||
mkdir -p grub-core/lib/libtasn1/tests
|
||||
cp libtasn1-4.19.0/@{README.md,COPYING@} grub-core/lib/libtasn1
|
||||
cp libtasn1-4.19.0/lib/@{coding.c,decoding.c,element.c,element.h,errors.c,gstr.c,gstr.h,int.h,parser_aux.c,parser_aux.h,structure.c,structure.h@} grub-core/lib/libtasn1/lib
|
||||
cp libtasn1-4.19.0/lib/includes/libtasn1.h grub-core/lib/libtasn1
|
||||
cp libtasn1-4.19.0/tests/@{CVE-2018-1000654-1_asn1_tab.h,CVE-2018-1000654-2_asn1_tab.h,CVE-2018-1000654.c,object-id-decoding.c,object-id-encoding.c,octet-string.c,reproducers.c,Test_overflow.c,Test_simple.c,Test_strings.c@} grub-core/lib/libtasn1/tests
|
||||
rm -rf libtasn1-4.19.0*
|
||||
@end example
|
||||
|
||||
After upgrading the library, it may be necessary to apply the patches in
|
||||
@file{grub-core/lib/libtasn1-patches/} to adjust the code to be compatible with
|
||||
GRUB. These patches were needed to use the current version of libtasn1. The
|
||||
existing patches may not apply cleanly, apply at all, or even be needed for a
|
||||
newer version of the library, and other patches may be needed due to changes in
|
||||
the newer version. If existing patches need to be refreshed to apply cleanly,
|
||||
please include updated patches as part of the a patch set sent to the list.
|
||||
If new patches are needed or existing patches are not needed, also please send
|
||||
additions or removals as part of any patch set upgrading libtasn1.
|
||||
|
||||
@node Debugging
|
||||
@chapter Debugging
|
||||
|
||||
|
@ -695,11 +660,10 @@ GDB is started from the @file{grub-core} directory in the GRUB2 build
|
|||
directory. GRUB2 developers have made this more simple by including a GDB
|
||||
script which does much of the setup. This file is at @file{grub-core/gdb_grub}
|
||||
in the build directory and is also installed via @command{make install}.
|
||||
When using a pre-built GRUB, the distribution may have a package which installs
|
||||
If not building GRUB, the distribution may have a package which installs
|
||||
this GDB script along with debug symbol binaries, such as Debian's
|
||||
@samp{grub-pc-dbg} package. The GDB script is intended to be used
|
||||
like so, assuming that @samp{/path/to/script} is the path to the directory
|
||||
containing the gdb_grub script and debug symbol files:
|
||||
like so, assuming:
|
||||
|
||||
@example
|
||||
cd $(dirname /path/to/script/gdb_grub)
|
||||
|
@ -823,11 +787,6 @@ out of its way to avoid using hardware breakpoints internally and uses them as
|
|||
briefly as possible when needed, thus allowing the user to have a maximal
|
||||
number at their disposal.
|
||||
|
||||
@menu
|
||||
* OVMF debug log::
|
||||
* Using the gdbinfo command::
|
||||
@end menu
|
||||
|
||||
@node OVMF debug log
|
||||
@subsection OVMF debug log
|
||||
|
||||
|
|
3223
docs/grub.texi
3223
docs/grub.texi
File diff suppressed because it is too large
Load diff
|
@ -1,4 +0,0 @@
|
|||
[NAME]
|
||||
grub-protect \- protect a disk key with a key protector
|
||||
[DESCRIPTION]
|
||||
grub-protect helps to protect a disk encryption key with a specified key protector.
|
11
gentpl.py
11
gentpl.py
|
@ -631,10 +631,7 @@ def platform_values(defn, platform, suffix):
|
|||
def extra_dist(defn):
|
||||
return foreach_value(defn, "extra_dist", lambda value: value + " ")
|
||||
|
||||
def extra_dep(defn):
|
||||
return foreach_value(defn, "depends", lambda value: value + " ")
|
||||
|
||||
def platform_sources(defn, p): return platform_values(defn, p, "_head") + platform_values(defn, p, "")
|
||||
def platform_sources(defn, p): return platform_values(defn, p, "")
|
||||
def platform_nodist_sources(defn, p): return platform_values(defn, p, "_nodist")
|
||||
|
||||
def platform_startup(defn, p): return platform_specific_values(defn, p, "_startup", "startup")
|
||||
|
@ -660,7 +657,7 @@ def first_time(defn, snippet):
|
|||
def is_platform_independent(defn):
|
||||
if 'enable' in defn:
|
||||
return False
|
||||
for suffix in [ "", "_head", "_nodist" ]:
|
||||
for suffix in [ "", "_nodist" ]:
|
||||
template = platform_values(defn, GRUB_PLATFORMS[0], suffix)
|
||||
for platform in GRUB_PLATFORMS[1:]:
|
||||
if template != platform_values(defn, platform, suffix):
|
||||
|
@ -702,10 +699,6 @@ def module(defn, platform):
|
|||
gvar_add("MOD_FILES", name + ".mod")
|
||||
gvar_add("MARKER_FILES", name + ".marker")
|
||||
gvar_add("CLEANFILES", name + ".marker")
|
||||
|
||||
for dep in defn.find_all("depends"):
|
||||
gvar_add("EXTRA_DEPS", "depends " + name + " " + dep + ":")
|
||||
|
||||
output("""
|
||||
""" + name + """.marker: $(""" + cname(defn) + """_SOURCES) $(nodist_""" + cname(defn) + """_SOURCES)
|
||||
$(TARGET_CPP) -DGRUB_LST_GENERATOR $(CPPFLAGS_MARKER) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(""" + cname(defn) + """_CPPFLAGS) $(CPPFLAGS) $^ > $@.new || (rm -f $@; exit 1)
|
||||
|
|
|
@ -90,7 +90,6 @@ endif
|
|||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/mm.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/parser.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/partition.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/key_protector.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/stack_protector.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/term.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/time.h
|
||||
|
@ -154,7 +153,6 @@ endif
|
|||
if COND_i386_ieee1275
|
||||
KERNEL_HEADER_FILES += $(top_builddir)/include/grub/machine/kernel.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/ieee1275/ieee1275.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/ieee1275/alloc.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/terminfo.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/extcmd.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/lib/arg.h
|
||||
|
@ -242,7 +240,6 @@ endif
|
|||
|
||||
if COND_powerpc_ieee1275
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/ieee1275/ieee1275.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/ieee1275/alloc.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/terminfo.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/extcmd.h
|
||||
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/lib/arg.h
|
||||
|
@ -455,11 +452,8 @@ crypto.lst: $(srcdir)/lib/libgcrypt-grub/cipher/crypto.lst
|
|||
platform_DATA += crypto.lst
|
||||
CLEANFILES += crypto.lst
|
||||
|
||||
extra_deps.lst:
|
||||
@echo $(EXTRA_DEPS) | sed "s/\s*:\s*/\n/g" > $@
|
||||
|
||||
syminfo.lst: gensyminfo.sh kernel_syms.lst extra_deps.lst $(MODULE_FILES)
|
||||
cat kernel_syms.lst extra_deps.lst > $@.new
|
||||
syminfo.lst: gensyminfo.sh kernel_syms.lst $(MODULE_FILES)
|
||||
cat kernel_syms.lst > $@.new
|
||||
for m in $(MODULE_FILES); do \
|
||||
sh $< $$m >> $@.new || exit 1; \
|
||||
done
|
||||
|
@ -469,7 +463,7 @@ syminfo.lst: gensyminfo.sh kernel_syms.lst extra_deps.lst $(MODULE_FILES)
|
|||
moddep.lst: syminfo.lst genmoddep.awk video.lst
|
||||
cat $< | sort | $(AWK) -f $(srcdir)/genmoddep.awk > $@ || (rm -f $@; exit 1)
|
||||
platform_DATA += moddep.lst
|
||||
CLEANFILES += config.log syminfo.lst moddep.lst extra_deps.lst
|
||||
CLEANFILES += config.log syminfo.lst moddep.lst
|
||||
|
||||
$(MOD_FILES): %.mod : genmod.sh moddep.lst %.module$(EXEEXT) build-grub-module-verifier$(BUILD_EXEEXT)
|
||||
TARGET_OBJ2ELF=@TARGET_OBJ2ELF@ sh $^ $@
|
||||
|
|
|
@ -536,7 +536,7 @@ image = {
|
|||
|
||||
image = {
|
||||
name = xz_decompress;
|
||||
mips_head = boot/mips/startup_raw.S;
|
||||
mips = boot/mips/startup_raw.S;
|
||||
common = boot/decompressor/minilib.c;
|
||||
common = boot/decompressor/xz.c;
|
||||
common = lib/xzembed/xz_dec_bcj.c;
|
||||
|
@ -554,7 +554,7 @@ image = {
|
|||
|
||||
image = {
|
||||
name = none_decompress;
|
||||
mips_head = boot/mips/startup_raw.S;
|
||||
mips = boot/mips/startup_raw.S;
|
||||
common = boot/decompressor/none.c;
|
||||
|
||||
cppflags = '-DGRUB_EMBED_DECOMPRESSOR=1';
|
||||
|
@ -714,16 +714,12 @@ module = {
|
|||
name = cmostest;
|
||||
common = commands/i386/cmostest.c;
|
||||
enable = cmos;
|
||||
enable = i386_efi;
|
||||
enable = x86_64_efi;
|
||||
};
|
||||
|
||||
module = {
|
||||
name = cmosdump;
|
||||
common = commands/i386/cmosdump.c;
|
||||
enable = cmos;
|
||||
enable = i386_efi;
|
||||
enable = x86_64_efi;
|
||||
};
|
||||
|
||||
module = {
|
||||
|
@ -1282,11 +1278,6 @@ module = {
|
|||
common = disk/raid6_recover.c;
|
||||
};
|
||||
|
||||
module = {
|
||||
name = key_protector;
|
||||
common = disk/key_protector.c;
|
||||
};
|
||||
|
||||
module = {
|
||||
name = scsi;
|
||||
common = disk/scsi.c;
|
||||
|
@ -1447,11 +1438,6 @@ module = {
|
|||
common = fs/odc.c;
|
||||
};
|
||||
|
||||
module = {
|
||||
name = erofs;
|
||||
common = fs/erofs.c;
|
||||
};
|
||||
|
||||
module = {
|
||||
name = ext2;
|
||||
common = fs/ext2.c;
|
||||
|
@ -1606,7 +1592,6 @@ module = {
|
|||
common = fs/zfs/zfs_lz4.c;
|
||||
common = fs/zfs/zfs_sha256.c;
|
||||
common = fs/zfs/zfs_fletcher.c;
|
||||
cppflags = '-I$(srcdir)/lib/posix_wrap -I$(srcdir)/lib/zstd';
|
||||
};
|
||||
|
||||
module = {
|
||||
|
@ -2008,7 +1993,7 @@ module = {
|
|||
extra_dist = script/yylex.l;
|
||||
extra_dist = script/parser.y;
|
||||
|
||||
cflags = '$(CFLAGS_POSIX) -Wno-redundant-decls -Wno-unused-but-set-variable';
|
||||
cflags = '$(CFLAGS_POSIX) -Wno-redundant-decls';
|
||||
cppflags = '$(CPPFLAGS_POSIX)';
|
||||
};
|
||||
|
||||
|
@ -2253,10 +2238,6 @@ module = {
|
|||
common = tests/videotest_checksum.c;
|
||||
};
|
||||
|
||||
/*
|
||||
* These tests fail depending on the version of unifont. As we don't distribute
|
||||
* our own unifont it fails for most users. Disable them so that they don't mask
|
||||
* real failures. They can be reinstated once we solve unifont problem.
|
||||
module = {
|
||||
name = gfxterm_menu;
|
||||
common = tests/gfxterm_menu.c;
|
||||
|
@ -2266,7 +2247,6 @@ module = {
|
|||
name = cmdline_cat_test;
|
||||
common = tests/cmdline_cat_test.c;
|
||||
};
|
||||
*/
|
||||
|
||||
module = {
|
||||
name = bitmap;
|
||||
|
@ -2572,34 +2552,6 @@ module = {
|
|||
enable = efi;
|
||||
};
|
||||
|
||||
module = {
|
||||
name = tss2;
|
||||
common = lib/tss2/buffer.c;
|
||||
common = lib/tss2/tss2_mu.c;
|
||||
common = lib/tss2/tpm2_cmd.c;
|
||||
common = lib/tss2/tss2.c;
|
||||
efi = lib/efi/tcg2.c;
|
||||
emu = lib/tss2/tcg2_emu.c;
|
||||
powerpc_ieee1275 = lib/ieee1275/tcg2.c;
|
||||
enable = efi;
|
||||
enable = emu;
|
||||
enable = powerpc_ieee1275;
|
||||
cppflags = '-I$(srcdir)/lib/tss2';
|
||||
};
|
||||
|
||||
module = {
|
||||
name = tpm2_key_protector;
|
||||
common = commands/tpm2_key_protector/args.c;
|
||||
common = commands/tpm2_key_protector/module.c;
|
||||
common = commands/tpm2_key_protector/tpm2key.c;
|
||||
common = commands/tpm2_key_protector/tpm2key_asn1_tab.c;
|
||||
/* The plaform support of tpm2_key_protector depends on the tcg2 implementation in tss2. */
|
||||
enable = efi;
|
||||
enable = emu;
|
||||
enable = powerpc_ieee1275;
|
||||
cppflags = '-I$(srcdir)/lib/tss2 -I$(srcdir)/lib/libtasn1-grub';
|
||||
};
|
||||
|
||||
module = {
|
||||
name = tr;
|
||||
common = commands/tr.c;
|
||||
|
@ -2642,35 +2594,4 @@ module = {
|
|||
name = bli;
|
||||
efi = commands/bli.c;
|
||||
enable = efi;
|
||||
depends = part_gpt;
|
||||
};
|
||||
|
||||
module = {
|
||||
name = asn1;
|
||||
common = lib/libtasn1-grub/lib/decoding.c;
|
||||
common = lib/libtasn1-grub/lib/coding.c;
|
||||
common = lib/libtasn1-grub/lib/element.c;
|
||||
common = lib/libtasn1-grub/lib/structure.c;
|
||||
common = lib/libtasn1-grub/lib/parser_aux.c;
|
||||
common = lib/libtasn1-grub/lib/gstr.c;
|
||||
common = lib/libtasn1-grub/lib/errors.c;
|
||||
common = lib/libtasn1_wrap/wrap.c;
|
||||
cflags = '$(CFLAGS_POSIX) $(CFLAGS_GNULIB)';
|
||||
/* -Wno-type-limits comes from configure.ac of libtasn1 */
|
||||
cppflags = '$(CPPFLAGS_POSIX) $(CPPFLAGS_GNULIB) -I$(srcdir)/lib/libtasn1-grub -I$(srcdir)/lib/libtasn1-grub/lib -Wno-type-limits';
|
||||
};
|
||||
|
||||
module = {
|
||||
name = asn1_test;
|
||||
common = tests/asn1/tests/CVE-2018-1000654.c;
|
||||
common = tests/asn1/tests/object-id-decoding.c;
|
||||
common = tests/asn1/tests/object-id-encoding.c;
|
||||
common = tests/asn1/tests/octet-string.c;
|
||||
common = tests/asn1/tests/reproducers.c;
|
||||
common = tests/asn1/tests/Test_overflow.c;
|
||||
common = tests/asn1/tests/Test_simple.c;
|
||||
common = tests/asn1/tests/Test_strings.c;
|
||||
common = tests/asn1/asn1_test.c;
|
||||
cflags = '-Wno-uninitialized';
|
||||
cppflags = '-I$(srcdir)/lib/libtasn1-grub -I$(srcdir)/tests/asn1/';
|
||||
};
|
||||
|
|
|
@ -218,7 +218,7 @@ enum
|
|||
|
||||
#define GRUB_EHCI_TERMINATE (1<<0)
|
||||
|
||||
#define GRUB_EHCI_TOGGLE ((grub_uint32_t) 1<<31)
|
||||
#define GRUB_EHCI_TOGGLE (1<<31)
|
||||
|
||||
enum
|
||||
{
|
||||
|
|
|
@ -38,20 +38,6 @@
|
|||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
enum
|
||||
{
|
||||
OPTION_EXCLUDE = 0,
|
||||
OPTION_LOAD_ONLY,
|
||||
OPTION_V1,
|
||||
OPTION_V2,
|
||||
OPTION_OEMID,
|
||||
OPTION_OEMTABLE,
|
||||
OPTION_OEMTABLEREV,
|
||||
OPTION_OEMTABLECREATOR,
|
||||
OPTION_OEMTABLECREATORREV,
|
||||
OPTION_NO_EBDA
|
||||
};
|
||||
|
||||
static const struct grub_arg_option options[] = {
|
||||
{"exclude", 'x', 0,
|
||||
N_("Don't load host tables specified by comma-separated list."),
|
||||
|
@ -504,21 +490,21 @@ grub_cmd_acpi (struct grub_extcmd_context *ctxt, int argc, char **args)
|
|||
|
||||
if (rsdp)
|
||||
{
|
||||
grub_uint8_t *entry_ptr;
|
||||
grub_uint32_t *entry_ptr;
|
||||
char *exclude = 0;
|
||||
char *load_only = 0;
|
||||
char *ptr;
|
||||
grub_size_t tbl_addr_size;
|
||||
struct grub_acpi_table_header *table_head;
|
||||
/* RSDT consists of header and an array of 32-bit pointers. */
|
||||
struct grub_acpi_table_header *rsdt;
|
||||
|
||||
exclude = state[OPTION_EXCLUDE].set ? grub_strdup (state[OPTION_EXCLUDE].arg) : 0;
|
||||
exclude = state[0].set ? grub_strdup (state[0].arg) : 0;
|
||||
if (exclude)
|
||||
{
|
||||
for (ptr = exclude; *ptr; ptr++)
|
||||
*ptr = grub_tolower (*ptr);
|
||||
}
|
||||
|
||||
load_only = state[OPTION_LOAD_ONLY].set ? grub_strdup (state[OPTION_LOAD_ONLY].arg) : 0;
|
||||
load_only = state[1].set ? grub_strdup (state[1].arg) : 0;
|
||||
if (load_only)
|
||||
{
|
||||
for (ptr = load_only; *ptr; ptr++)
|
||||
|
@ -529,31 +515,20 @@ grub_cmd_acpi (struct grub_extcmd_context *ctxt, int argc, char **args)
|
|||
rev1 = ! rsdp->revision;
|
||||
rev2 = rsdp->revision;
|
||||
if (rev2 && ((struct grub_acpi_table_header *) (grub_addr_t) ((struct grub_acpi_rsdp_v20 *) rsdp)->xsdt_addr) != NULL)
|
||||
{
|
||||
/* XSDT consists of header and an array of 64-bit pointers. */
|
||||
table_head = (struct grub_acpi_table_header *) (grub_addr_t) ((struct grub_acpi_rsdp_v20 *) rsdp)->xsdt_addr;
|
||||
tbl_addr_size = sizeof (((struct grub_acpi_rsdp_v20 *) rsdp)->xsdt_addr);
|
||||
}
|
||||
rsdt = (struct grub_acpi_table_header *) (grub_addr_t) ((struct grub_acpi_rsdp_v20 *) rsdp)->xsdt_addr;
|
||||
else
|
||||
{
|
||||
/* RSDT consists of header and an array of 32-bit pointers. */
|
||||
table_head = (struct grub_acpi_table_header *) (grub_addr_t) rsdp->rsdt_addr;
|
||||
tbl_addr_size = sizeof (rsdp->rsdt_addr);
|
||||
}
|
||||
rsdt = (struct grub_acpi_table_header *) (grub_addr_t) rsdp->rsdt_addr;
|
||||
|
||||
/* Load host tables. */
|
||||
for (entry_ptr = (grub_uint8_t *) (table_head + 1);
|
||||
entry_ptr < (grub_uint8_t *) (((grub_uint8_t *) table_head) + table_head->length);
|
||||
entry_ptr += tbl_addr_size)
|
||||
for (entry_ptr = (grub_uint32_t *) (rsdt + 1);
|
||||
entry_ptr < (grub_uint32_t *) (((grub_uint8_t *) rsdt)
|
||||
+ rsdt->length);
|
||||
entry_ptr++)
|
||||
{
|
||||
char signature[5];
|
||||
struct efiemu_acpi_table *table;
|
||||
struct grub_acpi_table_header *curtable;
|
||||
if (tbl_addr_size == sizeof (rsdp->rsdt_addr))
|
||||
curtable = (struct grub_acpi_table_header *) (grub_addr_t) *((grub_uint32_t *) entry_ptr);
|
||||
else
|
||||
curtable = (struct grub_acpi_table_header *) (grub_addr_t) *((grub_uint64_t *) entry_ptr);
|
||||
|
||||
struct grub_acpi_table_header *curtable
|
||||
= (struct grub_acpi_table_header *) (grub_addr_t) *entry_ptr;
|
||||
signature[4] = 0;
|
||||
for (i = 0; i < 4;i++)
|
||||
signature[i] = grub_tolower (curtable->signature[i]);
|
||||
|
@ -637,26 +612,26 @@ grub_cmd_acpi (struct grub_extcmd_context *ctxt, int argc, char **args)
|
|||
}
|
||||
|
||||
/* Does user specify versions to generate? */
|
||||
if (state[OPTION_V1].set || state[OPTION_V2].set)
|
||||
if (state[2].set || state[3].set)
|
||||
{
|
||||
rev1 = state[OPTION_V1].set;
|
||||
if (state[OPTION_V2].set)
|
||||
rev1 = state[2].set;
|
||||
if (state[3].set)
|
||||
rev2 = rev2 ? : 2;
|
||||
else
|
||||
rev2 = 0;
|
||||
}
|
||||
|
||||
/* Does user override root header information? */
|
||||
if (state[OPTION_OEMID].set)
|
||||
grub_strncpy (root_oemid, state[OPTION_OEMID].arg, sizeof (root_oemid));
|
||||
if (state[OPTION_OEMTABLE].set)
|
||||
grub_strncpy (root_oemtable, state[OPTION_OEMTABLE].arg, sizeof (root_oemtable));
|
||||
if (state[OPTION_OEMTABLEREV].set)
|
||||
root_oemrev = grub_strtoul (state[OPTION_OEMTABLEREV].arg, 0, 0);
|
||||
if (state[OPTION_OEMTABLECREATOR].set)
|
||||
grub_strncpy (root_creator_id, state[OPTION_OEMTABLECREATOR].arg, sizeof (root_creator_id));
|
||||
if (state[OPTION_OEMTABLECREATORREV].set)
|
||||
root_creator_rev = grub_strtoul (state[OPTION_OEMTABLECREATORREV].arg, 0, 0);
|
||||
if (state[4].set)
|
||||
grub_strncpy (root_oemid, state[4].arg, sizeof (root_oemid));
|
||||
if (state[5].set)
|
||||
grub_strncpy (root_oemtable, state[5].arg, sizeof (root_oemtable));
|
||||
if (state[6].set)
|
||||
root_oemrev = grub_strtoul (state[6].arg, 0, 0);
|
||||
if (state[7].set)
|
||||
grub_strncpy (root_creator_id, state[7].arg, sizeof (root_creator_id));
|
||||
if (state[8].set)
|
||||
root_creator_rev = grub_strtoul (state[8].arg, 0, 0);
|
||||
|
||||
/* Load user tables */
|
||||
for (i = 0; i < argc; i++)
|
||||
|
@ -772,7 +747,7 @@ grub_cmd_acpi (struct grub_extcmd_context *ctxt, int argc, char **args)
|
|||
acpi_tables = 0;
|
||||
|
||||
#if defined (__i386__) || defined (__x86_64__)
|
||||
if (! state[OPTION_NO_EBDA].set)
|
||||
if (! state[9].set)
|
||||
{
|
||||
grub_err_t err;
|
||||
err = grub_acpi_create_ebda ();
|
||||
|
|
|
@ -48,22 +48,6 @@ get_part_uuid (const char *device_name, char **part_uuid)
|
|||
if (device == NULL)
|
||||
return grub_error (grub_errno, N_("cannot open device: %s"), device_name);
|
||||
|
||||
if (device->disk == NULL)
|
||||
{
|
||||
grub_dprintf ("bli", "%s is not a disk device, partuuid skipped\n", device_name);
|
||||
*part_uuid = NULL;
|
||||
grub_device_close (device);
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
if (device->disk->partition == NULL)
|
||||
{
|
||||
grub_dprintf ("bli", "%s has no partition, partuuid skipped\n", device_name);
|
||||
*part_uuid = NULL;
|
||||
grub_device_close (device);
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
disk = grub_disk_open (device->disk->name);
|
||||
if (disk == NULL)
|
||||
{
|
||||
|
@ -115,7 +99,7 @@ set_loader_device_part_uuid (void)
|
|||
|
||||
status = get_part_uuid (device_name, &part_uuid);
|
||||
|
||||
if (status == GRUB_ERR_NONE && part_uuid)
|
||||
if (status == GRUB_ERR_NONE)
|
||||
status = grub_efi_set_variable_to_string ("LoaderDevicePartUUID", &bli_vendor_guid, part_uuid,
|
||||
GRUB_EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
GRUB_EFI_VARIABLE_RUNTIME_ACCESS);
|
||||
|
@ -133,6 +117,4 @@ GRUB_MOD_INIT (bli)
|
|||
GRUB_EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
GRUB_EFI_VARIABLE_RUNTIME_ACCESS);
|
||||
set_loader_device_part_uuid ();
|
||||
/* No error here is critical, other than being logged */
|
||||
grub_print_error ();
|
||||
}
|
||||
|
|
|
@ -92,6 +92,7 @@ lock_rom_area (void)
|
|||
static void
|
||||
fake_bios_data (int use_rom)
|
||||
{
|
||||
unsigned i;
|
||||
void *acpi, *smbios;
|
||||
grub_uint16_t *ebda_seg_ptr, *low_mem_ptr;
|
||||
|
||||
|
@ -100,15 +101,33 @@ fake_bios_data (int use_rom)
|
|||
if ((*ebda_seg_ptr) || (*low_mem_ptr))
|
||||
return;
|
||||
|
||||
acpi = grub_efi_find_configuration_table (&acpi2_guid);
|
||||
grub_dprintf ("efi", "ACPI2: %p\n", acpi);
|
||||
if (!acpi) {
|
||||
acpi = grub_efi_find_configuration_table (&acpi_guid);
|
||||
grub_dprintf ("efi", "ACPI: %p\n", acpi);
|
||||
}
|
||||
acpi = 0;
|
||||
smbios = 0;
|
||||
for (i = 0; i < grub_efi_system_table->num_table_entries; i++)
|
||||
{
|
||||
grub_guid_t *guid =
|
||||
&grub_efi_system_table->configuration_table[i].vendor_guid;
|
||||
|
||||
smbios = grub_efi_find_configuration_table (&smbios_guid);
|
||||
grub_dprintf ("efi", "SMBIOS: %p\n", smbios);
|
||||
if (! grub_memcmp (guid, &acpi2_guid, sizeof (grub_guid_t)))
|
||||
{
|
||||
acpi = grub_efi_system_table->configuration_table[i].vendor_table;
|
||||
grub_dprintf ("efi", "ACPI2: %p\n", acpi);
|
||||
}
|
||||
else if (! grub_memcmp (guid, &acpi_guid, sizeof (grub_guid_t)))
|
||||
{
|
||||
void *t;
|
||||
|
||||
t = grub_efi_system_table->configuration_table[i].vendor_table;
|
||||
if (! acpi)
|
||||
acpi = t;
|
||||
grub_dprintf ("efi", "ACPI: %p\n", t);
|
||||
}
|
||||
else if (! grub_memcmp (guid, &smbios_guid, sizeof (grub_guid_t)))
|
||||
{
|
||||
smbios = grub_efi_system_table->configuration_table[i].vendor_table;
|
||||
grub_dprintf ("efi", "SMBIOS: %p\n", smbios);
|
||||
}
|
||||
}
|
||||
|
||||
*ebda_seg_ptr = FAKE_EBDA_SEG;
|
||||
*low_mem_ptr = (FAKE_EBDA_SEG >> 6);
|
||||
|
|
|
@ -29,7 +29,7 @@
|
|||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
static struct known_protocol
|
||||
struct known_protocol
|
||||
{
|
||||
grub_guid_t guid;
|
||||
const char *name;
|
||||
|
@ -96,7 +96,7 @@ grub_cmd_lsefi (grub_command_t cmd __attribute__ ((unused)),
|
|||
grub_efi_handle_t handle = handles[i];
|
||||
grub_efi_status_t status;
|
||||
grub_efi_uintn_t num_protocols;
|
||||
grub_packed_guid_t **protocols;
|
||||
grub_guid_t **protocols;
|
||||
grub_efi_device_path_t *dp;
|
||||
|
||||
grub_printf ("Handle %p\n", handle);
|
||||
|
|
|
@ -64,18 +64,12 @@ grub_cmd_lsefisystab (struct grub_command *cmd __attribute__ ((unused)),
|
|||
char **args __attribute__ ((unused)))
|
||||
{
|
||||
const grub_efi_system_table_t *st = grub_efi_system_table;
|
||||
const grub_efi_uint32_t major_rev = st->hdr.revision >> 16;
|
||||
const grub_efi_uint32_t minor_rev_upper = (st->hdr.revision & 0xffff) / 10;
|
||||
const grub_efi_uint32_t minor_rev_lower = (st->hdr.revision & 0xffff) % 10;
|
||||
grub_efi_configuration_table_t *t;
|
||||
unsigned int i;
|
||||
|
||||
grub_printf ("Address: %p\n", st);
|
||||
grub_printf ("Signature: %016" PRIxGRUB_UINT64_T " revision: %u.%u",
|
||||
st->hdr.signature, major_rev, minor_rev_upper);
|
||||
if (minor_rev_lower)
|
||||
grub_printf (".%u", minor_rev_lower);
|
||||
grub_printf ("\n");
|
||||
grub_printf ("Signature: %016" PRIxGRUB_UINT64_T " revision: %08x\n",
|
||||
st->hdr.signature, st->hdr.revision);
|
||||
{
|
||||
char *vendor;
|
||||
grub_uint16_t *vendor_utf16;
|
||||
|
|
|
@ -136,16 +136,22 @@ grub_cmd_lssal (struct grub_command *cmd __attribute__ ((unused)),
|
|||
int argc __attribute__ ((unused)),
|
||||
char **args __attribute__ ((unused)))
|
||||
{
|
||||
const grub_efi_system_table_t *st = grub_efi_system_table;
|
||||
grub_efi_configuration_table_t *t = st->configuration_table;
|
||||
unsigned int i;
|
||||
static grub_guid_t guid = GRUB_EFI_SAL_TABLE_GUID;
|
||||
void *table = grub_efi_find_configuration_table (&guid);
|
||||
|
||||
if (table == NULL)
|
||||
for (i = 0; i < st->num_table_entries; i++)
|
||||
{
|
||||
grub_printf ("SAL not found\n");
|
||||
return GRUB_ERR_NONE;
|
||||
if (grub_memcmp (&guid, &t->vendor_guid,
|
||||
sizeof (grub_guid_t)) == 0)
|
||||
{
|
||||
disp_sal (t->vendor_table);
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
t++;
|
||||
}
|
||||
|
||||
disp_sal (table);
|
||||
grub_printf ("SAL not found\n");
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
|
|
|
@ -18,20 +18,44 @@
|
|||
*/
|
||||
|
||||
#include <grub/smbios.h>
|
||||
#include <grub/misc.h>
|
||||
#include <grub/efi/efi.h>
|
||||
#include <grub/efi/api.h>
|
||||
|
||||
struct grub_smbios_eps *
|
||||
grub_machine_smbios_get_eps (void)
|
||||
{
|
||||
unsigned i;
|
||||
static grub_guid_t smbios_guid = GRUB_EFI_SMBIOS_TABLE_GUID;
|
||||
|
||||
return (struct grub_smbios_eps *) grub_efi_find_configuration_table (&smbios_guid);
|
||||
for (i = 0; i < grub_efi_system_table->num_table_entries; i++)
|
||||
{
|
||||
grub_guid_t *guid =
|
||||
&grub_efi_system_table->configuration_table[i].vendor_guid;
|
||||
|
||||
if (! grub_memcmp (guid, &smbios_guid, sizeof (grub_guid_t)))
|
||||
return (struct grub_smbios_eps *)
|
||||
grub_efi_system_table->configuration_table[i].vendor_table;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
struct grub_smbios_eps3 *
|
||||
grub_machine_smbios_get_eps3 (void)
|
||||
{
|
||||
unsigned i;
|
||||
static grub_guid_t smbios3_guid = GRUB_EFI_SMBIOS3_TABLE_GUID;
|
||||
|
||||
return (struct grub_smbios_eps3 *) grub_efi_find_configuration_table (&smbios3_guid);
|
||||
for (i = 0; i < grub_efi_system_table->num_table_entries; i++)
|
||||
{
|
||||
grub_guid_t *guid =
|
||||
&grub_efi_system_table->configuration_table[i].vendor_guid;
|
||||
|
||||
if (! grub_memcmp (guid, &smbios3_guid, sizeof (grub_guid_t)))
|
||||
return (struct grub_smbios_eps3 *)
|
||||
grub_efi_system_table->configuration_table[i].vendor_table;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -292,15 +292,6 @@ grub_tpm_present (void)
|
|||
{
|
||||
grub_efi_handle_t tpm_handle;
|
||||
grub_efi_uint8_t protocol_version;
|
||||
grub_efi_cc_protocol_t *cc;
|
||||
|
||||
/*
|
||||
* When confidential computing measurement protocol is enabled
|
||||
* we assume the TPM is present.
|
||||
*/
|
||||
cc = grub_efi_locate_protocol (&cc_measurement_guid, NULL);
|
||||
if (cc != NULL)
|
||||
return 1;
|
||||
|
||||
if (!grub_tpm_handle_find (&tpm_handle, &protocol_version))
|
||||
return 0;
|
||||
|
|
|
@ -49,9 +49,6 @@ grub_extcmd_dispatcher (struct grub_command *cmd, int argc, char **args,
|
|||
}
|
||||
|
||||
state = grub_arg_list_alloc (ext, argc, args);
|
||||
if (state == NULL)
|
||||
return grub_errno;
|
||||
|
||||
if (grub_arg_parse (ext, argc, args, state, &new_args, &new_argc))
|
||||
{
|
||||
context.state = state;
|
||||
|
|
|
@ -306,8 +306,6 @@ grub_cmd_file (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
|
||||
elf = grub_elf_file (file, file->name);
|
||||
|
||||
if (elf == NULL)
|
||||
break;
|
||||
if (elf->ehdr.ehdr32.e_type != grub_cpu_to_le16_compile_time (ET_EXEC)
|
||||
|| elf->ehdr.ehdr32.e_ident[EI_DATA] != ELFDATA2LSB)
|
||||
break;
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
#include <grub/lib/hexdump.h>
|
||||
#include <grub/extcmd.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/lockdown.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -52,11 +51,7 @@ grub_cmd_hexdump (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
length = (state[1].set) ? grub_strtoul (state[1].arg, 0, 0) : 256;
|
||||
|
||||
if (!grub_strcmp (args[0], "(mem)"))
|
||||
{
|
||||
if (grub_is_lockdown() == GRUB_LOCKDOWN_ENABLED)
|
||||
return grub_error (GRUB_ERR_ACCESS_DENIED, N_("memory reading is disabled in lockdown mode"));
|
||||
hexdump (skip, (char *) (grub_addr_t) skip, length);
|
||||
}
|
||||
hexdump (skip, (char *) (grub_addr_t) skip, length);
|
||||
else if ((args[0][0] == '(') && (args[0][namelen - 1] == ')'))
|
||||
{
|
||||
grub_disk_t disk;
|
||||
|
|
|
@ -104,13 +104,13 @@ static grub_command_t cmd, cmd_clean, cmd_set;
|
|||
|
||||
GRUB_MOD_INIT(cmostest)
|
||||
{
|
||||
cmd = grub_register_command_lockdown ("cmostest", grub_cmd_cmostest,
|
||||
cmd = grub_register_command ("cmostest", grub_cmd_cmostest,
|
||||
N_("BYTE:BIT"),
|
||||
N_("Test bit at BYTE:BIT in CMOS."));
|
||||
cmd_clean = grub_register_command_lockdown ("cmosclean", grub_cmd_cmosclean,
|
||||
cmd_clean = grub_register_command ("cmosclean", grub_cmd_cmosclean,
|
||||
N_("BYTE:BIT"),
|
||||
N_("Clear bit at BYTE:BIT in CMOS."));
|
||||
cmd_set = grub_register_command_lockdown ("cmosset", grub_cmd_cmosset,
|
||||
cmd_set = grub_register_command ("cmosset", grub_cmd_cmosset,
|
||||
N_("BYTE:BIT"),
|
||||
/* TRANSLATORS: A bit may be either set (1) or clear (0). */
|
||||
N_("Set bit at BYTE:BIT in CMOS."));
|
||||
|
|
|
@ -26,7 +26,7 @@
|
|||
#include <grub/extcmd.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/i386/cpuid.h>
|
||||
#include <grub/i386/msr.h>
|
||||
#include <grub/i386/rdmsr.h>
|
||||
|
||||
GRUB_MOD_LICENSE("GPLv3+");
|
||||
|
||||
|
@ -42,16 +42,27 @@ static const struct grub_arg_option options[] =
|
|||
static grub_err_t
|
||||
grub_cmd_msr_read (grub_extcmd_context_t ctxt, int argc, char **argv)
|
||||
{
|
||||
grub_err_t err;
|
||||
grub_uint32_t addr;
|
||||
grub_uint32_t manufacturer[3], max_cpuid, a, b, c, features, addr;
|
||||
grub_uint64_t value;
|
||||
const char *ptr;
|
||||
char buf[sizeof("1122334455667788")];
|
||||
|
||||
err = grub_cpu_is_msr_supported ();
|
||||
/*
|
||||
* The CPUID instruction should be used to determine whether MSRs
|
||||
* are supported. (CPUID.01H:EDX[5] = 1)
|
||||
*/
|
||||
if (! grub_cpu_is_cpuid_supported ())
|
||||
return grub_error (GRUB_ERR_BUG, N_("unsupported instruction"));
|
||||
|
||||
if (err != GRUB_ERR_NONE)
|
||||
return grub_error (err, N_("RDMSR is unsupported"));
|
||||
grub_cpuid (0, max_cpuid, manufacturer[0], manufacturer[2], manufacturer[1]);
|
||||
|
||||
if (max_cpuid < 1)
|
||||
return grub_error (GRUB_ERR_BUG, N_("unsupported instruction"));
|
||||
|
||||
grub_cpuid (1, a, b, c, features);
|
||||
|
||||
if (!(features & (1 << 5)))
|
||||
return grub_error (GRUB_ERR_BUG, N_("unsupported instruction"));
|
||||
|
||||
if (argc != 1)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, N_("one argument expected"));
|
||||
|
@ -65,7 +76,7 @@ grub_cmd_msr_read (grub_extcmd_context_t ctxt, int argc, char **argv)
|
|||
if (*ptr != '\0')
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, N_("invalid argument"));
|
||||
|
||||
value = grub_rdmsr (addr);
|
||||
value = grub_msr_read (addr);
|
||||
|
||||
if (ctxt->state[0].set)
|
||||
{
|
||||
|
|
|
@ -27,7 +27,7 @@
|
|||
#include <grub/lockdown.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/i386/cpuid.h>
|
||||
#include <grub/i386/msr.h>
|
||||
#include <grub/i386/wrmsr.h>
|
||||
|
||||
GRUB_MOD_LICENSE("GPLv3+");
|
||||
|
||||
|
@ -36,15 +36,26 @@ static grub_command_t cmd_write;
|
|||
static grub_err_t
|
||||
grub_cmd_msr_write (grub_command_t cmd __attribute__ ((unused)), int argc, char **argv)
|
||||
{
|
||||
grub_err_t err;
|
||||
grub_uint32_t addr;
|
||||
grub_uint32_t manufacturer[3], max_cpuid, a, b, c, features, addr;
|
||||
grub_uint64_t value;
|
||||
const char *ptr;
|
||||
|
||||
err = grub_cpu_is_msr_supported ();
|
||||
/*
|
||||
* The CPUID instruction should be used to determine whether MSRs
|
||||
* are supported. (CPUID.01H:EDX[5] = 1)
|
||||
*/
|
||||
if (!grub_cpu_is_cpuid_supported ())
|
||||
return grub_error (GRUB_ERR_BUG, N_("unsupported instruction"));
|
||||
|
||||
if (err != GRUB_ERR_NONE)
|
||||
return grub_error (err, N_("WRMSR is unsupported"));
|
||||
grub_cpuid (0, max_cpuid, manufacturer[0], manufacturer[2], manufacturer[1]);
|
||||
|
||||
if (max_cpuid < 1)
|
||||
return grub_error (GRUB_ERR_BUG, N_("unsupported instruction"));
|
||||
|
||||
grub_cpuid (1, a, b, c, features);
|
||||
|
||||
if (!(features & (1 << 5)))
|
||||
return grub_error (GRUB_ERR_BUG, N_("unsupported instruction"));
|
||||
|
||||
if (argc != 2)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, N_("two arguments expected"));
|
||||
|
@ -66,7 +77,7 @@ grub_cmd_msr_write (grub_command_t cmd __attribute__ ((unused)), int argc, char
|
|||
if (*ptr != '\0')
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, N_("invalid argument"));
|
||||
|
||||
grub_wrmsr (addr, value);
|
||||
grub_msr_write (addr, value);
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
|
|
@ -23,10 +23,48 @@
|
|||
#include <grub/types.h>
|
||||
#include <grub/tpm.h>
|
||||
#include <grub/ieee1275/ieee1275.h>
|
||||
#include <grub/ieee1275/tpm.h>
|
||||
#include <grub/mm.h>
|
||||
#include <grub/misc.h>
|
||||
|
||||
static grub_ieee1275_ihandle_t tpm_ihandle;
|
||||
static grub_uint8_t tpm_version;
|
||||
|
||||
#define IEEE1275_IHANDLE_INVALID ((grub_ieee1275_ihandle_t) 0)
|
||||
|
||||
static void
|
||||
tpm_get_tpm_version (void)
|
||||
{
|
||||
grub_ieee1275_phandle_t vtpm;
|
||||
char buffer[20];
|
||||
|
||||
if (!grub_ieee1275_finddevice ("/vdevice/vtpm", &vtpm) &&
|
||||
!grub_ieee1275_get_property (vtpm, "compatible", buffer,
|
||||
sizeof (buffer), NULL) &&
|
||||
!grub_strcmp (buffer, "IBM,vtpm20"))
|
||||
tpm_version = 2;
|
||||
}
|
||||
|
||||
static grub_err_t
|
||||
tpm_init (void)
|
||||
{
|
||||
static int init_success = 0;
|
||||
|
||||
if (!init_success)
|
||||
{
|
||||
if (grub_ieee1275_open ("/vdevice/vtpm", &tpm_ihandle) < 0)
|
||||
{
|
||||
tpm_ihandle = IEEE1275_IHANDLE_INVALID;
|
||||
return GRUB_ERR_UNKNOWN_DEVICE;
|
||||
}
|
||||
|
||||
init_success = 1;
|
||||
|
||||
tpm_get_tpm_version ();
|
||||
}
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
static int
|
||||
ibmvtpm_2hash_ext_log (grub_uint8_t pcrindex,
|
||||
grub_uint32_t eventtype,
|
||||
|
@ -52,7 +90,7 @@ ibmvtpm_2hash_ext_log (grub_uint8_t pcrindex,
|
|||
|
||||
INIT_IEEE1275_COMMON (&args.common, "call-method", 8, 2);
|
||||
args.method = (grub_ieee1275_cell_t) "2hash-ext-log";
|
||||
args.ihandle = grub_ieee1275_tpm_ihandle;
|
||||
args.ihandle = tpm_ihandle;
|
||||
args.pcrindex = pcrindex;
|
||||
args.eventtype = eventtype;
|
||||
args.description = (grub_ieee1275_cell_t) description;
|
||||
|
@ -100,7 +138,7 @@ grub_tpm_measure (unsigned char *buf, grub_size_t size, grub_uint8_t pcr,
|
|||
grub_dprintf ("tpm", "log_event, pcr = %d, size = 0x%" PRIxGRUB_SIZE ", %s\n",
|
||||
pcr, size, description);
|
||||
|
||||
if (grub_ieee1275_tpm_ihandle != GRUB_IEEE1275_IHANDLE_INVALID)
|
||||
if (tpm_version == 2)
|
||||
return tpm2_log_event (buf, size, pcr, description);
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
|
@ -113,5 +151,5 @@ grub_tpm_present (void)
|
|||
* Call tpm_init() "late" rather than from GRUB_MOD_INIT() so that device nodes
|
||||
* can be found.
|
||||
*/
|
||||
return grub_ieee1275_tpm_init() == GRUB_ERR_NONE;
|
||||
return tpm_init() == GRUB_ERR_NONE;
|
||||
}
|
||||
|
|
|
@ -198,6 +198,7 @@ legacy_file (const char *filename)
|
|||
const char **args = grub_malloc (sizeof (args[0]));
|
||||
if (!args)
|
||||
{
|
||||
grub_file_close (file);
|
||||
grub_free (suffix);
|
||||
grub_free (entrysrc);
|
||||
return grub_errno;
|
||||
|
|
|
@ -87,44 +87,37 @@ grub_ls_list_devices (int longlist)
|
|||
struct grub_ls_list_files_ctx
|
||||
{
|
||||
char *dirname;
|
||||
char *filename;
|
||||
int all;
|
||||
int human;
|
||||
int longlist;
|
||||
int print_dirhdr;
|
||||
};
|
||||
|
||||
/* Helper for grub_ls_list_files. */
|
||||
static int
|
||||
print_file (const char *filename, const struct grub_dirhook_info *info,
|
||||
print_files (const char *filename, const struct grub_dirhook_info *info,
|
||||
void *data)
|
||||
{
|
||||
struct grub_ls_list_files_ctx *ctx = data;
|
||||
|
||||
if (ctx->all || filename[0] != '.')
|
||||
grub_printf ("%s%s ", filename, info->dir ? "/" : "");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Helper for grub_ls_list_files. */
|
||||
static int
|
||||
print_files_long (const char *filename, const struct grub_dirhook_info *info,
|
||||
void *data)
|
||||
{
|
||||
char *pathname = NULL;
|
||||
struct grub_ls_list_files_ctx *ctx = data;
|
||||
|
||||
if ((! ctx->all) && (filename[0] == '.'))
|
||||
return 0;
|
||||
|
||||
if ((ctx->filename != NULL) && (grub_strcmp (filename, ctx->filename) != 0))
|
||||
return 0;
|
||||
|
||||
if (ctx->print_dirhdr)
|
||||
{
|
||||
grub_printf ("%s:\n", ctx->dirname);
|
||||
ctx->print_dirhdr = 0;
|
||||
}
|
||||
|
||||
if (! ctx->longlist)
|
||||
{
|
||||
if (ctx->filename != NULL)
|
||||
grub_xputs (ctx->dirname);
|
||||
grub_printf ("%s%s ", filename, info->dir ? "/" : "");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (! info->dir)
|
||||
{
|
||||
grub_file_t file;
|
||||
char *pathname;
|
||||
|
||||
if (ctx->dirname[grub_strlen (ctx->dirname) - 1] == '/')
|
||||
pathname = grub_xasprintf ("%s%s", ctx->dirname, filename);
|
||||
|
@ -138,19 +131,20 @@ print_file (const char *filename, const struct grub_dirhook_info *info,
|
|||
should be reported as directories. */
|
||||
file = grub_file_open (pathname, GRUB_FILE_TYPE_GET_SIZE
|
||||
| GRUB_FILE_TYPE_NO_DECOMPRESS);
|
||||
if (file)
|
||||
if (! file)
|
||||
{
|
||||
if (! ctx->human)
|
||||
grub_printf ("%-12llu", (unsigned long long) file->size);
|
||||
else
|
||||
grub_printf ("%-12s", grub_get_human_size (file->size,
|
||||
GRUB_HUMAN_SIZE_SHORT));
|
||||
grub_file_close (file);
|
||||
grub_errno = 0;
|
||||
grub_free (pathname);
|
||||
return 0;
|
||||
}
|
||||
else
|
||||
grub_xputs ("????????????");
|
||||
|
||||
grub_errno = GRUB_ERR_NONE;
|
||||
if (! ctx->human)
|
||||
grub_printf ("%-12llu", (unsigned long long) file->size);
|
||||
else
|
||||
grub_printf ("%-12s", grub_get_human_size (file->size,
|
||||
GRUB_HUMAN_SIZE_SHORT));
|
||||
grub_file_close (file);
|
||||
grub_free (pathname);
|
||||
}
|
||||
else
|
||||
grub_printf ("%-12s", _("DIR"));
|
||||
|
@ -171,22 +165,13 @@ print_file (const char *filename, const struct grub_dirhook_info *info,
|
|||
datetime.day, datetime.hour,
|
||||
datetime.minute, datetime.second);
|
||||
}
|
||||
/*
|
||||
* Only print the full path when listing a file path given as an argument
|
||||
* to ls, i.e. when ctx->filename != NULL. File listings that are printed
|
||||
* due to showing the contents of a directory do not need a full path because
|
||||
* the full path to the directory will have already been printed.
|
||||
*/
|
||||
grub_printf ("%s%s\n", (ctx->filename != NULL) ? pathname : filename,
|
||||
info->dir ? "/" : "");
|
||||
|
||||
grub_free (pathname);
|
||||
grub_printf ("%s%s\n", filename, info->dir ? "/" : "");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static grub_err_t
|
||||
grub_ls_list_files (char *dirname, int longlist, int all, int human, int dirhdr)
|
||||
grub_ls_list_files (char *dirname, int longlist, int all, int human)
|
||||
{
|
||||
char *device_name;
|
||||
grub_fs_t fs;
|
||||
|
@ -231,38 +216,44 @@ grub_ls_list_files (char *dirname, int longlist, int all, int human, int dirhdr)
|
|||
{
|
||||
struct grub_ls_list_files_ctx ctx = {
|
||||
.dirname = dirname,
|
||||
.filename = NULL,
|
||||
.all = all,
|
||||
.human = human,
|
||||
.longlist = longlist,
|
||||
.print_dirhdr = dirhdr
|
||||
.human = human
|
||||
};
|
||||
|
||||
(fs->fs_dir) (dev, path, print_file, &ctx);
|
||||
if (longlist)
|
||||
(fs->fs_dir) (dev, path, print_files_long, &ctx);
|
||||
else
|
||||
(fs->fs_dir) (dev, path, print_files, &ctx);
|
||||
|
||||
if (grub_errno == GRUB_ERR_BAD_FILE_TYPE
|
||||
&& path[grub_strlen (path) - 1] != '/')
|
||||
{
|
||||
/*
|
||||
* Reset errno as it is currently set, but will cause subsequent code
|
||||
* to think there is an error.
|
||||
*/
|
||||
grub_errno = GRUB_ERR_NONE;
|
||||
|
||||
/* PATH might be a regular file. */
|
||||
ctx.print_dirhdr = 0;
|
||||
ctx.filename = grub_strrchr (dirname, '/');
|
||||
if (ctx.filename == NULL)
|
||||
goto fail;
|
||||
++(ctx.filename);
|
||||
char *p;
|
||||
grub_file_t file;
|
||||
struct grub_dirhook_info info;
|
||||
grub_errno = 0;
|
||||
|
||||
ctx.dirname = grub_strndup (dirname, ctx.filename - dirname);
|
||||
if (ctx.dirname == NULL)
|
||||
file = grub_file_open (dirname, GRUB_FILE_TYPE_GET_SIZE
|
||||
| GRUB_FILE_TYPE_NO_DECOMPRESS);
|
||||
if (! file)
|
||||
goto fail;
|
||||
|
||||
(fs->fs_dir) (dev, ctx.dirname + (path - dirname), print_file, &ctx);
|
||||
grub_file_close (file);
|
||||
|
||||
grub_free (ctx.dirname);
|
||||
p = grub_strrchr (dirname, '/') + 1;
|
||||
dirname = grub_strndup (dirname, p - dirname);
|
||||
if (! dirname)
|
||||
goto fail;
|
||||
|
||||
all = 1;
|
||||
grub_memset (&info, 0, sizeof (info));
|
||||
if (longlist)
|
||||
print_files_long (p, &info, &ctx);
|
||||
else
|
||||
print_files (p, &info, &ctx);
|
||||
|
||||
grub_free (dirname);
|
||||
}
|
||||
|
||||
if (grub_errno == GRUB_ERR_NONE)
|
||||
|
@ -277,7 +268,7 @@ grub_ls_list_files (char *dirname, int longlist, int all, int human, int dirhdr)
|
|||
|
||||
grub_free (device_name);
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static grub_err_t
|
||||
|
@ -290,10 +281,10 @@ grub_cmd_ls (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
grub_ls_list_devices (state[0].set);
|
||||
else
|
||||
for (i = 0; i < argc; i++)
|
||||
grub_ls_list_files (args[i], state[0].set, state[2].set, state[1].set,
|
||||
argc > 1);
|
||||
grub_ls_list_files (args[i], state[0].set, state[2].set,
|
||||
state[1].set);
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static grub_extcmd_t cmd;
|
||||
|
|
|
@ -122,20 +122,17 @@ grub_cmd_write (grub_command_t cmd, int argc, char **argv)
|
|||
GRUB_MOD_INIT(memrw)
|
||||
{
|
||||
cmd_read_byte =
|
||||
grub_register_extcmd_lockdown ("read_byte", grub_cmd_read, 0,
|
||||
N_("ADDR"),
|
||||
N_("Read 8-bit value from ADDR."),
|
||||
options);
|
||||
grub_register_extcmd ("read_byte", grub_cmd_read, 0,
|
||||
N_("ADDR"), N_("Read 8-bit value from ADDR."),
|
||||
options);
|
||||
cmd_read_word =
|
||||
grub_register_extcmd_lockdown ("read_word", grub_cmd_read, 0,
|
||||
N_("ADDR"),
|
||||
N_("Read 16-bit value from ADDR."),
|
||||
options);
|
||||
grub_register_extcmd ("read_word", grub_cmd_read, 0,
|
||||
N_("ADDR"), N_("Read 16-bit value from ADDR."),
|
||||
options);
|
||||
cmd_read_dword =
|
||||
grub_register_extcmd_lockdown ("read_dword", grub_cmd_read, 0,
|
||||
N_("ADDR"),
|
||||
N_("Read 32-bit value from ADDR."),
|
||||
options);
|
||||
grub_register_extcmd ("read_dword", grub_cmd_read, 0,
|
||||
N_("ADDR"), N_("Read 32-bit value from ADDR."),
|
||||
options);
|
||||
cmd_write_byte =
|
||||
grub_register_command_lockdown ("write_byte", grub_cmd_write,
|
||||
N_("ADDR VALUE [MASK]"),
|
||||
|
|
|
@ -29,10 +29,6 @@
|
|||
#include <grub/command.h>
|
||||
#include <grub/i18n.h>
|
||||
|
||||
#ifdef GRUB_MACHINE_EFI
|
||||
#include <grub/cryptodisk.h>
|
||||
#endif
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
/* cat FILE */
|
||||
|
@ -171,7 +167,7 @@ grub_mini_cmd_lsmod (struct grub_command *cmd __attribute__ ((unused)),
|
|||
{
|
||||
grub_dl_dep_t dep;
|
||||
|
||||
grub_printf ("%s\t%" PRIuGRUB_UINT64_T "\t\t", mod->name, mod->ref_count);
|
||||
grub_printf ("%s\t%d\t\t", mod->name, mod->ref_count);
|
||||
for (dep = mod->dep; dep; dep = dep->next)
|
||||
{
|
||||
if (dep != mod->dep)
|
||||
|
@ -191,13 +187,6 @@ grub_mini_cmd_exit (struct grub_command *cmd __attribute__ ((unused)),
|
|||
int argc __attribute__ ((unused)),
|
||||
char *argv[] __attribute__ ((unused)))
|
||||
{
|
||||
#ifdef GRUB_MACHINE_EFI
|
||||
/*
|
||||
* The "exit" command is often used to launch the next boot application.
|
||||
* So, erase the secrets.
|
||||
*/
|
||||
grub_cryptodisk_erasesecrets ();
|
||||
#endif
|
||||
grub_exit ();
|
||||
/* Not reached. */
|
||||
}
|
||||
|
@ -214,8 +203,8 @@ GRUB_MOD_INIT(minicmd)
|
|||
grub_register_command ("help", grub_mini_cmd_help,
|
||||
0, N_("Show this message."));
|
||||
cmd_dump =
|
||||
grub_register_command_lockdown ("dump", grub_mini_cmd_dump,
|
||||
N_("ADDR [SIZE]"), N_("Show memory contents."));
|
||||
grub_register_command ("dump", grub_mini_cmd_dump,
|
||||
N_("ADDR [SIZE]"), N_("Show memory contents."));
|
||||
cmd_rmmod =
|
||||
grub_register_command ("rmmod", grub_mini_cmd_rmmod,
|
||||
N_("MODULE"), N_("Remove a module."));
|
||||
|
|
|
@ -1010,8 +1010,6 @@ GRUB_MOD_INIT(pgp)
|
|||
|
||||
GRUB_MOD_FINI(pgp)
|
||||
{
|
||||
grub_register_variable_hook ("check_signatures", NULL, NULL);
|
||||
grub_env_unset ("check_signatures");
|
||||
grub_verifier_unregister (&grub_pubkey_verifier);
|
||||
grub_unregister_extcmd (cmd);
|
||||
grub_unregister_extcmd (cmd_trust);
|
||||
|
|
|
@ -25,7 +25,6 @@
|
|||
#include <grub/types.h>
|
||||
#include <grub/extcmd.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -38,14 +37,13 @@ static const struct grub_arg_option options[] =
|
|||
static char *
|
||||
grub_getline (int silent)
|
||||
{
|
||||
grub_size_t i;
|
||||
int i;
|
||||
char *line;
|
||||
char *tmp;
|
||||
int c;
|
||||
grub_size_t alloc_size;
|
||||
|
||||
i = 0;
|
||||
line = grub_malloc (1 + sizeof('\0'));
|
||||
line = grub_malloc (1 + i + sizeof('\0'));
|
||||
if (! line)
|
||||
return NULL;
|
||||
|
||||
|
@ -61,17 +59,8 @@ grub_getline (int silent)
|
|||
line[i] = (char) c;
|
||||
if (!silent)
|
||||
grub_printf ("%c", c);
|
||||
if (grub_add (i, 1, &i))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow is detected"));
|
||||
return NULL;
|
||||
}
|
||||
if (grub_add (i, 1 + sizeof('\0'), &alloc_size))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow is detected"));
|
||||
return NULL;
|
||||
}
|
||||
tmp = grub_realloc (line, alloc_size);
|
||||
i++;
|
||||
tmp = grub_realloc (line, 1 + i + sizeof('\0'));
|
||||
if (! tmp)
|
||||
{
|
||||
grub_free (line);
|
||||
|
|
|
@ -54,41 +54,6 @@ struct search_ctx
|
|||
int is_cache;
|
||||
};
|
||||
|
||||
static bool
|
||||
is_unencrypted_disk (grub_disk_t disk)
|
||||
{
|
||||
grub_command_t cmd;
|
||||
char *disk_str;
|
||||
int disk_str_len;
|
||||
int res;
|
||||
|
||||
if (disk->dev->id == GRUB_DISK_DEVICE_CRYPTODISK_ID)
|
||||
return false; /* This is (crypto) disk. */
|
||||
|
||||
if (disk->dev->id == GRUB_DISK_DEVICE_DISKFILTER_ID)
|
||||
{
|
||||
char opt[] = "--quiet";
|
||||
char *args[2];
|
||||
|
||||
cmd = grub_command_find ("cryptocheck");
|
||||
if (cmd == NULL) /* No diskfilter module loaded for some reason. */
|
||||
return true;
|
||||
|
||||
disk_str_len = grub_strlen (disk->name) + 2 + 1;
|
||||
disk_str = grub_malloc (disk_str_len);
|
||||
if (disk_str == NULL) /* Something is wrong, better report as unencrypted. */
|
||||
return true;
|
||||
|
||||
grub_snprintf (disk_str, disk_str_len, "(%s)", disk->name);
|
||||
args[0] = opt;
|
||||
args[1] = disk_str;
|
||||
res = cmd->func (cmd, 2, args);
|
||||
grub_free (disk_str);
|
||||
return (res != GRUB_ERR_NONE) ? true : false; /* GRUB_ERR_NONE for encrypted. */
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/* Helper for FUNC_NAME. */
|
||||
static int
|
||||
iterate_device (const char *name, void *data)
|
||||
|
@ -121,26 +86,6 @@ iterate_device (const char *name, void *data)
|
|||
grub_device_close (dev);
|
||||
}
|
||||
|
||||
/* Limit to encrypted disks when requested. */
|
||||
if (ctx->flags & SEARCH_FLAGS_CRYPTODISK_ONLY)
|
||||
{
|
||||
grub_device_t dev;
|
||||
|
||||
dev = grub_device_open (name);
|
||||
if (dev == NULL)
|
||||
{
|
||||
grub_errno = GRUB_ERR_NONE;
|
||||
return 0;
|
||||
}
|
||||
if (dev->disk == NULL || is_unencrypted_disk (dev->disk) == true)
|
||||
{
|
||||
grub_device_close (dev);
|
||||
grub_errno = GRUB_ERR_NONE;
|
||||
return 0;
|
||||
}
|
||||
grub_device_close (dev);
|
||||
}
|
||||
|
||||
#ifdef DO_SEARCH_FS_UUID
|
||||
#define compare_fn grub_strcasecmp
|
||||
#else
|
||||
|
|
|
@ -41,7 +41,6 @@ static const struct grub_arg_option options[] =
|
|||
ARG_TYPE_STRING},
|
||||
{"no-floppy", 'n', 0, N_("Do not probe any floppy drive."), 0, 0},
|
||||
{"efidisk-only", 0, 0, N_("Only probe EFI disks."), 0, 0},
|
||||
{"cryptodisk-only", 0, 0, N_("Only probe encrypted disks."), 0, 0},
|
||||
{"hint", 'h', GRUB_ARG_OPTION_REPEATABLE,
|
||||
N_("First try the device HINT. If HINT ends in comma, "
|
||||
"also try subpartitions"), N_("HINT"), ARG_TYPE_STRING},
|
||||
|
@ -76,7 +75,6 @@ enum options
|
|||
SEARCH_SET,
|
||||
SEARCH_NO_FLOPPY,
|
||||
SEARCH_EFIDISK_ONLY,
|
||||
SEARCH_CRYPTODISK_ONLY,
|
||||
SEARCH_HINT,
|
||||
SEARCH_HINT_IEEE1275,
|
||||
SEARCH_HINT_BIOS,
|
||||
|
@ -191,9 +189,6 @@ grub_cmd_search (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
if (state[SEARCH_EFIDISK_ONLY].set)
|
||||
flags |= SEARCH_FLAGS_EFIDISK_ONLY;
|
||||
|
||||
if (state[SEARCH_CRYPTODISK_ONLY].set)
|
||||
flags |= SEARCH_FLAGS_CRYPTODISK_ONLY;
|
||||
|
||||
if (state[SEARCH_LABEL].set)
|
||||
grub_search_label (id, var, flags, hints, nhints);
|
||||
else if (state[SEARCH_FS_UUID].set)
|
||||
|
@ -215,7 +210,7 @@ GRUB_MOD_INIT(search)
|
|||
cmd =
|
||||
grub_register_extcmd ("search", grub_cmd_search,
|
||||
GRUB_COMMAND_FLAG_EXTRACTOR | GRUB_COMMAND_ACCEPT_DASH,
|
||||
N_("[-f|-l|-u|-s|-n] [--cryptodisk-only] [--hint HINT [--hint HINT] ...]"
|
||||
N_("[-f|-l|-u|-s|-n] [--hint HINT [--hint HINT] ...]"
|
||||
" NAME"),
|
||||
N_("Search devices by file, filesystem label"
|
||||
" or filesystem UUID."
|
||||
|
|
|
@ -29,9 +29,6 @@
|
|||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
/* Set a limit on recursion to avoid stack overflow. */
|
||||
#define MAX_TEST_RECURSION_DEPTH 100
|
||||
|
||||
/* A simple implementation for signed numbers. */
|
||||
static int
|
||||
grub_strtosl (char *arg, const char ** const end, int base)
|
||||
|
@ -153,7 +150,7 @@ get_fileinfo (char *path, struct test_parse_ctx *ctx)
|
|||
|
||||
/* Parse a test expression starting from *argn. */
|
||||
static int
|
||||
test_parse (char **args, int *argn, int argc, int *depth)
|
||||
test_parse (char **args, int *argn, int argc)
|
||||
{
|
||||
struct test_parse_ctx ctx = {
|
||||
.and = 1,
|
||||
|
@ -390,24 +387,13 @@ test_parse (char **args, int *argn, int argc, int *depth)
|
|||
if (grub_strcmp (args[*argn], ")") == 0)
|
||||
{
|
||||
(*argn)++;
|
||||
if (*depth > 0)
|
||||
(*depth)--;
|
||||
|
||||
return ctx.or || ctx.and;
|
||||
}
|
||||
/* Recursively invoke if parenthesis. */
|
||||
if (grub_strcmp (args[*argn], "(") == 0)
|
||||
{
|
||||
(*argn)++;
|
||||
|
||||
if (++(*depth) > MAX_TEST_RECURSION_DEPTH)
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("max recursion depth exceeded"));
|
||||
depth--;
|
||||
return ctx.or || ctx.and;
|
||||
}
|
||||
|
||||
update_val (test_parse (args, argn, argc, depth), &ctx);
|
||||
update_val (test_parse (args, argn, argc), &ctx);
|
||||
continue;
|
||||
}
|
||||
|
||||
|
@ -442,12 +428,11 @@ grub_cmd_test (grub_command_t cmd __attribute__ ((unused)),
|
|||
int argc, char **args)
|
||||
{
|
||||
int argn = 0;
|
||||
int depth = 0;
|
||||
|
||||
if (argc >= 1 && grub_strcmp (args[argc - 1], "]") == 0)
|
||||
argc--;
|
||||
|
||||
return test_parse (args, &argn, argc, &depth) ? GRUB_ERR_NONE
|
||||
return test_parse (args, &argn, argc) ? GRUB_ERR_NONE
|
||||
: grub_error (GRUB_ERR_TEST_FAILURE, N_("false"));
|
||||
}
|
||||
|
||||
|
|
|
@ -36,16 +36,6 @@ grub_tpm_verify_init (grub_file_t io,
|
|||
{
|
||||
*context = io->name;
|
||||
*flags |= GRUB_VERIFY_FLAGS_SINGLE_CHUNK;
|
||||
|
||||
/*
|
||||
* The loopback image is mapped as a disk allowing it to function like
|
||||
* a block device. However, we measure files read from the block device
|
||||
* not the device itself. For example, we don't measure block devices like
|
||||
* hd0 disk directly. This process is crucial to prevent out-of-memory
|
||||
* errors as loopback images are inherently large.
|
||||
*/
|
||||
if ((type & GRUB_FILE_TYPE_MASK) == GRUB_FILE_TYPE_LOOPBACK)
|
||||
*flags = GRUB_VERIFY_FLAGS_SKIP_VERIFICATION;
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
|
|
|
@ -1,127 +0,0 @@
|
|||
/*
|
||||
* GRUB -- GRand Unified Bootloader
|
||||
* Copyright (C) 2022 Microsoft Corporation
|
||||
* Copyright (C) 2024 Free Software Foundation, Inc.
|
||||
*
|
||||
* GRUB is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GRUB is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GRUB. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include <grub/err.h>
|
||||
#include <grub/mm.h>
|
||||
#include <grub/misc.h>
|
||||
|
||||
#include "tpm2_args.h"
|
||||
|
||||
grub_err_t
|
||||
grub_tpm2_protector_parse_pcrs (char *value, grub_uint8_t *pcrs,
|
||||
grub_uint8_t *pcr_count)
|
||||
{
|
||||
char *current_pcr = value;
|
||||
char *next_pcr;
|
||||
const char *pcr_end;
|
||||
grub_uint64_t pcr;
|
||||
grub_uint8_t i;
|
||||
|
||||
if (grub_strlen (value) == 0)
|
||||
return GRUB_ERR_BAD_ARGUMENT;
|
||||
|
||||
*pcr_count = 0;
|
||||
for (i = 0; i < TPM_MAX_PCRS; i++)
|
||||
{
|
||||
next_pcr = grub_strchr (current_pcr, ',');
|
||||
if (next_pcr == current_pcr)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, N_("empty entry in PCR list"));
|
||||
if (next_pcr != NULL)
|
||||
*next_pcr = '\0';
|
||||
|
||||
pcr = grub_strtoul (current_pcr, &pcr_end, 10);
|
||||
if (*current_pcr == '\0' || *pcr_end != '\0')
|
||||
return grub_error (GRUB_ERR_BAD_NUMBER, N_("entry '%s' in PCR list is not a number"), current_pcr);
|
||||
|
||||
if (pcr > TPM_MAX_PCRS - 1)
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, N_("entry %llu in PCR list is too large to be a PCR number, PCR numbers range from 0 to %u"), (unsigned long long)pcr, TPM_MAX_PCRS - 1);
|
||||
|
||||
pcrs[i] = (grub_uint8_t) pcr;
|
||||
++(*pcr_count);
|
||||
|
||||
if (next_pcr == NULL)
|
||||
break;
|
||||
|
||||
current_pcr = next_pcr + 1;
|
||||
if (*current_pcr == '\0')
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, N_("trailing comma at the end of PCR list"));
|
||||
}
|
||||
|
||||
if (i == TPM_MAX_PCRS)
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, N_("too many PCRs in PCR list, the maximum number of PCRs is %u"), TPM_MAX_PCRS);
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_tpm2_protector_parse_asymmetric (const char *value,
|
||||
grub_srk_type_t *srk_type)
|
||||
{
|
||||
if (grub_strcasecmp (value, "ECC") == 0 ||
|
||||
grub_strcasecmp (value, "ECC_NIST_P256") == 0)
|
||||
{
|
||||
srk_type->type = TPM_ALG_ECC;
|
||||
srk_type->detail.ecc_curve = TPM_ECC_NIST_P256;
|
||||
}
|
||||
else if (grub_strcasecmp (value, "RSA") == 0 ||
|
||||
grub_strcasecmp (value, "RSA2048") == 0)
|
||||
{
|
||||
srk_type->type = TPM_ALG_RSA;
|
||||
srk_type->detail.rsa_bits = 2048;
|
||||
}
|
||||
else
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, N_("value '%s' is not a valid asymmetric key type"), value);
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_tpm2_protector_parse_bank (const char *value, TPM_ALG_ID_t *bank)
|
||||
{
|
||||
if (grub_strcasecmp (value, "SHA1") == 0)
|
||||
*bank = TPM_ALG_SHA1;
|
||||
else if (grub_strcasecmp (value, "SHA256") == 0)
|
||||
*bank = TPM_ALG_SHA256;
|
||||
else if (grub_strcasecmp (value, "SHA384") == 0)
|
||||
*bank = TPM_ALG_SHA384;
|
||||
else if (grub_strcasecmp (value, "SHA512") == 0)
|
||||
*bank = TPM_ALG_SHA512;
|
||||
else
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, N_("value '%s' is not a valid PCR bank"), value);
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_tpm2_protector_parse_tpm_handle (const char *value, TPM_HANDLE_t *handle)
|
||||
{
|
||||
grub_uint64_t num;
|
||||
const char *str_end;
|
||||
|
||||
num = grub_strtoul (value, &str_end, 0);
|
||||
if (*value == '\0' || *str_end != '\0')
|
||||
return grub_error (GRUB_ERR_BAD_NUMBER, N_("TPM handle value '%s' is not a number"), value);
|
||||
|
||||
if (num > GRUB_UINT_MAX)
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, N_("value %llu is too large to be a TPM handle, TPM handles are unsigned 32-bit integers"), (unsigned long long)num);
|
||||
|
||||
*handle = (TPM_HANDLE_t) num;
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
File diff suppressed because it is too large
Load diff
|
@ -1,36 +0,0 @@
|
|||
/*
|
||||
* GRUB -- GRand Unified Bootloader
|
||||
* Copyright (C) 2022 Microsoft Corporation
|
||||
* Copyright (C) 2024 Free Software Foundation, Inc.
|
||||
*
|
||||
* GRUB is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GRUB is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GRUB. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef GRUB_TPM2_TPM2_HEADER
|
||||
#define GRUB_TPM2_TPM2_HEADER 1
|
||||
|
||||
#include <tss2_types.h>
|
||||
#include <tss2_structs.h>
|
||||
#include <tpm2_cmd.h>
|
||||
|
||||
/* Well-Known Windows SRK handle */
|
||||
#define TPM2_SRK_HANDLE 0x81000001
|
||||
|
||||
struct tpm2_sealed_key {
|
||||
TPM2B_PUBLIC_t public;
|
||||
TPM2B_PRIVATE_t private;
|
||||
};
|
||||
typedef struct tpm2_sealed_key tpm2_sealed_key_t;
|
||||
|
||||
#endif /* ! GRUB_TPM2_TPM2_HEADER */
|
|
@ -1,49 +0,0 @@
|
|||
/*
|
||||
* GRUB -- GRand Unified Bootloader
|
||||
* Copyright (C) 2022 Microsoft Corporation
|
||||
* Copyright (C) 2024 Free Software Foundation, Inc.
|
||||
*
|
||||
* GRUB is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GRUB is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GRUB. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef GRUB_TPM2_INTERNAL_ARGS_HEADER
|
||||
#define GRUB_TPM2_INTERNAL_ARGS_HEADER 1
|
||||
|
||||
#include <grub/err.h>
|
||||
|
||||
#include "tpm2.h"
|
||||
|
||||
struct grub_srk_type
|
||||
{
|
||||
TPMI_ALG_PUBLIC_t type;
|
||||
union {
|
||||
TPM_KEY_BITS_t rsa_bits;
|
||||
TPM_ECC_CURVE_t ecc_curve;
|
||||
} detail;
|
||||
};
|
||||
typedef struct grub_srk_type grub_srk_type_t;
|
||||
|
||||
extern grub_err_t
|
||||
grub_tpm2_protector_parse_pcrs (char *value, grub_uint8_t *pcrs, grub_uint8_t *pcr_count);
|
||||
|
||||
extern grub_err_t
|
||||
grub_tpm2_protector_parse_asymmetric (const char *value, grub_srk_type_t *srk_type);
|
||||
|
||||
extern grub_err_t
|
||||
grub_tpm2_protector_parse_bank (const char *value, TPM_ALG_ID_t *bank);
|
||||
|
||||
extern grub_err_t
|
||||
grub_tpm2_protector_parse_tpm_handle (const char *value, TPM_HANDLE_t *handle);
|
||||
|
||||
#endif /* ! GRUB_TPM2_INTERNAL_ARGS_HEADER */
|
|
@ -1,49 +0,0 @@
|
|||
--
|
||||
-- GRUB: GRand Unified Bootloader
|
||||
-- Copyright (C) 2024 Free Software Foundation, Inc.
|
||||
--
|
||||
-- GRUB is free software: you can redistribute it and/or modify
|
||||
-- it under the terms of the GNU General Public License as published by
|
||||
-- the Free Software Foundation, either version 3 of the License, or
|
||||
-- (at your option) any later version.
|
||||
--
|
||||
-- GRUB is distributed in the hope that it will be useful,
|
||||
-- but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
-- GNU General Public License for more details.
|
||||
--
|
||||
-- You should have received a copy of the GNU General Public License
|
||||
-- along with GRUB. If not, see <http://www.gnu.org/licenses/>.
|
||||
--
|
||||
-- This file describes TPM 2.0 Key File format for libtasn1.
|
||||
-- To generate tpm2key_asn1_tab.c: asn1Parser tpm2key.asn
|
||||
--
|
||||
TPM2KEY {}
|
||||
DEFINITIONS IMPLICIT TAGS ::=
|
||||
|
||||
BEGIN
|
||||
|
||||
TPMPolicy ::= SEQUENCE {
|
||||
CommandCode [0] EXPLICIT INTEGER,
|
||||
CommandPolicy [1] EXPLICIT OCTET STRING
|
||||
}
|
||||
|
||||
TPMAuthPolicy ::= SEQUENCE {
|
||||
Name [0] EXPLICIT UTF8String OPTIONAL,
|
||||
Policy [1] EXPLICIT SEQUENCE OF TPMPolicy
|
||||
}
|
||||
|
||||
TPMKey ::= SEQUENCE {
|
||||
type OBJECT IDENTIFIER,
|
||||
emptyAuth [0] EXPLICIT BOOLEAN OPTIONAL,
|
||||
policy [1] EXPLICIT SEQUENCE OF TPMPolicy OPTIONAL,
|
||||
secret [2] EXPLICIT OCTET STRING OPTIONAL,
|
||||
authPolicy [3] EXPLICIT SEQUENCE OF TPMAuthPolicy OPTIONAL,
|
||||
description [4] EXPLICIT UTF8String OPTIONAL,
|
||||
rsaParent [5] EXPLICIT BOOLEAN OPTIONAL,
|
||||
parent INTEGER,
|
||||
pubkey OCTET STRING,
|
||||
privkey OCTET STRING
|
||||
}
|
||||
|
||||
END
|
|
@ -1,499 +0,0 @@
|
|||
/*
|
||||
* GRUB -- GRand Unified Bootloader
|
||||
* Copyright (C) 2023 SUSE LLC
|
||||
* Copyright (C) 2024 Free Software Foundation, Inc.
|
||||
*
|
||||
* GRUB is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GRUB is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GRUB. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include <grub/list.h>
|
||||
#include <grub/misc.h>
|
||||
#include <grub/mm.h>
|
||||
|
||||
#include <tss2_buffer.h>
|
||||
|
||||
#include "tpm2key.h"
|
||||
|
||||
extern asn1_static_node tpm2key_asn1_tab[];
|
||||
const char *sealed_key_oid = "2.23.133.10.1.5";
|
||||
|
||||
static int
|
||||
asn1_allocate_and_read (asn1_node node, const char *name, void **content, grub_size_t *content_size)
|
||||
{
|
||||
grub_uint8_t *tmpstr = NULL;
|
||||
int tmpstr_size = 0;
|
||||
int ret;
|
||||
|
||||
if (content == NULL)
|
||||
return ASN1_MEM_ERROR;
|
||||
|
||||
ret = asn1_read_value (node, name, NULL, &tmpstr_size);
|
||||
if (ret != ASN1_MEM_ERROR)
|
||||
return ret;
|
||||
|
||||
tmpstr = grub_malloc (tmpstr_size);
|
||||
if (tmpstr == NULL)
|
||||
return ASN1_MEM_ERROR;
|
||||
|
||||
ret = asn1_read_value (node, name, tmpstr, &tmpstr_size);
|
||||
if (ret != ASN1_SUCCESS)
|
||||
return ret;
|
||||
|
||||
*content = tmpstr;
|
||||
*content_size = tmpstr_size;
|
||||
|
||||
return ASN1_SUCCESS;
|
||||
}
|
||||
|
||||
static int
|
||||
asn1_read_uint32 (asn1_node node, const char *name, grub_uint32_t *out)
|
||||
{
|
||||
grub_uint32_t tmp = 0;
|
||||
grub_uint8_t *ptr;
|
||||
void *data = NULL;
|
||||
grub_size_t data_size;
|
||||
int ret;
|
||||
|
||||
ret = asn1_allocate_and_read (node, name, &data, &data_size);
|
||||
if (ret != ASN1_SUCCESS)
|
||||
return ret;
|
||||
|
||||
/*
|
||||
* ASN.1 INTEGER is encoded in the following format:
|
||||
*
|
||||
* TAG LENGTH OCTECTS
|
||||
*
|
||||
* The integer TAG is 02 and LENGTH is the number of followed OCTECTS in
|
||||
* big endian. For example:
|
||||
*
|
||||
* 0x1: 02 01 01
|
||||
* 0xabcd: 02 02 ab cd
|
||||
*
|
||||
* To decribe 0x1, it only takes 1 octect, so LENGTH is 0x01 and the
|
||||
* octect is 0x01. On the other hand, 0xabcd requires 2 octects: 'ab" and
|
||||
* 'cd', so LENGTH is 0x02.
|
||||
*
|
||||
* This function only expects a uint32 integer, so it rejects any integer
|
||||
* containing more than 4 octects.
|
||||
*/
|
||||
if (data_size > 4)
|
||||
{
|
||||
ret = ASN1_MEM_ERROR;
|
||||
goto error;
|
||||
}
|
||||
|
||||
/* Copy the octects into 'tmp' to make it a big-endian uint32 */
|
||||
ptr = (grub_uint8_t *) &tmp + (4 - data_size);
|
||||
grub_memcpy (ptr, data, data_size);
|
||||
|
||||
/* Convert the big-endian integer to host uint32 */
|
||||
tmp = grub_be_to_cpu32 (tmp);
|
||||
|
||||
*out = tmp;
|
||||
error:
|
||||
if (data)
|
||||
grub_free (data);
|
||||
return ret;
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_tpm2key_start_parsing (asn1_node *parsed_tpm2key, void *data, grub_size_t size)
|
||||
{
|
||||
asn1_node tpm2key;
|
||||
asn1_node tpm2key_asn1 = NULL;
|
||||
void *type_oid = NULL;
|
||||
grub_size_t type_oid_size = 0;
|
||||
void *empty_auth = NULL;
|
||||
grub_size_t empty_auth_size = 0;
|
||||
int tmp_size = 0;
|
||||
int ret;
|
||||
grub_err_t err;
|
||||
|
||||
/*
|
||||
* TPMKey ::= SEQUENCE {
|
||||
* type OBJECT IDENTIFIER,
|
||||
* emptyAuth [0] EXPLICIT BOOLEAN OPTIONAL,
|
||||
* policy [1] EXPLICIT SEQUENCE OF TPMPolicy OPTIONAL,
|
||||
* secret [2] EXPLICIT OCTET STRING OPTIONAL,
|
||||
* authPolicy [3] EXPLICIT SEQUENCE OF TPMAuthPolicy OPTIONAL,
|
||||
* description [4] EXPLICIT UTF8String OPTIONAL,
|
||||
* rsaParent [5] EXPLICIT BOOLEAN OPTIONAL,
|
||||
* parent INTEGER,
|
||||
* pubkey OCTET STRING,
|
||||
* privkey OCTET STRING
|
||||
* }
|
||||
*/
|
||||
ret = asn1_array2tree (tpm2key_asn1_tab, &tpm2key_asn1, NULL);
|
||||
if (ret != ASN1_SUCCESS)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, "failed to parse TPM2KEY ASN.1 array");
|
||||
|
||||
ret = asn1_create_element (tpm2key_asn1, "TPM2KEY.TPMKey", &tpm2key);
|
||||
if (ret != ASN1_SUCCESS)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, "failed to create TPM2KEY.TPMKey");
|
||||
|
||||
ret = asn1_der_decoding (&tpm2key, data, size, NULL);
|
||||
if (ret != ASN1_SUCCESS)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, "failed to decode TPM2KEY DER");
|
||||
|
||||
/* Check if 'type' is Sealed Key or not */
|
||||
ret = asn1_allocate_and_read (tpm2key, "type", &type_oid, &type_oid_size);
|
||||
if (ret != ASN1_SUCCESS)
|
||||
return grub_error (GRUB_ERR_BAD_FILE_TYPE, "not a valid TPM2KEY file");
|
||||
|
||||
if (grub_memcmp (sealed_key_oid, type_oid, type_oid_size) != 0)
|
||||
{
|
||||
err = grub_error (GRUB_ERR_BAD_FILE_TYPE, "not a valid TPM2KEY file");
|
||||
goto error;
|
||||
}
|
||||
|
||||
/* 'emptyAuth' must be 'TRUE' since we don't support password authorization */
|
||||
ret = asn1_allocate_and_read (tpm2key, "emptyAuth", &empty_auth, &empty_auth_size);
|
||||
if (ret != ASN1_SUCCESS || grub_strncmp ("TRUE", empty_auth, empty_auth_size) != 0)
|
||||
{
|
||||
err = grub_error (GRUB_ERR_BAD_ARGUMENT, "emptyAuth not TRUE");
|
||||
goto error;
|
||||
}
|
||||
|
||||
/* 'secret' should not be in a sealed key */
|
||||
ret = asn1_read_value (tpm2key, "secret", NULL, &tmp_size);
|
||||
if (ret != ASN1_ELEMENT_NOT_FOUND)
|
||||
{
|
||||
err = grub_error (GRUB_ERR_BAD_ARGUMENT, "\"secret\" not allowed for Sealed Key");
|
||||
goto error;
|
||||
}
|
||||
|
||||
*parsed_tpm2key = tpm2key;
|
||||
|
||||
err = GRUB_ERR_NONE;
|
||||
|
||||
error:
|
||||
grub_free (type_oid);
|
||||
grub_free (empty_auth);
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
void
|
||||
grub_tpm2key_end_parsing (asn1_node tpm2key)
|
||||
{
|
||||
asn1_delete_structure (&tpm2key);
|
||||
tpm2key = NULL;
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_tpm2key_get_rsaparent (asn1_node tpm2key, grub_uint8_t *rsaparent)
|
||||
{
|
||||
void *bool_str = NULL;
|
||||
grub_size_t bool_str_size = 0;
|
||||
int ret;
|
||||
|
||||
if (rsaparent == NULL)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, "NULL pointer detected");
|
||||
|
||||
if (tpm2key == NULL)
|
||||
return grub_error (GRUB_ERR_READ_ERROR, "invalid parent node");
|
||||
|
||||
ret = asn1_allocate_and_read (tpm2key, "rsaParent", &bool_str, &bool_str_size);
|
||||
if (ret == ASN1_SUCCESS)
|
||||
{
|
||||
if (grub_strncmp ("TRUE", bool_str, bool_str_size) == 0)
|
||||
*rsaparent = 1;
|
||||
else
|
||||
*rsaparent = 0;
|
||||
}
|
||||
else if (ret == ASN1_ELEMENT_NOT_FOUND)
|
||||
*rsaparent = 0;
|
||||
else
|
||||
return grub_error (GRUB_ERR_READ_ERROR, "failed to retrieve rsaParent");
|
||||
|
||||
grub_free (bool_str);
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_tpm2key_get_parent (asn1_node tpm2key, grub_uint32_t *parent)
|
||||
{
|
||||
int ret;
|
||||
|
||||
if (parent == NULL)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, "NULL pointer detected");
|
||||
|
||||
if (tpm2key == NULL)
|
||||
return grub_error (GRUB_ERR_READ_ERROR, "invalid parent node");
|
||||
|
||||
ret = asn1_read_uint32 (tpm2key, "parent", parent);
|
||||
if (ret != ASN1_SUCCESS)
|
||||
return grub_error (GRUB_ERR_READ_ERROR, "failed to retrieve parent");
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
static grub_err_t
|
||||
tpm2key_get_octstring (asn1_node tpm2key, const char *name, void **data, grub_size_t *size)
|
||||
{
|
||||
int ret;
|
||||
|
||||
if (name == NULL || data == NULL || size == NULL)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, "invalid parameter(s)");
|
||||
|
||||
if (tpm2key == NULL)
|
||||
return grub_error (GRUB_ERR_READ_ERROR, "invalid %s node", name);
|
||||
|
||||
ret = asn1_allocate_and_read (tpm2key, name, data, size);
|
||||
if (ret != ASN1_SUCCESS)
|
||||
return grub_error (GRUB_ERR_READ_ERROR, "failed to retrieve %s", name);
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_tpm2key_get_pubkey (asn1_node tpm2key, void **data, grub_size_t *size)
|
||||
{
|
||||
return tpm2key_get_octstring (tpm2key, "pubkey", data, size);
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_tpm2key_get_privkey (asn1_node tpm2key, void **data, grub_size_t *size)
|
||||
{
|
||||
return tpm2key_get_octstring (tpm2key, "privkey", data, size);
|
||||
}
|
||||
|
||||
/*
|
||||
* The maximum and minimum number of elements for 'policy' and 'authPolicy' sequences
|
||||
*
|
||||
* Although there is no limit for the number of sequences elements, we set the upper
|
||||
* bound to 99 to make it easier to implement the code.
|
||||
*
|
||||
* Any 'policy' or 'authPolicy' contains more than 99 commands/policies would become
|
||||
* extremely complex to manage so it is impractical to support such use case.
|
||||
*/
|
||||
#define TPM2KEY_ELEMENTS_MAX 99
|
||||
#define TPM2KEY_ELEMENTS_MIN 1
|
||||
|
||||
/*
|
||||
* The string to fetch 'Policy' from 'authPolicy':
|
||||
* authPolicy.?XX.Policy
|
||||
*/
|
||||
#define AUTHPOLICY_POL_MAX_STR "authPolicy.?XX.Policy"
|
||||
#define AUTHPOLICY_POL_MAX (sizeof (AUTHPOLICY_POL_MAX_STR))
|
||||
|
||||
/*
|
||||
* Expected strings for CommandCode and CommandPolicy:
|
||||
* policy.?XX.CommandCode
|
||||
* policy.?XX.CommandPolicy
|
||||
* authPolicy.?XX.Policy.?YY.CommandCode
|
||||
* authPolicy.?XX.Policy.?YY.CommandPolicy
|
||||
*/
|
||||
#define CMD_CODE_MAX_STR AUTHPOLICY_POL_MAX_STR".?YY.CommandCode"
|
||||
#define CMD_POL_MAX_STR AUTHPOLICY_POL_MAX_STR".?YY.CommandPolicy"
|
||||
#define CMD_CODE_MAX (sizeof (CMD_CODE_MAX_STR))
|
||||
#define CMD_POL_MAX (sizeof (CMD_POL_MAX_STR))
|
||||
|
||||
static int
|
||||
tpm2key_get_policy_seq (asn1_node tpm2key, const char *prefix,
|
||||
tpm2key_policy_t *policy_seq)
|
||||
{
|
||||
tpm2key_policy_t tmp_seq = NULL;
|
||||
tpm2key_policy_t policy = NULL;
|
||||
int policy_n;
|
||||
char cmd_code[CMD_CODE_MAX];
|
||||
char cmd_pol[CMD_POL_MAX];
|
||||
grub_size_t cmd_policy_len;
|
||||
int i;
|
||||
int ret;
|
||||
|
||||
ret = asn1_number_of_elements (tpm2key, prefix, &policy_n);
|
||||
if (ret != ASN1_SUCCESS)
|
||||
return ret;
|
||||
|
||||
/*
|
||||
* Limit the number of policy commands to two digits (99)
|
||||
* Although there is no upper bound for the number of policy commands,
|
||||
* in practice, it takes one or two policy commands to unseal the key,
|
||||
* so the 99 commands limit is more than enough.
|
||||
*/
|
||||
if (policy_n > TPM2KEY_ELEMENTS_MAX || policy_n < TPM2KEY_ELEMENTS_MIN)
|
||||
return ASN1_VALUE_NOT_VALID;
|
||||
|
||||
/*
|
||||
* Iterate the policy commands backwards since grub_list_push() prepends
|
||||
* the item into the list.
|
||||
*/
|
||||
for (i = policy_n; i >= 1; i--) {
|
||||
policy = grub_zalloc (sizeof (struct tpm2key_policy));
|
||||
if (policy == NULL)
|
||||
{
|
||||
ret = ASN1_MEM_ALLOC_ERROR;
|
||||
goto error;
|
||||
}
|
||||
grub_snprintf (cmd_code, CMD_CODE_MAX, "%s.?%d.CommandCode", prefix, i);
|
||||
grub_snprintf (cmd_pol, CMD_POL_MAX, "%s.?%d.CommandPolicy", prefix, i);
|
||||
|
||||
/* CommandCode [0] EXPLICIT INTEGER */
|
||||
ret = asn1_read_uint32 (tpm2key, cmd_code, &policy->cmd_code);
|
||||
if (ret != ASN1_SUCCESS)
|
||||
return ret;
|
||||
|
||||
/* CommandPolicy [1] EXPLICIT OCTET STRING */
|
||||
ret = tpm2key_get_octstring (tpm2key, cmd_pol, &policy->cmd_policy,
|
||||
&cmd_policy_len);
|
||||
if (ret != ASN1_SUCCESS)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
else if (cmd_policy_len > GRUB_TPM2_BUFFER_CAPACITY)
|
||||
{
|
||||
/*
|
||||
* CommandPolicy is the marshalled parameters for the TPM command so
|
||||
* it should not be larger than the maximum TPM2 buffer.
|
||||
*/
|
||||
ret = ASN1_VALUE_NOT_VALID;
|
||||
goto error;
|
||||
}
|
||||
policy->cmd_policy_len = (grub_uint16_t)cmd_policy_len;
|
||||
|
||||
/* Prepend the policy command into the sequence */
|
||||
grub_list_push (GRUB_AS_LIST_P (&tmp_seq), GRUB_AS_LIST (policy));
|
||||
}
|
||||
|
||||
*policy_seq = tmp_seq;
|
||||
|
||||
return ASN1_SUCCESS;
|
||||
|
||||
error:
|
||||
if (policy != NULL)
|
||||
{
|
||||
grub_free (policy->cmd_policy);
|
||||
grub_free (policy);
|
||||
}
|
||||
grub_tpm2key_free_policy_seq (tmp_seq);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_tpm2key_get_policy_seq (asn1_node tpm2key, tpm2key_policy_t *policy_seq)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret = tpm2key_get_policy_seq (tpm2key, "policy", policy_seq);
|
||||
if (ret == ASN1_ELEMENT_NOT_FOUND)
|
||||
{
|
||||
/* "policy" is optional, so it may not be available */
|
||||
*policy_seq = NULL;
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
else if (ret != ASN1_SUCCESS)
|
||||
return grub_error (GRUB_ERR_READ_ERROR, "failed to retrieve policy");
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
void
|
||||
grub_tpm2key_free_policy_seq (tpm2key_policy_t policy_seq)
|
||||
{
|
||||
tpm2key_policy_t policy;
|
||||
tpm2key_policy_t next;
|
||||
|
||||
if (policy_seq == NULL)
|
||||
return;
|
||||
|
||||
FOR_LIST_ELEMENTS_SAFE (policy, next, policy_seq)
|
||||
{
|
||||
grub_free (policy->cmd_policy);
|
||||
grub_free (policy);
|
||||
}
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_tpm2key_get_authpolicy_seq (asn1_node tpm2key, tpm2key_authpolicy_t *authpol_seq)
|
||||
{
|
||||
tpm2key_authpolicy_t tmp_seq = NULL;
|
||||
tpm2key_authpolicy_t authpol = NULL;
|
||||
int authpol_n;
|
||||
char authpol_pol[AUTHPOLICY_POL_MAX];
|
||||
int i;
|
||||
int ret;
|
||||
grub_err_t err;
|
||||
|
||||
ret = asn1_number_of_elements (tpm2key, "authPolicy", &authpol_n);
|
||||
if (ret == ASN1_ELEMENT_NOT_FOUND)
|
||||
{
|
||||
/* "authPolicy" is optional, so it may not be available */
|
||||
*authpol_seq = NULL;
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
else if (ret != ASN1_SUCCESS)
|
||||
return grub_error (GRUB_ERR_READ_ERROR, "failed to retrieve authPolicy");
|
||||
|
||||
/* Limit the number of authPolicy elements to two digits (99) */
|
||||
if (authpol_n > TPM2KEY_ELEMENTS_MAX || authpol_n < TPM2KEY_ELEMENTS_MIN)
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, "invalid number of authPolicy elements");
|
||||
|
||||
/*
|
||||
* Iterate the authPolicy elements backwards since grub_list_push() prepends
|
||||
* the item into the list.
|
||||
*/
|
||||
for (i = authpol_n; i >= 1; i--) {
|
||||
authpol = grub_zalloc (sizeof (struct tpm2key_authpolicy));
|
||||
if (authpol == NULL)
|
||||
{
|
||||
err = grub_error (GRUB_ERR_OUT_OF_MEMORY, "failed to allocate memory for authPolicy");
|
||||
goto error;
|
||||
}
|
||||
grub_snprintf (authpol_pol, AUTHPOLICY_POL_MAX, "authPolicy.?%d.Policy", i);
|
||||
|
||||
ret = tpm2key_get_policy_seq (tpm2key, authpol_pol, &authpol->policy_seq);
|
||||
if (ret != ASN1_SUCCESS)
|
||||
{
|
||||
err = grub_error (GRUB_ERR_READ_ERROR, "failed to retrieve policy from authPolicy");
|
||||
goto error;
|
||||
}
|
||||
|
||||
/* Prepend the authPolicy element into the sequence */
|
||||
grub_list_push (GRUB_AS_LIST_P (&tmp_seq), GRUB_AS_LIST (authpol));
|
||||
}
|
||||
|
||||
*authpol_seq = tmp_seq;
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
|
||||
error:
|
||||
if (authpol != NULL)
|
||||
{
|
||||
grub_tpm2key_free_policy_seq (authpol->policy_seq);
|
||||
grub_free (authpol);
|
||||
}
|
||||
|
||||
grub_tpm2key_free_authpolicy_seq (tmp_seq);
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
void
|
||||
grub_tpm2key_free_authpolicy_seq (tpm2key_authpolicy_t authpol_seq)
|
||||
{
|
||||
tpm2key_authpolicy_t authpol;
|
||||
tpm2key_authpolicy_t next;
|
||||
|
||||
if (authpol_seq == NULL)
|
||||
return;
|
||||
|
||||
FOR_LIST_ELEMENTS_SAFE (authpol, next, authpol_seq)
|
||||
{
|
||||
grub_tpm2key_free_policy_seq (authpol->policy_seq);
|
||||
grub_free (authpol);
|
||||
}
|
||||
}
|
|
@ -1,87 +0,0 @@
|
|||
/*
|
||||
* GRUB -- GRand Unified Bootloader
|
||||
* Copyright (C) 2023 SUSE LLC
|
||||
* Copyright (C) 2024 Free Software Foundation, Inc.
|
||||
*
|
||||
* GRUB is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GRUB is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GRUB. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef GRUB_TPM2_TPM2KEY_HEADER
|
||||
#define GRUB_TPM2_TPM2KEY_HEADER 1
|
||||
|
||||
#include <grub/types.h>
|
||||
#include <libtasn1.h>
|
||||
|
||||
/*
|
||||
* TPMPolicy ::= SEQUENCE {
|
||||
* CommandCode [0] EXPLICIT INTEGER,
|
||||
* CommandPolicy [1] EXPLICIT OCTET STRING
|
||||
* }
|
||||
*/
|
||||
struct tpm2key_policy {
|
||||
struct tpm2key_policy *next;
|
||||
struct tpm2key_policy **prev;
|
||||
grub_uint32_t cmd_code;
|
||||
void *cmd_policy;
|
||||
grub_uint16_t cmd_policy_len;
|
||||
};
|
||||
typedef struct tpm2key_policy *tpm2key_policy_t;
|
||||
|
||||
/*
|
||||
* TPMAuthPolicy ::= SEQUENCE {
|
||||
* Name [0] EXPLICIT UTF8String OPTIONAL,
|
||||
* Policy [1] EXPLICIT SEQUENCE OF TPMPolicy
|
||||
* }
|
||||
*
|
||||
* Name is not a necessary part to unseal the key. Ignore it.
|
||||
*/
|
||||
struct tpm2key_authpolicy {
|
||||
struct tpm2key_authpolicy *next;
|
||||
struct tpm2key_authpolicy **prev;
|
||||
/* char *name; */
|
||||
tpm2key_policy_t policy_seq;
|
||||
};
|
||||
typedef struct tpm2key_authpolicy *tpm2key_authpolicy_t;
|
||||
|
||||
extern grub_err_t
|
||||
grub_tpm2key_start_parsing (asn1_node *parsed_tpm2key, void *data, grub_size_t size);
|
||||
|
||||
extern void
|
||||
grub_tpm2key_end_parsing (asn1_node tpm2key);
|
||||
|
||||
extern grub_err_t
|
||||
grub_tpm2key_get_rsaparent (asn1_node tpm2key, grub_uint8_t *rsaparent);
|
||||
|
||||
extern grub_err_t
|
||||
grub_tpm2key_get_parent (asn1_node tpm2key, grub_uint32_t *parent);
|
||||
|
||||
extern grub_err_t
|
||||
grub_tpm2key_get_pubkey (asn1_node tpm2key, void **data, grub_size_t *size);
|
||||
|
||||
extern grub_err_t
|
||||
grub_tpm2key_get_privkey (asn1_node tpm2key, void **data, grub_size_t *size);
|
||||
|
||||
extern grub_err_t
|
||||
grub_tpm2key_get_policy_seq (asn1_node tpm2key, tpm2key_policy_t *policy_seq);
|
||||
|
||||
extern void
|
||||
grub_tpm2key_free_policy_seq (tpm2key_policy_t policy_seq);
|
||||
|
||||
extern grub_err_t
|
||||
grub_tpm2key_get_authpolicy_seq (asn1_node tpm2key, tpm2key_authpolicy_t *authpol_seq);
|
||||
|
||||
extern void
|
||||
grub_tpm2key_free_authpolicy_seq (tpm2key_authpolicy_t authpol_seq);
|
||||
|
||||
#endif /* GRUB_TPM2_TPM2KEY_HEADER */
|
|
@ -1,63 +0,0 @@
|
|||
/*
|
||||
* GRUB -- GRand Unified Bootloader
|
||||
* Copyright (C) 2024 Free Software Foundation, Inc.
|
||||
*
|
||||
* GRUB is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GRUB is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GRUB. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/*
|
||||
* This file is generated by 'asn1Parser tpm2key.asn' and the '#include'
|
||||
* headers are replaced with the ones in grub2.
|
||||
* - 'grub/mm.h' for the definition of 'NULL'
|
||||
* - 'libtasn1.h' for the definition of 'asn1_static_node'
|
||||
*/
|
||||
|
||||
#include <grub/mm.h>
|
||||
#include <libtasn1.h>
|
||||
|
||||
const asn1_static_node tpm2key_asn1_tab[] = {
|
||||
{ "TPM2KEY", 536875024, NULL },
|
||||
{ NULL, 1073741836, NULL },
|
||||
{ "TPMPolicy", 1610612741, NULL },
|
||||
{ "CommandCode", 1610620931, NULL },
|
||||
{ NULL, 2056, "0"},
|
||||
{ "CommandPolicy", 536879111, NULL },
|
||||
{ NULL, 2056, "1"},
|
||||
{ "TPMAuthPolicy", 1610612741, NULL },
|
||||
{ "Name", 1610637346, NULL },
|
||||
{ NULL, 2056, "0"},
|
||||
{ "Policy", 536879115, NULL },
|
||||
{ NULL, 1073743880, "1"},
|
||||
{ NULL, 2, "TPMPolicy"},
|
||||
{ "TPMKey", 536870917, NULL },
|
||||
{ "type", 1073741836, NULL },
|
||||
{ "emptyAuth", 1610637316, NULL },
|
||||
{ NULL, 2056, "0"},
|
||||
{ "policy", 1610637323, NULL },
|
||||
{ NULL, 1073743880, "1"},
|
||||
{ NULL, 2, "TPMPolicy"},
|
||||
{ "secret", 1610637319, NULL },
|
||||
{ NULL, 2056, "2"},
|
||||
{ "authPolicy", 1610637323, NULL },
|
||||
{ NULL, 1073743880, "3"},
|
||||
{ NULL, 2, "TPMAuthPolicy"},
|
||||
{ "description", 1610637346, NULL },
|
||||
{ NULL, 2056, "4"},
|
||||
{ "rsaParent", 1610637316, NULL },
|
||||
{ NULL, 2056, "5"},
|
||||
{ "parent", 1073741827, NULL },
|
||||
{ "pubkey", 1073741831, NULL },
|
||||
{ "privkey", 7, NULL },
|
||||
{ NULL, 0, NULL }
|
||||
};
|
|
@ -191,11 +191,6 @@ grub_cmd_videoinfo (grub_command_t cmd __attribute__ ((unused)),
|
|||
/* Don't worry about errors. */
|
||||
grub_errno = GRUB_ERR_NONE;
|
||||
}
|
||||
else if (id != GRUB_VIDEO_DRIVER_NONE)
|
||||
{
|
||||
grub_puts_ (N_(" A video driver is active, cannot initialize this driver until it is deactivated\n"));
|
||||
continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (adapter->init ())
|
||||
|
|
|
@ -152,7 +152,8 @@ struct grub_ahci_device
|
|||
|
||||
static grub_err_t
|
||||
grub_ahci_readwrite_real (struct grub_ahci_device *dev,
|
||||
struct grub_disk_ata_pass_through_parms *parms, int reset);
|
||||
struct grub_disk_ata_pass_through_parms *parms,
|
||||
int spinup, int reset);
|
||||
|
||||
|
||||
enum
|
||||
|
@ -572,7 +573,7 @@ grub_ahci_pciinit (grub_pci_device_t dev,
|
|||
/* struct grub_disk_ata_pass_through_parms parms2;
|
||||
grub_memset (&parms2, 0, sizeof (parms2));
|
||||
parms2.taskfile.cmd = 8;
|
||||
grub_ahci_readwrite_real (dev, &parms2, 1);*/
|
||||
grub_ahci_readwrite_real (dev, &parms2, 1, 1);*/
|
||||
}
|
||||
|
||||
endtime = grub_get_time_ms () + 32000;
|
||||
|
@ -907,14 +908,15 @@ grub_ahci_reset_port (struct grub_ahci_device *dev, int force)
|
|||
dev->hba->ports[dev->port].sata_error = dev->hba->ports[dev->port].sata_error;
|
||||
grub_memset (&parms2, 0, sizeof (parms2));
|
||||
parms2.taskfile.cmd = 8;
|
||||
return grub_ahci_readwrite_real (dev, &parms2, 1);
|
||||
return grub_ahci_readwrite_real (dev, &parms2, 1, 1);
|
||||
}
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
static grub_err_t
|
||||
grub_ahci_readwrite_real (struct grub_ahci_device *dev,
|
||||
struct grub_disk_ata_pass_through_parms *parms, int reset)
|
||||
struct grub_disk_ata_pass_through_parms *parms,
|
||||
int spinup, int reset)
|
||||
{
|
||||
struct grub_pci_dma_chunk *bufc;
|
||||
grub_uint64_t endtime;
|
||||
|
@ -1036,7 +1038,7 @@ grub_ahci_readwrite_real (struct grub_ahci_device *dev,
|
|||
grub_dprintf ("ahci", "AHCI tfd = %x\n",
|
||||
dev->hba->ports[dev->port].task_file_data);
|
||||
|
||||
endtime = grub_get_time_ms () + 20000;
|
||||
endtime = grub_get_time_ms () + (spinup ? 20000 : 20000);
|
||||
while ((dev->hba->ports[dev->port].command_issue & 1))
|
||||
if (grub_get_time_ms () > endtime ||
|
||||
(dev->hba->ports[dev->port].intstatus & GRUB_AHCI_HBA_PORT_IS_FATAL_MASK))
|
||||
|
@ -1095,9 +1097,9 @@ grub_ahci_readwrite_real (struct grub_ahci_device *dev,
|
|||
static grub_err_t
|
||||
grub_ahci_readwrite (grub_ata_t disk,
|
||||
struct grub_disk_ata_pass_through_parms *parms,
|
||||
int spinup __attribute__((__unused__)))
|
||||
int spinup)
|
||||
{
|
||||
return grub_ahci_readwrite_real (disk->data, parms, 0);
|
||||
return grub_ahci_readwrite_real (disk->data, parms, spinup, 0);
|
||||
}
|
||||
|
||||
static grub_err_t
|
||||
|
|
|
@ -112,10 +112,10 @@ grub_ata_identify (struct grub_ata *dev)
|
|||
return grub_atapi_identify (dev);
|
||||
|
||||
info64 = grub_malloc (GRUB_DISK_SECTOR_SIZE);
|
||||
if (info64 == NULL)
|
||||
return grub_errno;
|
||||
info32 = (grub_uint32_t *) info64;
|
||||
info16 = (grub_uint16_t *) info64;
|
||||
if (! info16)
|
||||
return grub_errno;
|
||||
|
||||
grub_memset (&parms, 0, sizeof (parms));
|
||||
parms.buffer = info16;
|
||||
|
|
|
@ -17,7 +17,6 @@
|
|||
*/
|
||||
|
||||
#include <grub/cryptodisk.h>
|
||||
#include <grub/env.h>
|
||||
#include <grub/mm.h>
|
||||
#include <grub/misc.h>
|
||||
#include <grub/dl.h>
|
||||
|
@ -27,8 +26,6 @@
|
|||
#include <grub/file.h>
|
||||
#include <grub/procfs.h>
|
||||
#include <grub/partition.h>
|
||||
#include <grub/key_protector.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
#ifdef GRUB_UTIL
|
||||
#include <grub/emu/hostdisk.h>
|
||||
|
@ -47,8 +44,7 @@ enum
|
|||
OPTION_KEYFILE,
|
||||
OPTION_KEYFILE_OFFSET,
|
||||
OPTION_KEYFILE_SIZE,
|
||||
OPTION_HEADER,
|
||||
OPTION_PROTECTOR
|
||||
OPTION_HEADER
|
||||
};
|
||||
|
||||
static const struct grub_arg_option options[] =
|
||||
|
@ -62,8 +58,6 @@ static const struct grub_arg_option options[] =
|
|||
{"keyfile-offset", 'O', 0, N_("Key file offset (bytes)"), 0, ARG_TYPE_INT},
|
||||
{"keyfile-size", 'S', 0, N_("Key file data size (bytes)"), 0, ARG_TYPE_INT},
|
||||
{"header", 'H', 0, N_("Read header from file"), 0, ARG_TYPE_STRING},
|
||||
{"protector", 'P', GRUB_ARG_OPTION_REPEATABLE,
|
||||
N_("Unlock volume(s) using key protector(s)."), 0, ARG_TYPE_STRING},
|
||||
{0, 0, 0, 0, 0, 0}
|
||||
};
|
||||
|
||||
|
@ -1067,7 +1061,6 @@ grub_cryptodisk_scan_device_real (const char *name,
|
|||
grub_err_t ret = GRUB_ERR_NONE;
|
||||
grub_cryptodisk_t dev;
|
||||
grub_cryptodisk_dev_t cr;
|
||||
int i;
|
||||
struct cryptodisk_read_hook_ctx read_hook_data = {0};
|
||||
int askpass = 0;
|
||||
char *part = NULL;
|
||||
|
@ -1120,175 +1113,41 @@ grub_cryptodisk_scan_device_real (const char *name,
|
|||
goto error_no_close;
|
||||
if (!dev)
|
||||
continue;
|
||||
break;
|
||||
}
|
||||
|
||||
if (dev == NULL)
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_MODULE,
|
||||
"no cryptodisk module can handle this device");
|
||||
goto error_no_close;
|
||||
}
|
||||
if (!cargs->key_len)
|
||||
{
|
||||
/* Get the passphrase from the user, if no key data. */
|
||||
askpass = 1;
|
||||
part = grub_partition_get_name (source->partition);
|
||||
grub_printf_ (N_("Enter passphrase for %s%s%s (%s): "), source->name,
|
||||
source->partition != NULL ? "," : "",
|
||||
part != NULL ? part : N_("UNKNOWN"),
|
||||
dev->uuid);
|
||||
grub_free (part);
|
||||
|
||||
if (cargs->protectors)
|
||||
{
|
||||
for (i = 0; cargs->protectors[i]; i++)
|
||||
{
|
||||
if (cargs->key_cache[i].invalid)
|
||||
continue;
|
||||
cargs->key_data = grub_malloc (GRUB_CRYPTODISK_MAX_PASSPHRASE);
|
||||
if (cargs->key_data == NULL)
|
||||
goto error_no_close;
|
||||
|
||||
if (cargs->key_cache[i].key == NULL)
|
||||
{
|
||||
ret = grub_key_protector_recover_key (cargs->protectors[i],
|
||||
&cargs->key_cache[i].key,
|
||||
&cargs->key_cache[i].key_len);
|
||||
if (ret != GRUB_ERR_NONE)
|
||||
{
|
||||
if (grub_errno)
|
||||
{
|
||||
grub_print_error ();
|
||||
grub_errno = GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
grub_dprintf ("cryptodisk",
|
||||
"failed to recover a key from key protector "
|
||||
"%s, will not try it again for any other "
|
||||
"disks, if any, during this invocation of "
|
||||
"cryptomount\n",
|
||||
cargs->protectors[i]);
|
||||
|
||||
cargs->key_cache[i].invalid = 1;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
cargs->key_data = cargs->key_cache[i].key;
|
||||
cargs->key_len = cargs->key_cache[i].key_len;
|
||||
|
||||
ret = cr->recover_key (source, dev, cargs);
|
||||
if (ret != GRUB_ERR_NONE)
|
||||
{
|
||||
/* Reset key data to trigger the passphrase prompt later */
|
||||
cargs->key_data = NULL;
|
||||
cargs->key_len = 0;
|
||||
|
||||
part = grub_partition_get_name (source->partition);
|
||||
grub_dprintf ("cryptodisk",
|
||||
"recovered a key from key protector %s but it "
|
||||
"failed to unlock %s%s%s (%s)\n",
|
||||
cargs->protectors[i], source->name,
|
||||
source->partition != NULL ? "," : "",
|
||||
part != NULL ? part : N_("UNKNOWN"), dev->uuid);
|
||||
grub_free (part);
|
||||
continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
ret = grub_cryptodisk_insert (dev, name, source);
|
||||
if (ret != GRUB_ERR_NONE)
|
||||
goto error;
|
||||
#ifndef GRUB_UTIL
|
||||
grub_cli_set_auth_needed ();
|
||||
#endif
|
||||
goto cleanup;
|
||||
}
|
||||
}
|
||||
|
||||
part = grub_partition_get_name (source->partition);
|
||||
grub_error (GRUB_ERR_ACCESS_DENIED,
|
||||
N_("no key protector provided a usable key for %s%s%s (%s)"),
|
||||
source->name, source->partition != NULL ? "," : "",
|
||||
part != NULL ? part : N_("UNKNOWN"), dev->uuid);
|
||||
grub_free (part);
|
||||
}
|
||||
|
||||
if (cargs->key_len)
|
||||
{
|
||||
ret = cr->recover_key (source, dev, cargs);
|
||||
if (ret != GRUB_ERR_NONE)
|
||||
goto error;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Get the passphrase from the user, if no key data. */
|
||||
unsigned long tries = 3;
|
||||
const char *tries_env;
|
||||
|
||||
/*
|
||||
* Print the error from key protectors and clear grub_errno.
|
||||
*
|
||||
* Since '--protector' cannot coexist with '--password' and
|
||||
* '--key-file', in case key protectors fail, only
|
||||
* "cargs->key_len == 0" is expected, so cryptomount falls back
|
||||
* here to request the passphrase.
|
||||
*
|
||||
* To avoid the error from key protectors stops the further code,
|
||||
* print the error to notify the user why key protectors fail and
|
||||
* clear grub_errno to have a fresh start.
|
||||
*/
|
||||
if (grub_errno != GRUB_ERR_NONE)
|
||||
{
|
||||
grub_print_error ();
|
||||
grub_errno = GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
askpass = 1;
|
||||
cargs->key_data = grub_malloc (GRUB_CRYPTODISK_MAX_PASSPHRASE);
|
||||
if (cargs->key_data == NULL)
|
||||
goto error_no_close;
|
||||
|
||||
tries_env = grub_env_get ("cryptodisk_passphrase_tries");
|
||||
if (tries_env != NULL && tries_env[0] != '\0')
|
||||
{
|
||||
unsigned long tries_env_val;
|
||||
const char *p;
|
||||
|
||||
tries_env_val = grub_strtoul (tries_env, &p, 0);
|
||||
if (*p == '\0' && tries_env_val != ~0UL)
|
||||
tries = tries_env_val;
|
||||
else
|
||||
grub_printf_ (N_("Invalid cryptodisk_passphrase_tries value `%s'. Defaulting to %lu.\n"),
|
||||
tries_env,
|
||||
tries);
|
||||
}
|
||||
|
||||
for (; tries > 0; tries--)
|
||||
{
|
||||
part = grub_partition_get_name (source->partition);
|
||||
grub_printf_ (N_("Enter passphrase for %s%s%s (%s): "), source->name,
|
||||
source->partition != NULL ? "," : "",
|
||||
part != NULL ? part : N_("UNKNOWN"),
|
||||
dev->uuid);
|
||||
grub_free (part);
|
||||
|
||||
if (!grub_password_get ((char *) cargs->key_data, GRUB_CRYPTODISK_MAX_PASSPHRASE))
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_ARGUMENT, "passphrase not supplied");
|
||||
goto error;
|
||||
}
|
||||
cargs->key_len = grub_strlen ((char *) cargs->key_data);
|
||||
|
||||
ret = cr->recover_key (source, dev, cargs);
|
||||
if (ret == GRUB_ERR_NONE)
|
||||
break;
|
||||
if (ret != GRUB_ERR_ACCESS_DENIED || tries == 1)
|
||||
if (!grub_password_get ((char *) cargs->key_data, GRUB_CRYPTODISK_MAX_PASSPHRASE))
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_ARGUMENT, "passphrase not supplied");
|
||||
goto error;
|
||||
grub_puts_ (N_("Invalid passphrase."));
|
||||
}
|
||||
cargs->key_len = grub_strlen ((char *) cargs->key_data);
|
||||
}
|
||||
|
||||
/*
|
||||
* Since recover_key() calls a function that returns grub_errno,
|
||||
* a leftover error value from a previously rejected passphrase
|
||||
* will trigger a phantom failure. We therefore clear it before
|
||||
* trying a new passphrase.
|
||||
*/
|
||||
grub_errno = GRUB_ERR_NONE;
|
||||
}
|
||||
}
|
||||
ret = cr->recover_key (source, dev, cargs);
|
||||
if (ret != GRUB_ERR_NONE)
|
||||
goto error;
|
||||
|
||||
ret = grub_cryptodisk_insert (dev, name, source);
|
||||
if (ret != GRUB_ERR_NONE)
|
||||
goto error;
|
||||
ret = grub_cryptodisk_insert (dev, name, source);
|
||||
if (ret != GRUB_ERR_NONE)
|
||||
goto error;
|
||||
|
||||
goto cleanup;
|
||||
}
|
||||
grub_error (GRUB_ERR_BAD_MODULE, "no cryptodisk module can handle this device");
|
||||
goto cleanup;
|
||||
|
||||
error:
|
||||
|
@ -1302,7 +1161,6 @@ grub_cryptodisk_scan_device_real (const char *name,
|
|||
|
||||
if (askpass)
|
||||
{
|
||||
grub_memset (cargs->key_data, 0, cargs->key_len);
|
||||
cargs->key_len = 0;
|
||||
grub_free (cargs->key_data);
|
||||
}
|
||||
|
@ -1378,8 +1236,7 @@ grub_cryptodisk_scan_device (const char *name,
|
|||
dev = grub_cryptodisk_scan_device_real (name, source, cargs);
|
||||
if (dev)
|
||||
{
|
||||
ret = (cargs->search_uuid != NULL
|
||||
&& grub_uuidcasecmp (cargs->search_uuid, dev->uuid, sizeof (dev->uuid)) == 0);
|
||||
ret = (cargs->search_uuid != NULL && grub_strcasecmp (cargs->search_uuid, dev->uuid) == 0);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
|
@ -1401,24 +1258,6 @@ grub_cryptodisk_scan_device (const char *name,
|
|||
return ret;
|
||||
}
|
||||
|
||||
static void
|
||||
grub_cryptodisk_clear_key_cache (struct grub_cryptomount_args *cargs)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (cargs->key_cache == NULL || cargs->protectors == NULL)
|
||||
return;
|
||||
|
||||
for (i = 0; cargs->protectors[i]; i++)
|
||||
{
|
||||
if (cargs->key_cache[i].key)
|
||||
grub_memset (cargs->key_cache[i].key, 0, cargs->key_cache[i].key_len);
|
||||
grub_free (cargs->key_cache[i].key);
|
||||
}
|
||||
|
||||
grub_free (cargs->key_cache);
|
||||
}
|
||||
|
||||
static grub_err_t
|
||||
grub_cmd_cryptomount (grub_extcmd_context_t ctxt, int argc, char **args)
|
||||
{
|
||||
|
@ -1431,14 +1270,6 @@ grub_cmd_cryptomount (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
if (grub_cryptodisk_list == NULL)
|
||||
return grub_error (GRUB_ERR_BAD_MODULE, "no cryptodisk modules loaded");
|
||||
|
||||
if (state[OPTION_PASSWORD].set && state[OPTION_PROTECTOR].set) /* password and key protector */
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT,
|
||||
"a password and a key protector cannot both be set");
|
||||
|
||||
if (state[OPTION_KEYFILE].set && state[OPTION_PROTECTOR].set) /* key file and key protector */
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT,
|
||||
"a key file and a key protector cannot both be set");
|
||||
|
||||
if (state[OPTION_PASSWORD].set) /* password */
|
||||
{
|
||||
cargs.key_data = (grub_uint8_t *) state[OPTION_PASSWORD].arg;
|
||||
|
@ -1488,9 +1319,9 @@ grub_cmd_cryptomount (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
|
||||
if (keyfile_offset > keyfile->size)
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE,
|
||||
N_("Keyfile offset, %llu, is greater than "
|
||||
"keyfile size, %llu"),
|
||||
keyfile_offset, (unsigned long long) keyfile->size);
|
||||
N_("Keyfile offset, %llu, is greater than"
|
||||
"keyfile size, %" PRIuGRUB_UINT64_T),
|
||||
keyfile_offset, keyfile->size);
|
||||
|
||||
if (grub_file_seek (keyfile, (grub_off_t) keyfile_offset) == (grub_off_t) -1)
|
||||
return grub_errno;
|
||||
|
@ -1531,15 +1362,6 @@ grub_cmd_cryptomount (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
return grub_errno;
|
||||
}
|
||||
|
||||
if (state[OPTION_PROTECTOR].set) /* key protector(s) */
|
||||
{
|
||||
cargs.key_cache = grub_calloc (state[OPTION_PROTECTOR].set, sizeof (*cargs.key_cache));
|
||||
if (cargs.key_cache == NULL)
|
||||
return grub_error (GRUB_ERR_OUT_OF_MEMORY,
|
||||
"no memory for key protector key cache");
|
||||
cargs.protectors = state[OPTION_PROTECTOR].args;
|
||||
}
|
||||
|
||||
if (state[OPTION_UUID].set) /* uuid */
|
||||
{
|
||||
int found_uuid;
|
||||
|
@ -1548,7 +1370,6 @@ grub_cmd_cryptomount (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
dev = grub_cryptodisk_get_by_uuid (args[0]);
|
||||
if (dev)
|
||||
{
|
||||
grub_cryptodisk_clear_key_cache (&cargs);
|
||||
grub_dprintf ("cryptodisk",
|
||||
"already mounted as crypto%lu\n", dev->id);
|
||||
return GRUB_ERR_NONE;
|
||||
|
@ -1557,7 +1378,6 @@ grub_cmd_cryptomount (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
cargs.check_boot = state[OPTION_BOOT].set;
|
||||
cargs.search_uuid = args[0];
|
||||
found_uuid = grub_device_iterate (&grub_cryptodisk_scan_device, &cargs);
|
||||
grub_cryptodisk_clear_key_cache (&cargs);
|
||||
|
||||
if (found_uuid)
|
||||
return GRUB_ERR_NONE;
|
||||
|
@ -1577,7 +1397,6 @@ grub_cmd_cryptomount (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
{
|
||||
cargs.check_boot = state[OPTION_BOOT].set;
|
||||
grub_device_iterate (&grub_cryptodisk_scan_device, &cargs);
|
||||
grub_cryptodisk_clear_key_cache (&cargs);
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
else
|
||||
|
@ -1601,7 +1420,6 @@ grub_cmd_cryptomount (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
disk = grub_disk_open (diskname);
|
||||
if (!disk)
|
||||
{
|
||||
grub_cryptodisk_clear_key_cache (&cargs);
|
||||
if (disklast)
|
||||
*disklast = ')';
|
||||
return grub_errno;
|
||||
|
@ -1612,14 +1430,12 @@ grub_cmd_cryptomount (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
{
|
||||
grub_dprintf ("cryptodisk", "already mounted as crypto%lu\n", dev->id);
|
||||
grub_disk_close (disk);
|
||||
grub_cryptodisk_clear_key_cache (&cargs);
|
||||
if (disklast)
|
||||
*disklast = ')';
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
dev = grub_cryptodisk_scan_device_real (diskname, disk, &cargs);
|
||||
grub_cryptodisk_clear_key_cache (&cargs);
|
||||
|
||||
grub_disk_close (disk);
|
||||
if (disklast)
|
||||
|
@ -1656,70 +1472,40 @@ static char *
|
|||
luks_script_get (grub_size_t *sz)
|
||||
{
|
||||
grub_cryptodisk_t i;
|
||||
grub_size_t size = 0, mul;
|
||||
grub_size_t size = 0;
|
||||
char *ptr, *ret;
|
||||
|
||||
*sz = 0;
|
||||
|
||||
for (i = cryptodisk_list; i != NULL; i = i->next)
|
||||
if (grub_strcmp (i->modname, "luks") == 0 ||
|
||||
grub_strcmp (i->modname, "luks2") == 0)
|
||||
if (grub_strcmp (i->modname, "luks") == 0)
|
||||
{
|
||||
/*
|
||||
* Add space in the line for (in order) spaces, cipher mode, cipher IV
|
||||
* mode, sector offset, sector size and the trailing newline. This is
|
||||
* an upper bound on the size of this data. There are 15 extra bytes
|
||||
* in an earlier version of this code that are unaccounted for. It is
|
||||
* left in the calculations in case it is needed. At worst, its short-
|
||||
* lived wasted space.
|
||||
*
|
||||
* 60 = 5 + 5 + 8 + 20 + 6 + 1 + 15
|
||||
*/
|
||||
if (grub_add (size, grub_strlen (i->modname), &size) ||
|
||||
grub_add (size, sizeof ("_mount") + 60, &size) ||
|
||||
grub_add (size, grub_strlen (i->uuid), &size) ||
|
||||
grub_add (size, grub_strlen (i->cipher->cipher->name), &size) ||
|
||||
grub_mul (i->keysize, 2, &mul) ||
|
||||
grub_add (size, mul, &size))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, "overflow detected while obtaining size of luks script");
|
||||
return 0;
|
||||
}
|
||||
size += sizeof ("luks_mount ");
|
||||
size += grub_strlen (i->uuid);
|
||||
size += grub_strlen (i->cipher->cipher->name);
|
||||
size += 54;
|
||||
if (i->essiv_hash)
|
||||
{
|
||||
if (grub_add (size, grub_strlen (i->essiv_hash->name), &size))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, "overflow detected while obtaining size of luks script");
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
size += grub_strlen (i->essiv_hash->name);
|
||||
size += i->keysize * 2;
|
||||
}
|
||||
if (grub_add (size, 1, &size))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, "overflow detected while obtaining size of luks script");
|
||||
return 0;
|
||||
}
|
||||
|
||||
ret = grub_malloc (size);
|
||||
ret = grub_malloc (size + 1);
|
||||
if (!ret)
|
||||
return 0;
|
||||
|
||||
ptr = ret;
|
||||
|
||||
for (i = cryptodisk_list; i != NULL; i = i->next)
|
||||
if (grub_strcmp (i->modname, "luks") == 0 ||
|
||||
grub_strcmp (i->modname, "luks2") == 0)
|
||||
if (grub_strcmp (i->modname, "luks") == 0)
|
||||
{
|
||||
unsigned j;
|
||||
const char *iptr;
|
||||
ptr = grub_stpcpy (ptr, i->modname);
|
||||
ptr = grub_stpcpy (ptr, "_mount ");
|
||||
ptr = grub_stpcpy (ptr, "luks_mount ");
|
||||
ptr = grub_stpcpy (ptr, i->uuid);
|
||||
*ptr++ = ' ';
|
||||
ptr += grub_snprintf (ptr, 21, "%" PRIxGRUB_OFFSET, i->offset_sectors);
|
||||
*ptr++ = ' ';
|
||||
ptr += grub_snprintf (ptr, 7, "%u", 1 << i->log_sector_size);
|
||||
*ptr++ = ' ';
|
||||
grub_snprintf (ptr, 21, "%" PRIuGRUB_UINT64_T " ", i->offset_sectors);
|
||||
while (*ptr)
|
||||
ptr++;
|
||||
for (iptr = i->cipher->cipher->name; *iptr; iptr++)
|
||||
*ptr++ = grub_tolower (*iptr);
|
||||
switch (i->mode)
|
||||
|
@ -1776,114 +1562,6 @@ luks_script_get (grub_size_t *sz)
|
|||
return ret;
|
||||
}
|
||||
|
||||
#ifdef GRUB_MACHINE_EFI
|
||||
grub_err_t
|
||||
grub_cryptodisk_challenge_password (void)
|
||||
{
|
||||
grub_cryptodisk_t cr_dev;
|
||||
|
||||
for (cr_dev = cryptodisk_list; cr_dev != NULL; cr_dev = cr_dev->next)
|
||||
{
|
||||
grub_cryptodisk_dev_t cr;
|
||||
grub_disk_t source = NULL;
|
||||
grub_err_t ret = GRUB_ERR_NONE;
|
||||
grub_cryptodisk_t dev = NULL;
|
||||
char *part = NULL;
|
||||
struct grub_cryptomount_args cargs = {0};
|
||||
|
||||
cargs.check_boot = 0;
|
||||
cargs.search_uuid = cr_dev->uuid;
|
||||
|
||||
source = grub_disk_open (cr_dev->source);
|
||||
|
||||
if (source == NULL)
|
||||
{
|
||||
ret = grub_errno;
|
||||
goto error_out;
|
||||
}
|
||||
|
||||
FOR_CRYPTODISK_DEVS (cr)
|
||||
{
|
||||
dev = cr->scan (source, &cargs);
|
||||
if (grub_errno)
|
||||
{
|
||||
ret = grub_errno;
|
||||
goto error_out;
|
||||
}
|
||||
if (dev == NULL)
|
||||
continue;
|
||||
break;
|
||||
}
|
||||
|
||||
if (dev == NULL)
|
||||
{
|
||||
ret = grub_error (GRUB_ERR_BAD_MODULE, "no cryptodisk module can handle this device");
|
||||
goto error_out;
|
||||
}
|
||||
|
||||
part = grub_partition_get_name (source->partition);
|
||||
grub_printf_ (N_("Enter passphrase for %s%s%s (%s): "), source->name,
|
||||
source->partition != NULL ? "," : "",
|
||||
part != NULL ? part : N_("UNKNOWN"), cr_dev->uuid);
|
||||
grub_free (part);
|
||||
|
||||
cargs.key_data = grub_malloc (GRUB_CRYPTODISK_MAX_PASSPHRASE);
|
||||
if (cargs.key_data == NULL)
|
||||
{
|
||||
ret = grub_errno;
|
||||
goto error_out;
|
||||
}
|
||||
|
||||
if (!grub_password_get ((char *) cargs.key_data, GRUB_CRYPTODISK_MAX_PASSPHRASE))
|
||||
{
|
||||
ret = grub_error (GRUB_ERR_BAD_ARGUMENT, "passphrase not supplied");
|
||||
goto error_out;
|
||||
}
|
||||
cargs.key_len = grub_strlen ((char *) cargs.key_data);
|
||||
ret = cr->recover_key (source, dev, &cargs);
|
||||
|
||||
error_out:
|
||||
grub_disk_close (source);
|
||||
if (dev != NULL)
|
||||
cryptodisk_close (dev);
|
||||
if (cargs.key_data)
|
||||
{
|
||||
grub_memset (cargs.key_data, 0, cargs.key_len);
|
||||
grub_free (cargs.key_data);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
void
|
||||
grub_cryptodisk_erasesecrets (void)
|
||||
{
|
||||
grub_cryptodisk_t i;
|
||||
grub_uint8_t *buf;
|
||||
|
||||
buf = grub_zalloc (GRUB_CRYPTODISK_MAX_KEYLEN);
|
||||
if (buf == NULL)
|
||||
grub_fatal ("grub_cryptodisk_erasesecrets: cannot allocate memory");
|
||||
|
||||
for (i = cryptodisk_list; i != NULL; i = i->next)
|
||||
if (grub_cryptodisk_setkey (i, buf, i->keysize))
|
||||
grub_fatal ("grub_cryptodisk_erasesecrets: cannot erase secrets for %s", i->source);
|
||||
else
|
||||
grub_printf ("Erased crypto secrets for %s\n", i->source);
|
||||
/*
|
||||
* Unfortunately, there is no way to "force unmount" a given disk, it may
|
||||
* have mounted "child" disks as well, e.g., an LVM volume. So, this
|
||||
* function MUST be called when there is no way back, e.g., when exiting.
|
||||
* Otherwise, subsequent read calls for a cryptodisk will return garbage.
|
||||
*/
|
||||
|
||||
grub_free (buf);
|
||||
}
|
||||
#endif /* GRUB_MACHINE_EFI */
|
||||
|
||||
struct grub_procfs_entry luks_script =
|
||||
{
|
||||
.name = "luks_script",
|
||||
|
@ -1898,7 +1576,6 @@ GRUB_MOD_INIT (cryptodisk)
|
|||
cmd = grub_register_extcmd ("cryptomount", grub_cmd_cryptomount, 0,
|
||||
N_("[ [-p password] | [-k keyfile"
|
||||
" [-O keyoffset] [-S keysize] ] ] [-H file]"
|
||||
" [-P protector [-P protector ...]]"
|
||||
" <SOURCE|-u UUID|-a|-b>"),
|
||||
N_("Mount a crypto device."), options);
|
||||
grub_procfs_register ("luks_script", &luks_script);
|
||||
|
@ -1906,9 +1583,6 @@ GRUB_MOD_INIT (cryptodisk)
|
|||
|
||||
GRUB_MOD_FINI (cryptodisk)
|
||||
{
|
||||
#ifdef GRUB_MACHINE_EFI
|
||||
grub_cryptodisk_erasesecrets ();
|
||||
#endif
|
||||
grub_disk_dev_unregister (&grub_cryptodisk_dev);
|
||||
cryptodisk_cleanup ();
|
||||
grub_unregister_extcmd (cmd);
|
||||
|
|
|
@ -20,12 +20,10 @@
|
|||
#include <grub/dl.h>
|
||||
#include <grub/disk.h>
|
||||
#include <grub/mm.h>
|
||||
#include <grub/command.h>
|
||||
#include <grub/err.h>
|
||||
#include <grub/misc.h>
|
||||
#include <grub/diskfilter.h>
|
||||
#include <grub/partition.h>
|
||||
#include <grub/safemath.h>
|
||||
#ifdef GRUB_UTIL
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/util/misc.h>
|
||||
|
@ -228,28 +226,15 @@ scan_devices (const char *arname)
|
|||
int need_rescan;
|
||||
|
||||
for (pull = 0; pull < GRUB_DISK_PULL_MAX; pull++)
|
||||
{
|
||||
/* look up the crytodisk devices first */
|
||||
for (p = grub_disk_dev_list; p; p = p->next)
|
||||
if (p->id == GRUB_DISK_DEVICE_CRYPTODISK_ID && p->disk_iterate)
|
||||
{
|
||||
if ((p->disk_iterate) (scan_disk_hook, NULL, pull))
|
||||
return;
|
||||
if (arname && is_lv_readable (find_lv (arname), 1))
|
||||
return;
|
||||
break;
|
||||
}
|
||||
|
||||
/* check the devices other than crytodisk */
|
||||
for (p = grub_disk_dev_list; p; p = p->next)
|
||||
if (p->id != GRUB_DISK_DEVICE_DISKFILTER_ID && p->disk_iterate)
|
||||
{
|
||||
if ((p->disk_iterate) (scan_disk_hook, NULL, pull))
|
||||
return;
|
||||
if (arname && is_lv_readable (find_lv (arname), 1))
|
||||
return;
|
||||
}
|
||||
}
|
||||
for (p = grub_disk_dev_list; p; p = p->next)
|
||||
if (p->id != GRUB_DISK_DEVICE_DISKFILTER_ID
|
||||
&& p->disk_iterate)
|
||||
{
|
||||
if ((p->disk_iterate) (scan_disk_hook, NULL, pull))
|
||||
return;
|
||||
if (arname && is_lv_readable (find_lv (arname), 1))
|
||||
return;
|
||||
}
|
||||
|
||||
scan_depth = 0;
|
||||
need_rescan = 1;
|
||||
|
@ -735,7 +720,7 @@ read_segment (struct grub_diskfilter_segment *seg, grub_disk_addr_t sector,
|
|||
case GRUB_DISKFILTER_RAID6:
|
||||
{
|
||||
grub_disk_addr_t read_sector;
|
||||
grub_uint64_t b, p, n, disknr;
|
||||
grub_uint64_t b, p, n, disknr, e;
|
||||
|
||||
/* n = 1 for level 4 and 5, 2 for level 6. */
|
||||
n = seg->type / 3;
|
||||
|
@ -785,6 +770,7 @@ read_segment (struct grub_diskfilter_segment *seg, grub_disk_addr_t sector,
|
|||
if (read_size > size)
|
||||
read_size = size;
|
||||
|
||||
e = 0;
|
||||
/* Reset read error. */
|
||||
if (grub_errno == GRUB_ERR_READ_ERROR
|
||||
|| grub_errno == GRUB_ERR_UNKNOWN_DEVICE)
|
||||
|
@ -798,6 +784,7 @@ read_segment (struct grub_diskfilter_segment *seg, grub_disk_addr_t sector,
|
|||
if ((err) && (err != GRUB_ERR_READ_ERROR
|
||||
&& err != GRUB_ERR_UNKNOWN_DEVICE))
|
||||
return err;
|
||||
e++;
|
||||
|
||||
if (err)
|
||||
{
|
||||
|
@ -981,6 +968,8 @@ grub_diskfilter_vg_register (struct grub_diskfilter_vg *vg)
|
|||
|
||||
for (lv = vg->lvs; lv; lv = lv->next)
|
||||
{
|
||||
grub_err_t err;
|
||||
|
||||
/* RAID 1 and single-disk RAID 0 don't use a chunksize but code
|
||||
assumes one so set one. */
|
||||
for (i = 0; i < lv->segment_count; i++)
|
||||
|
@ -992,10 +981,6 @@ grub_diskfilter_vg_register (struct grub_diskfilter_vg *vg)
|
|||
&& lv->segments[i].stripe_size == 0)
|
||||
lv->segments[i].stripe_size = 64;
|
||||
}
|
||||
}
|
||||
for (lv = vg->lvs; lv; lv = lv->next)
|
||||
{
|
||||
grub_err_t err;
|
||||
|
||||
err = validate_lv(lv);
|
||||
if (err)
|
||||
|
@ -1056,7 +1041,7 @@ grub_diskfilter_make_raid (grub_size_t uuidlen, char *uuid, int nmemb,
|
|||
{
|
||||
struct grub_diskfilter_vg *array;
|
||||
int i;
|
||||
grub_size_t j, sz;
|
||||
grub_size_t j;
|
||||
grub_uint64_t totsize;
|
||||
struct grub_diskfilter_pv *pv;
|
||||
grub_err_t err;
|
||||
|
@ -1157,11 +1142,7 @@ grub_diskfilter_make_raid (grub_size_t uuidlen, char *uuid, int nmemb,
|
|||
}
|
||||
array->lvs->vg = array;
|
||||
|
||||
if (grub_mul (uuidlen, 2, &sz) ||
|
||||
grub_add (sz, sizeof ("mduuid/"), &sz))
|
||||
goto fail;
|
||||
|
||||
array->lvs->idname = grub_malloc (sz);
|
||||
array->lvs->idname = grub_malloc (sizeof ("mduuid/") + 2 * uuidlen);
|
||||
if (!array->lvs->idname)
|
||||
goto fail;
|
||||
|
||||
|
@ -1378,86 +1359,6 @@ grub_diskfilter_get_pv_from_disk (grub_disk_t disk,
|
|||
}
|
||||
#endif
|
||||
|
||||
static int
|
||||
grub_diskfilter_check_pvs_encrypted (grub_disk_t disk, int *pvs_cnt)
|
||||
{
|
||||
struct grub_diskfilter_lv *lv = disk->data;
|
||||
struct grub_diskfilter_pv *pv;
|
||||
|
||||
*pvs_cnt = 0;
|
||||
|
||||
if (lv->vg->pvs)
|
||||
for (pv = lv->vg->pvs; pv; pv = pv->next)
|
||||
{
|
||||
(*pvs_cnt)++;
|
||||
|
||||
if (pv->disk == NULL)
|
||||
{
|
||||
/* Can be a partially activated VG, bail out. */
|
||||
return GRUB_ERR_TEST_FAILURE;
|
||||
}
|
||||
|
||||
if (pv->disk->dev->id != GRUB_DISK_DEVICE_CRYPTODISK_ID)
|
||||
{
|
||||
/* All backing devices must be cryptodisks, stop. */
|
||||
return GRUB_ERR_TEST_FAILURE;
|
||||
}
|
||||
}
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
static grub_err_t
|
||||
grub_cmd_cryptocheck (grub_command_t cmd __attribute__ ((unused)),
|
||||
int argc, char **args)
|
||||
{
|
||||
grub_disk_t disk;
|
||||
int check_pvs_res;
|
||||
int namelen;
|
||||
int pvs_cnt;
|
||||
int opt_quiet = 0;
|
||||
|
||||
if (argc == 2)
|
||||
{
|
||||
if (grub_strcmp (args[0], "--quiet") == 0)
|
||||
{
|
||||
opt_quiet = 1;
|
||||
argc--;
|
||||
args++;
|
||||
}
|
||||
else
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, N_("unrecognized option: %s"), args[0]);
|
||||
}
|
||||
|
||||
if (argc != 1)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, N_("disk name expected"));
|
||||
|
||||
namelen = grub_strlen (args[0]);
|
||||
if (namelen > 2 && (args[0][0] == '(') && (args[0][namelen - 1] == ')'))
|
||||
args[0][namelen - 1] = 0;
|
||||
else
|
||||
return grub_error (GRUB_ERR_UNKNOWN_DEVICE, N_("invalid disk: %s"),
|
||||
args[0]);
|
||||
|
||||
if (!is_valid_diskfilter_name (&args[0][1]))
|
||||
return grub_error (GRUB_ERR_UNKNOWN_DEVICE, N_("unrecognized disk: %s"),
|
||||
&args[0][1]);
|
||||
|
||||
disk = grub_disk_open (&args[0][1]);
|
||||
if (disk == NULL)
|
||||
return grub_error (GRUB_ERR_UNKNOWN_DEVICE, N_("no such disk: %s"),
|
||||
&args[0][1]);
|
||||
|
||||
check_pvs_res = grub_diskfilter_check_pvs_encrypted (disk, &pvs_cnt);
|
||||
grub_disk_close (disk);
|
||||
if (!opt_quiet)
|
||||
grub_printf ("%s is %sencrypted (%d pv%s examined)\n", &args[0][1],
|
||||
(check_pvs_res == GRUB_ERR_NONE) ? "" : "un",
|
||||
pvs_cnt,
|
||||
(pvs_cnt > 1) ? "s" : "");
|
||||
|
||||
return check_pvs_res;
|
||||
}
|
||||
|
||||
static struct grub_disk_dev grub_diskfilter_dev =
|
||||
{
|
||||
.name = "diskfilter",
|
||||
|
@ -1474,21 +1375,14 @@ static struct grub_disk_dev grub_diskfilter_dev =
|
|||
.next = 0
|
||||
};
|
||||
|
||||
static grub_command_t cmd;
|
||||
|
||||
|
||||
GRUB_MOD_INIT(diskfilter)
|
||||
{
|
||||
grub_disk_dev_register (&grub_diskfilter_dev);
|
||||
cmd = grub_register_command ("cryptocheck", grub_cmd_cryptocheck,
|
||||
N_("[--quiet] DEVICE"),
|
||||
N_("Check if a logical volume resides on encrypted disks."));
|
||||
}
|
||||
|
||||
GRUB_MOD_FINI(diskfilter)
|
||||
{
|
||||
grub_disk_dev_unregister (&grub_diskfilter_dev);
|
||||
if (cmd != NULL)
|
||||
grub_unregister_command (cmd);
|
||||
free_array ();
|
||||
}
|
||||
|
|
|
@ -471,7 +471,7 @@ grub_biosdisk_rw (int cmd, grub_disk_t disk,
|
|||
struct grub_biosdisk_dap *dap;
|
||||
|
||||
dap = (struct grub_biosdisk_dap *) (GRUB_MEMORY_MACHINE_SCRATCH_ADDR
|
||||
+ (GRUB_DISK_MAX_LBA_SECTORS
|
||||
+ (data->sectors
|
||||
<< disk->log_sector_size));
|
||||
dap->length = sizeof (*dap);
|
||||
dap->reserved = 0;
|
||||
|
@ -561,9 +561,6 @@ get_safe_sectors (grub_disk_t disk, grub_disk_addr_t sector)
|
|||
struct grub_biosdisk_data *data = disk->data;
|
||||
grub_uint32_t sectors = data->sectors;
|
||||
|
||||
if (data->flags & GRUB_BIOSDISK_FLAG_LBA)
|
||||
sectors = GRUB_DISK_MAX_LBA_SECTORS;
|
||||
|
||||
/* OFFSET = SECTOR % SECTORS */
|
||||
grub_divmod64 (sector, sectors, &offset);
|
||||
|
||||
|
|
|
@ -26,7 +26,6 @@
|
|||
#include <grub/mm.h>
|
||||
#include <grub/scsicmd.h>
|
||||
#include <grub/time.h>
|
||||
#include <grub/safemath.h>
|
||||
#include <grub/ieee1275/ieee1275.h>
|
||||
#include <grub/ieee1275/obdisk.h>
|
||||
|
||||
|
@ -129,17 +128,9 @@ count_commas (const char *src)
|
|||
static char *
|
||||
decode_grub_devname (const char *name)
|
||||
{
|
||||
char *devpath;
|
||||
char *devpath = grub_malloc (grub_strlen (name) + 1);
|
||||
char *p, c;
|
||||
grub_size_t sz;
|
||||
|
||||
if (grub_add (grub_strlen (name), 1, &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow detected while obtaining size of device name"));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
devpath = grub_malloc (sz);
|
||||
if (devpath == NULL)
|
||||
return NULL;
|
||||
|
||||
|
@ -165,20 +156,12 @@ static char *
|
|||
encode_grub_devname (const char *path)
|
||||
{
|
||||
char *encoding, *optr;
|
||||
grub_size_t sz;
|
||||
|
||||
if (path == NULL)
|
||||
return NULL;
|
||||
|
||||
if (grub_add (sizeof (IEEE1275_DEV) + 1, count_commas (path), &sz) ||
|
||||
grub_add (sz, grub_strlen (path), &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow detected while obtaining encoding size"));
|
||||
grub_print_error ();
|
||||
return NULL;
|
||||
}
|
||||
|
||||
encoding = grub_malloc (sz);
|
||||
encoding = grub_malloc (sizeof (IEEE1275_DEV) + count_commas (path) +
|
||||
grub_strlen (path) + 1);
|
||||
|
||||
if (encoding == NULL)
|
||||
{
|
||||
|
@ -413,22 +396,8 @@ canonicalise_disk (const char *devname)
|
|||
|
||||
real_unit_str_len = grub_strlen (op->name) + sizeof (IEEE1275_DISK_ALIAS)
|
||||
+ grub_strlen (real_unit_address);
|
||||
if (grub_add (grub_strlen (op->name), sizeof (IEEE1275_DISK_ALIAS), &real_unit_str_len) ||
|
||||
grub_add (real_unit_str_len, grub_strlen (real_unit_address), &real_unit_str_len))
|
||||
{
|
||||
grub_free (parent);
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow detected while obtaining size of canonical name"));
|
||||
grub_print_error ();
|
||||
return NULL;
|
||||
}
|
||||
|
||||
real_canon = grub_malloc (real_unit_str_len);
|
||||
if (real_canon == NULL)
|
||||
{
|
||||
grub_free (parent);
|
||||
grub_print_error ();
|
||||
return NULL;
|
||||
}
|
||||
|
||||
grub_snprintf (real_canon, real_unit_str_len, "%s/disk@%s",
|
||||
op->name, real_unit_address);
|
||||
|
@ -444,7 +413,6 @@ canonicalise_disk (const char *devname)
|
|||
static struct disk_dev *
|
||||
add_canon_disk (const char *cname)
|
||||
{
|
||||
grub_size_t sz;
|
||||
struct disk_dev *dev;
|
||||
|
||||
dev = grub_zalloc (sizeof (struct disk_dev));
|
||||
|
@ -460,18 +428,13 @@ add_canon_disk (const char *cname)
|
|||
* arguments and allows a client program to open
|
||||
* the entire (raw) disk. Any disk label is ignored.
|
||||
*/
|
||||
if (grub_add (grub_strlen (cname), sizeof (":nolabel"), &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, "overflow detected while appending :nolabel to end of canonical name");
|
||||
goto failed;
|
||||
}
|
||||
|
||||
dev->raw_name = grub_malloc (sz);
|
||||
dev->raw_name = grub_malloc (grub_strlen (cname) + sizeof (":nolabel"));
|
||||
|
||||
if (dev->raw_name == NULL)
|
||||
goto failed;
|
||||
|
||||
grub_snprintf (dev->raw_name, sz, "%s:nolabel", cname);
|
||||
grub_snprintf (dev->raw_name, grub_strlen (cname) + sizeof (":nolabel"),
|
||||
"%s:nolabel", cname);
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
#include <grub/ieee1275/ofdisk.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/time.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
static char *last_devpath;
|
||||
static grub_ieee1275_ihandle_t last_ihandle;
|
||||
|
@ -81,7 +80,6 @@ ofdisk_hash_add_real (char *devpath)
|
|||
struct ofdisk_hash_ent **head = &ofdisk_hash[ofdisk_hash_fn(devpath)];
|
||||
const char *iptr;
|
||||
char *optr;
|
||||
grub_size_t sz;
|
||||
|
||||
p = grub_zalloc (sizeof (*p));
|
||||
if (!p)
|
||||
|
@ -89,14 +87,8 @@ ofdisk_hash_add_real (char *devpath)
|
|||
|
||||
p->devpath = devpath;
|
||||
|
||||
if (grub_mul (grub_strlen (p->devpath), 2, &sz) ||
|
||||
grub_add (sz, sizeof ("ieee1275/"), &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow detected while obtaining size of device path"));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
p->grub_devpath = grub_malloc (sz);
|
||||
p->grub_devpath = grub_malloc (sizeof ("ieee1275/")
|
||||
+ 2 * grub_strlen (p->devpath));
|
||||
|
||||
if (!p->grub_devpath)
|
||||
{
|
||||
|
@ -106,13 +98,7 @@ ofdisk_hash_add_real (char *devpath)
|
|||
|
||||
if (! grub_ieee1275_test_flag (GRUB_IEEE1275_FLAG_NO_PARTITION_0))
|
||||
{
|
||||
if (grub_add (grub_strlen (p->devpath), 3, &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow detected while obtaining size of an open path"));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
p->open_path = grub_malloc (sz);
|
||||
p->open_path = grub_malloc (grub_strlen (p->devpath) + 3);
|
||||
if (!p->open_path)
|
||||
{
|
||||
grub_free (p->grub_devpath);
|
||||
|
@ -238,7 +224,6 @@ dev_iterate (const struct grub_ieee1275_devalias *alias)
|
|||
args;
|
||||
char *buf, *bufptr;
|
||||
unsigned i;
|
||||
grub_size_t sz;
|
||||
|
||||
if (grub_ieee1275_open (alias->path, &ihandle))
|
||||
return;
|
||||
|
@ -258,19 +243,9 @@ dev_iterate (const struct grub_ieee1275_devalias *alias)
|
|||
return;
|
||||
}
|
||||
|
||||
if (grub_add (grub_strlen (alias->path), 32, &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, "overflow detected while creating buffer for vscsi");
|
||||
grub_ieee1275_close (ihandle);
|
||||
return;
|
||||
}
|
||||
|
||||
buf = grub_malloc (sz);
|
||||
buf = grub_malloc (grub_strlen (alias->path) + 32);
|
||||
if (!buf)
|
||||
{
|
||||
grub_ieee1275_close (ihandle);
|
||||
return;
|
||||
}
|
||||
return;
|
||||
bufptr = grub_stpcpy (buf, alias->path);
|
||||
|
||||
for (i = 0; i < args.nentries; i++)
|
||||
|
@ -312,15 +287,9 @@ dev_iterate (const struct grub_ieee1275_devalias *alias)
|
|||
grub_uint64_t *table;
|
||||
grub_uint16_t table_size;
|
||||
grub_ieee1275_ihandle_t ihandle;
|
||||
grub_size_t sz;
|
||||
|
||||
if (grub_add (grub_strlen (alias->path), sizeof ("/disk@7766554433221100"), &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, "overflow detected while creating buffer for sas_ioa");
|
||||
return;
|
||||
}
|
||||
|
||||
buf = grub_malloc (sz);
|
||||
buf = grub_malloc (grub_strlen (alias->path) +
|
||||
sizeof ("/disk@7766554433221100"));
|
||||
if (!buf)
|
||||
return;
|
||||
bufptr = grub_stpcpy (buf, alias->path);
|
||||
|
@ -458,17 +427,9 @@ grub_ofdisk_iterate (grub_disk_dev_iterate_hook_t hook, void *hook_data,
|
|||
static char *
|
||||
compute_dev_path (const char *name)
|
||||
{
|
||||
char *devpath;
|
||||
char *devpath = grub_malloc (grub_strlen (name) + 3);
|
||||
char *p, c;
|
||||
grub_size_t sz;
|
||||
|
||||
if (grub_add (grub_strlen (name), 3, &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow detected while obtaining size of device path"));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
devpath = grub_malloc (sz);
|
||||
if (!devpath)
|
||||
return NULL;
|
||||
|
||||
|
@ -664,7 +625,6 @@ insert_bootpath (void)
|
|||
char *bootpath;
|
||||
grub_ssize_t bootpath_size;
|
||||
char *type;
|
||||
grub_size_t sz;
|
||||
|
||||
if (grub_ieee1275_get_property_length (grub_ieee1275_chosen, "bootpath",
|
||||
&bootpath_size)
|
||||
|
@ -675,13 +635,7 @@ insert_bootpath (void)
|
|||
return;
|
||||
}
|
||||
|
||||
if (grub_add (bootpath_size, 64, &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow detected while obtaining bootpath size"));
|
||||
return;
|
||||
}
|
||||
|
||||
bootpath = (char *) grub_malloc (sz);
|
||||
bootpath = (char *) grub_malloc ((grub_size_t) bootpath_size + 64);
|
||||
if (! bootpath)
|
||||
{
|
||||
grub_print_error ();
|
||||
|
|
|
@ -1,73 +0,0 @@
|
|||
/*
|
||||
* GRUB -- GRand Unified Bootloader
|
||||
* Copyright (C) 2022 Microsoft Corporation
|
||||
* Copyright (C) 2024 Free Software Foundation, Inc.
|
||||
*
|
||||
* GRUB is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GRUB is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GRUB. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include <grub/dl.h>
|
||||
#include <grub/list.h>
|
||||
#include <grub/misc.h>
|
||||
#include <grub/mm.h>
|
||||
#include <grub/key_protector.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
struct grub_key_protector *grub_key_protectors = NULL;
|
||||
|
||||
grub_err_t
|
||||
grub_key_protector_register (struct grub_key_protector *protector)
|
||||
{
|
||||
if (protector == NULL || protector->name == NULL || protector->name[0] == '\0')
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, "Invalid key protector for registration");
|
||||
|
||||
if (grub_key_protectors != NULL &&
|
||||
grub_named_list_find (GRUB_AS_NAMED_LIST (grub_key_protectors), protector->name) != NULL)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, "Key protector '%s' already registered", protector->name);
|
||||
|
||||
grub_list_push (GRUB_AS_LIST_P (&grub_key_protectors), GRUB_AS_LIST (protector));
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_key_protector_unregister (struct grub_key_protector *protector)
|
||||
{
|
||||
if (protector == NULL)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, "Invalid key protector for unregistration");
|
||||
|
||||
grub_list_remove (GRUB_AS_LIST (protector));
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
grub_err_t
|
||||
grub_key_protector_recover_key (const char *protector, grub_uint8_t **key,
|
||||
grub_size_t *key_size)
|
||||
{
|
||||
struct grub_key_protector *kp = NULL;
|
||||
|
||||
if (grub_key_protectors == NULL)
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, "No key protector registered");
|
||||
|
||||
if (protector == NULL || protector[0] == '\0')
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, "Invalid key protector");
|
||||
|
||||
kp = grub_named_list_find (GRUB_AS_NAMED_LIST (grub_key_protectors), protector);
|
||||
if (kp == NULL)
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, "Key protector '%s' not found", protector);
|
||||
|
||||
return kp->recover_key (key, key_size);
|
||||
}
|
|
@ -179,36 +179,6 @@ gpt_ldm_sector (grub_disk_t dsk)
|
|||
return sector;
|
||||
}
|
||||
|
||||
static void
|
||||
free_pv (struct grub_diskfilter_pv *pv)
|
||||
{
|
||||
if (pv == NULL)
|
||||
return;
|
||||
|
||||
grub_free (pv->internal_id);
|
||||
grub_free (pv->id.uuid);
|
||||
grub_free (pv);
|
||||
}
|
||||
|
||||
static void
|
||||
free_lv (struct grub_diskfilter_lv *lv)
|
||||
{
|
||||
if (lv == NULL)
|
||||
return;
|
||||
|
||||
grub_free (lv->internal_id);
|
||||
grub_free (lv->name);
|
||||
grub_free (lv->fullname);
|
||||
if (lv->segments)
|
||||
{
|
||||
unsigned int i;
|
||||
for (i = 0; i < lv->segment_count; i++)
|
||||
grub_free (lv->segments[i].nodes);
|
||||
grub_free (lv->segments);
|
||||
}
|
||||
grub_free (lv);
|
||||
}
|
||||
|
||||
static struct grub_diskfilter_vg *
|
||||
make_vg (grub_disk_t disk,
|
||||
const struct grub_ldm_label *label)
|
||||
|
@ -226,8 +196,12 @@ make_vg (grub_disk_t disk,
|
|||
vg->name = grub_malloc (LDM_NAME_STRLEN + 1);
|
||||
vg->uuid = grub_malloc (LDM_GUID_STRLEN + 1);
|
||||
if (! vg->uuid || !vg->name)
|
||||
goto fail1;
|
||||
|
||||
{
|
||||
grub_free (vg->uuid);
|
||||
grub_free (vg->name);
|
||||
grub_free (vg);
|
||||
return NULL;
|
||||
}
|
||||
grub_memcpy (vg->uuid, label->group_guid, LDM_GUID_STRLEN);
|
||||
grub_memcpy (vg->name, label->group_name, LDM_NAME_STRLEN);
|
||||
vg->name[LDM_NAME_STRLEN] = 0;
|
||||
|
@ -246,7 +220,6 @@ make_vg (grub_disk_t disk,
|
|||
struct grub_ldm_vblk vblk[GRUB_DISK_SECTOR_SIZE
|
||||
/ sizeof (struct grub_ldm_vblk)];
|
||||
unsigned i;
|
||||
grub_size_t sz;
|
||||
err = grub_disk_read (disk, cursec, 0,
|
||||
sizeof(vblk), &vblk);
|
||||
if (err)
|
||||
|
@ -278,16 +251,10 @@ make_vg (grub_disk_t disk,
|
|||
grub_free (pv);
|
||||
goto fail2;
|
||||
}
|
||||
if (grub_add (ptr[0], 2, &sz))
|
||||
{
|
||||
grub_free (pv);
|
||||
goto fail2;
|
||||
}
|
||||
|
||||
pv->internal_id = grub_malloc (sz);
|
||||
pv->internal_id = grub_malloc (ptr[0] + 2);
|
||||
if (!pv->internal_id)
|
||||
{
|
||||
free_pv (pv);
|
||||
grub_free (pv);
|
||||
goto fail2;
|
||||
}
|
||||
grub_memcpy (pv->internal_id, ptr, (grub_size_t) ptr[0] + 1);
|
||||
|
@ -297,7 +264,7 @@ make_vg (grub_disk_t disk,
|
|||
if (ptr + *ptr + 1 >= vblk[i].dynamic
|
||||
+ sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_pv (pv);
|
||||
grub_free (pv);
|
||||
goto fail2;
|
||||
}
|
||||
/* ptr = name. */
|
||||
|
@ -305,23 +272,11 @@ make_vg (grub_disk_t disk,
|
|||
if (ptr + *ptr + 1
|
||||
>= vblk[i].dynamic + sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_pv (pv);
|
||||
grub_free (pv);
|
||||
goto fail2;
|
||||
}
|
||||
pv->id.uuidlen = *ptr;
|
||||
|
||||
if (grub_add (pv->id.uuidlen, 1, &sz))
|
||||
{
|
||||
free_pv (pv);
|
||||
goto fail2;
|
||||
}
|
||||
|
||||
pv->id.uuid = grub_malloc (sz);
|
||||
if (pv->id.uuid == NULL)
|
||||
{
|
||||
free_pv (pv);
|
||||
goto fail2;
|
||||
}
|
||||
pv->id.uuid = grub_malloc (pv->id.uuidlen + 1);
|
||||
grub_memcpy (pv->id.uuid, ptr + 1, pv->id.uuidlen);
|
||||
pv->id.uuid[pv->id.uuidlen] = 0;
|
||||
|
||||
|
@ -367,7 +322,7 @@ make_vg (grub_disk_t disk,
|
|||
lv->segments = grub_zalloc (sizeof (*lv->segments));
|
||||
if (!lv->segments)
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
lv->segments->start_extent = 0;
|
||||
|
@ -378,25 +333,20 @@ make_vg (grub_disk_t disk,
|
|||
sizeof (*lv->segments->nodes));
|
||||
if (!lv->segments->nodes)
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
ptr = vblk[i].dynamic;
|
||||
if (ptr + *ptr + 1 >= vblk[i].dynamic
|
||||
+ sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
if (grub_add (ptr[0], 2, &sz))
|
||||
{
|
||||
free_lv (lv);
|
||||
goto fail2;
|
||||
}
|
||||
lv->internal_id = grub_malloc (sz);
|
||||
lv->internal_id = grub_malloc ((grub_size_t) ptr[0] + 2);
|
||||
if (!lv->internal_id)
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
grub_memcpy (lv->internal_id, ptr, ptr[0] + 1);
|
||||
|
@ -406,18 +356,20 @@ make_vg (grub_disk_t disk,
|
|||
if (ptr + *ptr + 1 >= vblk[i].dynamic
|
||||
+ sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
if (grub_add (*ptr, 1, &sz))
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv->internal_id);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
lv->name = grub_malloc (sz);
|
||||
if (!lv->name)
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv->internal_id);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
grub_memcpy (lv->name, ptr + 1, *ptr);
|
||||
|
@ -426,28 +378,36 @@ make_vg (grub_disk_t disk,
|
|||
vg->uuid, lv->name);
|
||||
if (!lv->fullname)
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv->internal_id);
|
||||
grub_free (lv->name);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
ptr += *ptr + 1;
|
||||
if (ptr + *ptr + 1
|
||||
>= vblk[i].dynamic + sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv->internal_id);
|
||||
grub_free (lv->name);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
/* ptr = volume type. */
|
||||
ptr += *ptr + 1;
|
||||
if (ptr >= vblk[i].dynamic + sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv->internal_id);
|
||||
grub_free (lv->name);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
/* ptr = flags. */
|
||||
ptr += *ptr + 1;
|
||||
if (ptr >= vblk[i].dynamic + sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv->internal_id);
|
||||
grub_free (lv->name);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
|
||||
|
@ -456,13 +416,17 @@ make_vg (grub_disk_t disk,
|
|||
/* ptr = number of children. */
|
||||
if (ptr >= vblk[i].dynamic + sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv->internal_id);
|
||||
grub_free (lv->name);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
ptr += *ptr + 1;
|
||||
if (ptr >= vblk[i].dynamic + sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv->internal_id);
|
||||
grub_free (lv->name);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
|
||||
|
@ -472,7 +436,9 @@ make_vg (grub_disk_t disk,
|
|||
|| ptr + *ptr + 1>= vblk[i].dynamic
|
||||
+ sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (lv);
|
||||
grub_free (lv->internal_id);
|
||||
grub_free (lv->name);
|
||||
grub_free (lv);
|
||||
goto fail2;
|
||||
}
|
||||
lv->size = read_int (ptr + 1, *ptr);
|
||||
|
@ -489,7 +455,6 @@ make_vg (grub_disk_t disk,
|
|||
struct grub_ldm_vblk vblk[GRUB_DISK_SECTOR_SIZE
|
||||
/ sizeof (struct grub_ldm_vblk)];
|
||||
unsigned i;
|
||||
grub_size_t sz;
|
||||
err = grub_disk_read (disk, cursec, 0,
|
||||
sizeof(vblk), &vblk);
|
||||
if (err)
|
||||
|
@ -522,18 +487,13 @@ make_vg (grub_disk_t disk,
|
|||
ptr = vblk[i].dynamic;
|
||||
if (ptr + *ptr + 1 >= vblk[i].dynamic + sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
if (grub_add (ptr[0], 2, &sz))
|
||||
{
|
||||
free_lv (comp);
|
||||
goto fail2;
|
||||
}
|
||||
comp->internal_id = grub_malloc (sz);
|
||||
comp->internal_id = grub_malloc ((grub_size_t) ptr[0] + 2);
|
||||
if (!comp->internal_id)
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
grub_memcpy (comp->internal_id, ptr, ptr[0] + 1);
|
||||
|
@ -542,14 +502,16 @@ make_vg (grub_disk_t disk,
|
|||
ptr += *ptr + 1;
|
||||
if (ptr + *ptr + 1 >= vblk[i].dynamic + sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
/* ptr = name. */
|
||||
ptr += *ptr + 1;
|
||||
if (ptr + *ptr + 1 >= vblk[i].dynamic + sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
/* ptr = state. */
|
||||
|
@ -559,7 +521,8 @@ make_vg (grub_disk_t disk,
|
|||
ptr += 4;
|
||||
if (ptr >= vblk[i].dynamic + sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
|
||||
|
@ -567,14 +530,16 @@ make_vg (grub_disk_t disk,
|
|||
ptr += *ptr + 1;
|
||||
if (ptr >= vblk[i].dynamic + sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
ptr += 8 + 8;
|
||||
if (ptr + *ptr + 1 >= vblk[i].dynamic
|
||||
+ sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
for (lv = vg->lvs; lv; lv = lv->next)
|
||||
|
@ -585,7 +550,8 @@ make_vg (grub_disk_t disk,
|
|||
}
|
||||
if (!lv)
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
continue;
|
||||
}
|
||||
comp->size = lv->size;
|
||||
|
@ -597,7 +563,8 @@ make_vg (grub_disk_t disk,
|
|||
sizeof (*comp->segments));
|
||||
if (!comp->segments)
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
}
|
||||
|
@ -608,7 +575,8 @@ make_vg (grub_disk_t disk,
|
|||
comp->segments = grub_malloc (sizeof (*comp->segments));
|
||||
if (!comp->segments)
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
comp->segments->start_extent = 0;
|
||||
|
@ -623,21 +591,27 @@ make_vg (grub_disk_t disk,
|
|||
}
|
||||
else
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->segments);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
ptr += *ptr + 1;
|
||||
ptr++;
|
||||
if (!(vblk[i].flags & 0x10))
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->segments);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
if (ptr >= vblk[i].dynamic + sizeof (vblk[i].dynamic)
|
||||
|| ptr + *ptr + 1 >= vblk[i].dynamic
|
||||
+ sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->segments);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
comp->segments->stripe_size = read_int (ptr + 1, *ptr);
|
||||
|
@ -645,16 +619,20 @@ make_vg (grub_disk_t disk,
|
|||
if (ptr + *ptr + 1 >= vblk[i].dynamic
|
||||
+ sizeof (vblk[i].dynamic))
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->segments);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
comp->segments->node_count = read_int (ptr + 1, *ptr);
|
||||
comp->segments->node_alloc = comp->segments->node_count;
|
||||
comp->segments->nodes = grub_calloc (comp->segments->node_alloc,
|
||||
sizeof (*comp->segments->nodes));
|
||||
if (comp->segments->nodes == NULL)
|
||||
if (!lv->segments->nodes)
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->segments);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
}
|
||||
|
@ -662,18 +640,25 @@ make_vg (grub_disk_t disk,
|
|||
if (lv->segments->node_alloc == lv->segments->node_count)
|
||||
{
|
||||
void *t;
|
||||
grub_size_t sz;
|
||||
|
||||
if (grub_mul (lv->segments->node_alloc, 2, &lv->segments->node_alloc) ||
|
||||
grub_mul (lv->segments->node_alloc, sizeof (*lv->segments->nodes), &sz))
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->segments->nodes);
|
||||
grub_free (comp->segments);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
|
||||
t = grub_realloc (lv->segments->nodes, sz);
|
||||
if (!t)
|
||||
{
|
||||
free_lv (comp);
|
||||
grub_free (comp->segments->nodes);
|
||||
grub_free (comp->segments);
|
||||
grub_free (comp->internal_id);
|
||||
grub_free (comp);
|
||||
goto fail2;
|
||||
}
|
||||
lv->segments->nodes = t;
|
||||
|
@ -813,10 +798,7 @@ make_vg (grub_disk_t disk,
|
|||
comp->segments[comp->segment_count].nodes
|
||||
= grub_malloc (sizeof (*comp->segments[comp->segment_count].nodes));
|
||||
if (!comp->segments[comp->segment_count].nodes)
|
||||
{
|
||||
grub_free (comp->segments);
|
||||
goto fail2;
|
||||
}
|
||||
goto fail2;
|
||||
comp->segments[comp->segment_count].nodes[0] = part;
|
||||
comp->segment_count++;
|
||||
}
|
||||
|
@ -831,19 +813,25 @@ make_vg (grub_disk_t disk,
|
|||
struct grub_diskfilter_pv *pv, *next_pv;
|
||||
for (lv = vg->lvs; lv; lv = next_lv)
|
||||
{
|
||||
next_lv = lv->next;
|
||||
free_lv (lv);
|
||||
unsigned i;
|
||||
for (i = 0; i < lv->segment_count; i++)
|
||||
grub_free (lv->segments[i].nodes);
|
||||
|
||||
next_lv = lv->next;
|
||||
grub_free (lv->segments);
|
||||
grub_free (lv->internal_id);
|
||||
grub_free (lv->name);
|
||||
grub_free (lv->fullname);
|
||||
grub_free (lv);
|
||||
}
|
||||
for (pv = vg->pvs; pv; pv = next_pv)
|
||||
{
|
||||
next_pv = pv->next;
|
||||
free_pv (pv);
|
||||
grub_free (pv->id.uuid);
|
||||
grub_free (pv);
|
||||
}
|
||||
}
|
||||
fail1:
|
||||
grub_free (vg->uuid);
|
||||
grub_free (vg->name);
|
||||
grub_free (vg);
|
||||
return NULL;
|
||||
}
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
#include <grub/mm.h>
|
||||
#include <grub/extcmd.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -34,7 +33,6 @@ struct grub_loopback
|
|||
grub_file_t file;
|
||||
struct grub_loopback *next;
|
||||
unsigned long id;
|
||||
grub_uint64_t refcnt;
|
||||
};
|
||||
|
||||
static struct grub_loopback *loopback_list;
|
||||
|
@ -66,8 +64,6 @@ delete_loopback (const char *name)
|
|||
if (! dev)
|
||||
return grub_error (GRUB_ERR_BAD_DEVICE, "device not found");
|
||||
|
||||
if (dev->refcnt > 0)
|
||||
return grub_error (GRUB_ERR_STILL_REFERENCED, "device still referenced");
|
||||
/* Remove the device from the list. */
|
||||
*prev = dev->next;
|
||||
|
||||
|
@ -124,7 +120,6 @@ grub_cmd_loopback (grub_extcmd_context_t ctxt, int argc, char **args)
|
|||
|
||||
newdev->file = file;
|
||||
newdev->id = last_id++;
|
||||
newdev->refcnt = 0;
|
||||
|
||||
/* Add the new entry to the list. */
|
||||
newdev->next = loopback_list;
|
||||
|
@ -166,9 +161,6 @@ grub_loopback_open (const char *name, grub_disk_t disk)
|
|||
if (! dev)
|
||||
return grub_error (GRUB_ERR_UNKNOWN_DEVICE, "can't open device");
|
||||
|
||||
if (grub_add (dev->refcnt, 1, &dev->refcnt))
|
||||
grub_fatal ("Reference count overflow");
|
||||
|
||||
/* Use the filesize for the disk size, round up to a complete sector. */
|
||||
if (dev->file->size != GRUB_FILE_SIZE_UNKNOWN)
|
||||
disk->total_sectors = ((dev->file->size + GRUB_DISK_SECTOR_SIZE - 1)
|
||||
|
@ -186,15 +178,6 @@ grub_loopback_open (const char *name, grub_disk_t disk)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static void
|
||||
grub_loopback_close (grub_disk_t disk)
|
||||
{
|
||||
struct grub_loopback *dev = disk->data;
|
||||
|
||||
if (grub_sub (dev->refcnt, 1, &dev->refcnt))
|
||||
grub_fatal ("Reference count underflow");
|
||||
}
|
||||
|
||||
static grub_err_t
|
||||
grub_loopback_read (grub_disk_t disk, grub_disk_addr_t sector,
|
||||
grub_size_t size, char *buf)
|
||||
|
@ -237,7 +220,6 @@ static struct grub_disk_dev grub_loopback_dev =
|
|||
.id = GRUB_DISK_DEVICE_LOOPBACK_ID,
|
||||
.disk_iterate = grub_loopback_iterate,
|
||||
.disk_open = grub_loopback_open,
|
||||
.disk_close = grub_loopback_close,
|
||||
.disk_read = grub_loopback_read,
|
||||
.disk_write = grub_loopback_write,
|
||||
.next = 0
|
||||
|
|
|
@ -26,7 +26,6 @@
|
|||
#include <grub/crypto.h>
|
||||
#include <grub/partition.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
#include <base64.h>
|
||||
#include <json.h>
|
||||
|
@ -570,7 +569,6 @@ luks2_recover_key (grub_disk_t source,
|
|||
gcry_err_code_t gcry_ret;
|
||||
grub_json_t *json = NULL, keyslots;
|
||||
grub_err_t ret;
|
||||
grub_size_t sz;
|
||||
|
||||
if (cargs->key_data == NULL || cargs->key_len == 0)
|
||||
return grub_error (GRUB_ERR_BAD_ARGUMENT, "no key data");
|
||||
|
@ -579,12 +577,7 @@ luks2_recover_key (grub_disk_t source,
|
|||
if (ret)
|
||||
return ret;
|
||||
|
||||
grub_puts_ (N_("Attempting to decrypt master key..."));
|
||||
|
||||
if (grub_sub (grub_be_to_cpu64 (header.hdr_size), sizeof (header), &sz))
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, "underflow detected while calculating json header size");
|
||||
|
||||
json_header = grub_zalloc (sz);
|
||||
json_header = grub_zalloc (grub_be_to_cpu64 (header.hdr_size) - sizeof (header));
|
||||
if (!json_header)
|
||||
return GRUB_ERR_OUT_OF_MEMORY;
|
||||
|
||||
|
|
|
@ -34,11 +34,12 @@
|
|||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
struct ignored_feature_lv
|
||||
struct cache_lv
|
||||
{
|
||||
struct grub_diskfilter_lv *lv;
|
||||
char *cache_pool;
|
||||
char *origin;
|
||||
struct ignored_feature_lv *next;
|
||||
struct cache_lv *next;
|
||||
};
|
||||
|
||||
|
||||
|
@ -104,29 +105,30 @@ grub_lvm_check_flag (const char *p, const char *str, const char *flag)
|
|||
}
|
||||
|
||||
static void
|
||||
grub_lvm_free_ignored_feature_lvs (struct ignored_feature_lv *ignored_feature_lvs)
|
||||
grub_lvm_free_cache_lvs (struct cache_lv *cache_lvs)
|
||||
{
|
||||
struct ignored_feature_lv *ignored_feature;
|
||||
struct cache_lv *cache;
|
||||
|
||||
while ((ignored_feature = ignored_feature_lvs))
|
||||
while ((cache = cache_lvs))
|
||||
{
|
||||
ignored_feature_lvs = ignored_feature_lvs->next;
|
||||
cache_lvs = cache_lvs->next;
|
||||
|
||||
if (ignored_feature->lv)
|
||||
if (cache->lv)
|
||||
{
|
||||
unsigned int i;
|
||||
|
||||
for (i = 0; i < ignored_feature->lv->segment_count; ++i)
|
||||
if (ignored_feature->lv->segments)
|
||||
grub_free (ignored_feature->lv->segments[i].nodes);
|
||||
grub_free (ignored_feature->lv->segments);
|
||||
grub_free (ignored_feature->lv->fullname);
|
||||
grub_free (ignored_feature->lv->idname);
|
||||
grub_free (ignored_feature->lv->name);
|
||||
for (i = 0; i < cache->lv->segment_count; ++i)
|
||||
if (cache->lv->segments)
|
||||
grub_free (cache->lv->segments[i].nodes);
|
||||
grub_free (cache->lv->segments);
|
||||
grub_free (cache->lv->fullname);
|
||||
grub_free (cache->lv->idname);
|
||||
grub_free (cache->lv->name);
|
||||
}
|
||||
grub_free (ignored_feature->lv);
|
||||
grub_free (ignored_feature->origin);
|
||||
grub_free (ignored_feature);
|
||||
grub_free (cache->lv);
|
||||
grub_free (cache->origin);
|
||||
grub_free (cache->cache_pool);
|
||||
grub_free (cache);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -288,7 +290,7 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
|
||||
p = q = (char *)ptr;
|
||||
|
||||
if (grub_add (ptr, (grub_size_t) grub_le_to_cpu64 (rlocn->size), &ptr))
|
||||
if (grub_add ((grub_size_t)metadatabuf, (grub_size_t)mda_size, &ptr))
|
||||
goto error_parsing_metadata;
|
||||
|
||||
mda_end = (char *)ptr;
|
||||
|
@ -323,7 +325,7 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
|
||||
if (! vg)
|
||||
{
|
||||
struct ignored_feature_lv *ignored_feature_lvs = NULL;
|
||||
struct cache_lv *cache_lvs = NULL;
|
||||
|
||||
/* First time we see this volume group. We've to create the
|
||||
whole volume group structure. */
|
||||
|
@ -368,8 +370,6 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
break;
|
||||
|
||||
pv = grub_zalloc (sizeof (*pv));
|
||||
if (pv == NULL)
|
||||
goto fail4;
|
||||
q = p;
|
||||
while (*q != ' ' && q < mda_end)
|
||||
q++;
|
||||
|
@ -379,8 +379,6 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
|
||||
s = q - p;
|
||||
pv->name = grub_malloc (s + 1);
|
||||
if (pv->name == NULL)
|
||||
goto pvs_fail_noname;
|
||||
grub_memcpy (pv->name, p, s);
|
||||
pv->name[s] = '\0';
|
||||
|
||||
|
@ -453,8 +451,6 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
break;
|
||||
|
||||
lv = grub_zalloc (sizeof (*lv));
|
||||
if (lv == NULL)
|
||||
goto fail4;
|
||||
|
||||
q = p;
|
||||
while (*q != ' ' && q < mda_end)
|
||||
|
@ -549,8 +545,6 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
goto lvs_fail;
|
||||
}
|
||||
lv->segments = grub_calloc (lv->segment_count, sizeof (*seg));
|
||||
if (lv->segments == NULL)
|
||||
goto lvs_fail;
|
||||
seg = lv->segments;
|
||||
|
||||
for (i = 0; i < lv->segment_count; i++)
|
||||
|
@ -618,8 +612,6 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
|
||||
seg->nodes = grub_calloc (seg->node_count,
|
||||
sizeof (*stripe));
|
||||
if (seg->nodes == NULL)
|
||||
goto lvs_segment_fail;
|
||||
stripe = seg->nodes;
|
||||
|
||||
p = grub_strstr (p, "stripes = [");
|
||||
|
@ -679,9 +671,8 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
goto lvs_segment_fail;
|
||||
}
|
||||
|
||||
seg->nodes = grub_calloc (seg->node_count, sizeof (seg->nodes[0]));
|
||||
if (seg->nodes == NULL)
|
||||
goto lvs_segment_fail;
|
||||
seg->nodes = grub_zalloc (sizeof (seg->nodes[0])
|
||||
* seg->node_count);
|
||||
|
||||
p = grub_strstr (p, "mirrors = [");
|
||||
if (p == NULL)
|
||||
|
@ -769,9 +760,8 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
}
|
||||
}
|
||||
|
||||
seg->nodes = grub_calloc (seg->node_count, sizeof (seg->nodes[0]));
|
||||
if (seg->nodes == NULL)
|
||||
goto lvs_segment_fail;
|
||||
seg->nodes = grub_zalloc (sizeof (seg->nodes[0])
|
||||
* seg->node_count);
|
||||
|
||||
p = grub_strstr (p, "raids = [");
|
||||
if (p == NULL)
|
||||
|
@ -817,98 +807,108 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
seg->nodes[seg->node_count - 1].name = tmp;
|
||||
}
|
||||
}
|
||||
/*
|
||||
* Cache and integrity LVs have extra parts that
|
||||
* we can ignore for our read-only access.
|
||||
*/
|
||||
else if (grub_strncmp (p, "cache\"", sizeof ("cache\"") - 1) == 0 ||
|
||||
grub_strncmp (p, "cache+CACHE_USES_CACHEVOL\"", sizeof ("cache+CACHE_USES_CACHEVOL\"") - 1) == 0 ||
|
||||
grub_strncmp (p, "integrity\"", sizeof ("integrity\"") - 1) == 0)
|
||||
else if (grub_memcmp (p, "cache\"",
|
||||
sizeof ("cache\"") - 1) == 0)
|
||||
{
|
||||
struct ignored_feature_lv *ignored_feature = NULL;
|
||||
struct cache_lv *cache = NULL;
|
||||
|
||||
char *p2, *p3;
|
||||
grub_size_t sz;
|
||||
#ifdef GRUB_UTIL
|
||||
p2 = grub_strchr (p, '"');
|
||||
if (p2)
|
||||
*p2 = '\0';
|
||||
grub_util_info ("Ignoring extra metadata type '%s' for %s", p, lv->name);
|
||||
if (p2)
|
||||
*p2 ='"';
|
||||
#endif
|
||||
|
||||
ignored_feature = grub_zalloc (sizeof (*ignored_feature));
|
||||
if (!ignored_feature)
|
||||
goto ignored_feature_lv_fail;
|
||||
ignored_feature->lv = grub_zalloc (sizeof (*ignored_feature->lv));
|
||||
if (!ignored_feature->lv)
|
||||
goto ignored_feature_lv_fail;
|
||||
grub_memcpy (ignored_feature->lv, lv, sizeof (*ignored_feature->lv));
|
||||
cache = grub_zalloc (sizeof (*cache));
|
||||
if (!cache)
|
||||
goto cache_lv_fail;
|
||||
cache->lv = grub_zalloc (sizeof (*cache->lv));
|
||||
if (!cache->lv)
|
||||
goto cache_lv_fail;
|
||||
grub_memcpy (cache->lv, lv, sizeof (*cache->lv));
|
||||
|
||||
if (lv->fullname)
|
||||
{
|
||||
ignored_feature->lv->fullname = grub_strdup (lv->fullname);
|
||||
if (!ignored_feature->lv->fullname)
|
||||
goto ignored_feature_lv_fail;
|
||||
cache->lv->fullname = grub_strdup (lv->fullname);
|
||||
if (!cache->lv->fullname)
|
||||
goto cache_lv_fail;
|
||||
}
|
||||
if (lv->idname)
|
||||
{
|
||||
ignored_feature->lv->idname = grub_strdup (lv->idname);
|
||||
if (!ignored_feature->lv->idname)
|
||||
goto ignored_feature_lv_fail;
|
||||
cache->lv->idname = grub_strdup (lv->idname);
|
||||
if (!cache->lv->idname)
|
||||
goto cache_lv_fail;
|
||||
}
|
||||
if (lv->name)
|
||||
{
|
||||
ignored_feature->lv->name = grub_strdup (lv->name);
|
||||
if (!ignored_feature->lv->name)
|
||||
goto ignored_feature_lv_fail;
|
||||
cache->lv->name = grub_strdup (lv->name);
|
||||
if (!cache->lv->name)
|
||||
goto cache_lv_fail;
|
||||
}
|
||||
|
||||
skip_lv = 1;
|
||||
|
||||
|
||||
p2 = grub_strstr (p, "origin = \"");
|
||||
p2 = grub_strstr (p, "cache_pool = \"");
|
||||
if (!p2)
|
||||
goto ignored_feature_lv_fail;
|
||||
goto cache_lv_fail;
|
||||
|
||||
p2 = grub_strchr (p2, '"');
|
||||
if (!p2)
|
||||
goto ignored_feature_lv_fail;
|
||||
goto cache_lv_fail;
|
||||
|
||||
p3 = ++p2;
|
||||
if (p3 == mda_end)
|
||||
goto ignored_feature_lv_fail;
|
||||
goto cache_lv_fail;
|
||||
p3 = grub_strchr (p3, '"');
|
||||
if (!p3)
|
||||
goto ignored_feature_lv_fail;
|
||||
goto cache_lv_fail;
|
||||
|
||||
sz = p3 - p2;
|
||||
|
||||
ignored_feature->origin = grub_malloc (sz + 1);
|
||||
if (!ignored_feature->origin)
|
||||
goto ignored_feature_lv_fail;
|
||||
grub_memcpy (ignored_feature->origin, p2, sz);
|
||||
ignored_feature->origin[sz] = '\0';
|
||||
cache->cache_pool = grub_malloc (sz + 1);
|
||||
if (!cache->cache_pool)
|
||||
goto cache_lv_fail;
|
||||
grub_memcpy (cache->cache_pool, p2, sz);
|
||||
cache->cache_pool[sz] = '\0';
|
||||
|
||||
ignored_feature->next = ignored_feature_lvs;
|
||||
ignored_feature_lvs = ignored_feature;
|
||||
p2 = grub_strstr (p, "origin = \"");
|
||||
if (!p2)
|
||||
goto cache_lv_fail;
|
||||
|
||||
p2 = grub_strchr (p2, '"');
|
||||
if (!p2)
|
||||
goto cache_lv_fail;
|
||||
|
||||
p3 = ++p2;
|
||||
if (p3 == mda_end)
|
||||
goto cache_lv_fail;
|
||||
p3 = grub_strchr (p3, '"');
|
||||
if (!p3)
|
||||
goto cache_lv_fail;
|
||||
|
||||
sz = p3 - p2;
|
||||
|
||||
cache->origin = grub_malloc (sz + 1);
|
||||
if (!cache->origin)
|
||||
goto cache_lv_fail;
|
||||
grub_memcpy (cache->origin, p2, sz);
|
||||
cache->origin[sz] = '\0';
|
||||
|
||||
cache->next = cache_lvs;
|
||||
cache_lvs = cache;
|
||||
break;
|
||||
|
||||
ignored_feature_lv_fail:
|
||||
if (ignored_feature)
|
||||
cache_lv_fail:
|
||||
if (cache)
|
||||
{
|
||||
grub_free (ignored_feature->origin);
|
||||
if (ignored_feature->lv)
|
||||
grub_free (cache->origin);
|
||||
grub_free (cache->cache_pool);
|
||||
if (cache->lv)
|
||||
{
|
||||
grub_free (ignored_feature->lv->fullname);
|
||||
grub_free (ignored_feature->lv->idname);
|
||||
grub_free (ignored_feature->lv->name);
|
||||
grub_free (cache->lv->fullname);
|
||||
grub_free (cache->lv->idname);
|
||||
grub_free (cache->lv->name);
|
||||
}
|
||||
grub_free (ignored_feature->lv);
|
||||
grub_free (ignored_feature);
|
||||
grub_free (cache->lv);
|
||||
grub_free (cache);
|
||||
}
|
||||
grub_lvm_free_ignored_feature_lvs (ignored_feature_lvs);
|
||||
grub_lvm_free_cache_lvs (cache_lvs);
|
||||
goto fail4;
|
||||
}
|
||||
else
|
||||
|
@ -917,7 +917,7 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
char *p2;
|
||||
p2 = grub_strchr (p, '"');
|
||||
if (p2)
|
||||
*p2 = '\0';
|
||||
*p2 = 0;
|
||||
grub_util_info ("unknown LVM type %s", p);
|
||||
if (p2)
|
||||
*p2 ='"';
|
||||
|
@ -961,68 +961,10 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
{
|
||||
struct ignored_feature_lv *ignored_feature;
|
||||
|
||||
for (ignored_feature = ignored_feature_lvs; ignored_feature; ignored_feature = ignored_feature->next)
|
||||
{
|
||||
struct grub_diskfilter_lv *lv;
|
||||
|
||||
for (lv = vg->lvs; lv; lv = lv->next)
|
||||
if (grub_strcmp (lv->name, ignored_feature->origin) == 0)
|
||||
break;
|
||||
if (lv)
|
||||
{
|
||||
ignored_feature->lv->segments = grub_calloc (lv->segment_count, sizeof (*lv->segments));
|
||||
if (!ignored_feature->lv->segments)
|
||||
{
|
||||
grub_lvm_free_ignored_feature_lvs (ignored_feature_lvs);
|
||||
goto fail4;
|
||||
}
|
||||
grub_memcpy (ignored_feature->lv->segments, lv->segments, lv->segment_count * sizeof (*lv->segments));
|
||||
|
||||
for (i = 0; i < lv->segment_count; ++i)
|
||||
{
|
||||
struct grub_diskfilter_node *nodes = lv->segments[i].nodes;
|
||||
grub_size_t node_count = lv->segments[i].node_count;
|
||||
|
||||
ignored_feature->lv->segments[i].nodes = grub_calloc (node_count, sizeof (*nodes));
|
||||
if (!ignored_feature->lv->segments[i].nodes)
|
||||
{
|
||||
for (j = 0; j < i; ++j)
|
||||
grub_free (ignored_feature->lv->segments[j].nodes);
|
||||
grub_free (ignored_feature->lv->segments);
|
||||
ignored_feature->lv->segments = NULL;
|
||||
grub_lvm_free_ignored_feature_lvs (ignored_feature_lvs);
|
||||
goto fail4;
|
||||
}
|
||||
grub_memcpy (ignored_feature->lv->segments[i].nodes, nodes, node_count * sizeof (*nodes));
|
||||
}
|
||||
|
||||
if (ignored_feature->lv->segments)
|
||||
{
|
||||
ignored_feature->lv->segment_count = lv->segment_count;
|
||||
ignored_feature->lv->vg = vg;
|
||||
ignored_feature->lv->next = vg->lvs;
|
||||
vg->lvs = ignored_feature->lv;
|
||||
ignored_feature->lv = NULL;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
#ifdef GRUB_UTIL
|
||||
grub_util_info ("Couldn't find LVM part of ignored feature on %s", ignored_feature->origin);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Match LVs. Must be done after cache and integrity are found. */
|
||||
/* Match lvs. */
|
||||
{
|
||||
struct grub_diskfilter_lv *lv1;
|
||||
struct grub_diskfilter_lv *lv2;
|
||||
|
||||
for (lv1 = vg->lvs; lv1; lv1 = lv1->next)
|
||||
for (i = 0; i < lv1->segment_count; i++)
|
||||
for (j = 0; j < lv1->segments[i].node_count; j++)
|
||||
|
@ -1047,9 +989,60 @@ grub_lvm_detect (grub_disk_t disk,
|
|||
lv1->segments[i].nodes[j].lv = lv2;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
grub_lvm_free_ignored_feature_lvs (ignored_feature_lvs);
|
||||
{
|
||||
struct cache_lv *cache;
|
||||
|
||||
for (cache = cache_lvs; cache; cache = cache->next)
|
||||
{
|
||||
struct grub_diskfilter_lv *lv;
|
||||
|
||||
for (lv = vg->lvs; lv; lv = lv->next)
|
||||
if (grub_strcmp (lv->name, cache->origin) == 0)
|
||||
break;
|
||||
if (lv)
|
||||
{
|
||||
cache->lv->segments = grub_calloc (lv->segment_count, sizeof (*lv->segments));
|
||||
if (!cache->lv->segments)
|
||||
{
|
||||
grub_lvm_free_cache_lvs (cache_lvs);
|
||||
goto fail4;
|
||||
}
|
||||
grub_memcpy (cache->lv->segments, lv->segments, lv->segment_count * sizeof (*lv->segments));
|
||||
|
||||
for (i = 0; i < lv->segment_count; ++i)
|
||||
{
|
||||
struct grub_diskfilter_node *nodes = lv->segments[i].nodes;
|
||||
grub_size_t node_count = lv->segments[i].node_count;
|
||||
|
||||
cache->lv->segments[i].nodes = grub_calloc (node_count, sizeof (*nodes));
|
||||
if (!cache->lv->segments[i].nodes)
|
||||
{
|
||||
for (j = 0; j < i; ++j)
|
||||
grub_free (cache->lv->segments[j].nodes);
|
||||
grub_free (cache->lv->segments);
|
||||
cache->lv->segments = NULL;
|
||||
grub_lvm_free_cache_lvs (cache_lvs);
|
||||
goto fail4;
|
||||
}
|
||||
grub_memcpy (cache->lv->segments[i].nodes, nodes, node_count * sizeof (*nodes));
|
||||
}
|
||||
|
||||
if (cache->lv->segments)
|
||||
{
|
||||
cache->lv->segment_count = lv->segment_count;
|
||||
cache->lv->vg = vg;
|
||||
cache->lv->next = vg->lvs;
|
||||
vg->lvs = cache->lv;
|
||||
cache->lv = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
grub_lvm_free_cache_lvs (cache_lvs);
|
||||
if (grub_diskfilter_vg_register (vg))
|
||||
goto fail4;
|
||||
}
|
||||
|
|
|
@ -23,7 +23,6 @@
|
|||
#include <grub/err.h>
|
||||
#include <grub/misc.h>
|
||||
#include <grub/diskfilter.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -104,9 +103,6 @@ struct grub_raid_super_1x
|
|||
|
||||
#define WriteMostly1 1 /* Mask for writemostly flag in above devflags. */
|
||||
|
||||
#define GRUB_MD_SECTOR_SHIFT 9 /* Follow Linux kernel v6.8. */
|
||||
#define GRUB_MD_SECTOR_SIZE (1 << GRUB_MD_SECTOR_SHIFT)
|
||||
|
||||
static struct grub_diskfilter_vg *
|
||||
grub_mdraid_detect (grub_disk_t disk,
|
||||
struct grub_diskfilter_pv_id *id,
|
||||
|
@ -133,7 +129,6 @@ grub_mdraid_detect (grub_disk_t disk,
|
|||
grub_uint32_t level;
|
||||
struct grub_diskfilter_vg *array;
|
||||
char *uuid;
|
||||
grub_uint64_t sb_sz, data_end, sb_end;
|
||||
|
||||
if (size == GRUB_DISK_SIZE_UNKNOWN && minor_version == 0)
|
||||
continue;
|
||||
|
@ -159,79 +154,6 @@ grub_mdraid_detect (grub_disk_t disk,
|
|||
|| grub_le_to_cpu64 (sb.super_offset) != sector)
|
||||
continue;
|
||||
|
||||
/*
|
||||
* The first check follows the Linux kernel's data_size
|
||||
* validation from v6.8-rc5.
|
||||
*/
|
||||
if (grub_le_to_cpu64 (sb.data_size) < 10 ||
|
||||
grub_le_to_cpu64 (sb.raid_disks) > GRUB_MDRAID_MAX_DISKS)
|
||||
{
|
||||
grub_dprintf ("mdraid1x", "Corrupted superblock\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/*
|
||||
* Total size of superblock: 256 bytes plus 2 bytes per device
|
||||
* in the array.
|
||||
*/
|
||||
sb_sz = sizeof (struct grub_raid_super_1x) + grub_le_to_cpu64 (sb.raid_disks) * 2;
|
||||
|
||||
if (grub_add (grub_le_to_cpu64 (sb.super_offset),
|
||||
(ALIGN_UP(sb_sz, GRUB_MD_SECTOR_SIZE) >> GRUB_MD_SECTOR_SHIFT), &sb_end))
|
||||
{
|
||||
grub_dprintf ("mdraid1x", "Invalid superblock end.\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (grub_add (grub_le_to_cpu64 (sb.data_offset),
|
||||
grub_le_to_cpu64 (sb.data_size), &data_end))
|
||||
{
|
||||
grub_dprintf ("mdraid1x", "Invalid data end.\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* In minor versions 1 and 2, superblock is positioned before data. */
|
||||
if (minor_version)
|
||||
{
|
||||
if (grub_le_to_cpu64 (sb.data_offset) < sb_end)
|
||||
{
|
||||
grub_dprintf ("mdraid1x",
|
||||
"The superblock either overlaps with the data "
|
||||
"or is behind it.\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (data_end > size)
|
||||
{
|
||||
grub_dprintf ("mdraid1x",
|
||||
"The data region ends at %" PRIuGRUB_UINT64_T ", "
|
||||
"past the end of the disk (%" PRIuGRUB_UINT64_T ")\n",
|
||||
data_end, size);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* In minor version 0, superblock is at the end of the device. */
|
||||
if (grub_le_to_cpu64 (sb.super_offset) < data_end)
|
||||
{
|
||||
grub_dprintf ("mdraid1x",
|
||||
"The data either overlaps with the superblock "
|
||||
"or is behind it.\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (sb_end > size)
|
||||
{
|
||||
grub_dprintf ("mdraid1x",
|
||||
"The superblock region ends at "
|
||||
"%" PRIuGRUB_UINT64_T ", past the end of "
|
||||
"the disk (%" PRIuGRUB_UINT64_T ")\n",
|
||||
sb_end, size);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
if (sb.major_version != grub_cpu_to_le32_compile_time (1))
|
||||
/* Unsupported version. */
|
||||
return NULL;
|
||||
|
|
|
@ -23,7 +23,6 @@
|
|||
#include <grub/misc.h>
|
||||
#include <grub/mm.h>
|
||||
#include <grub/types.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -97,14 +96,8 @@ GRUB_MOD_INIT(memdisk)
|
|||
|
||||
grub_dprintf ("memdisk", "Found memdisk image at %p\n", memdisk_orig_addr);
|
||||
|
||||
if (grub_sub (header->size, sizeof (struct grub_module_header), &memdisk_size))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, "underflow detected while obtaining memdisk size");
|
||||
return;
|
||||
}
|
||||
memdisk_size = header->size - sizeof (struct grub_module_header);
|
||||
memdisk_addr = grub_malloc (memdisk_size);
|
||||
if (memdisk_addr == NULL)
|
||||
return;
|
||||
|
||||
grub_dprintf ("memdisk", "Copying memdisk image to dynamic memory\n");
|
||||
grub_memmove (memdisk_addr, memdisk_orig_addr, memdisk_size);
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
#include <grub/extcmd.h>
|
||||
#include <grub/partition.h>
|
||||
#include <grub/file.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -127,7 +126,7 @@ plainmount_configure_password (grub_cryptodisk_t dev, const char *hash,
|
|||
grub_uint8_t *derived_hash, *dh;
|
||||
char *p;
|
||||
unsigned int round, i, len, size;
|
||||
grub_size_t alloc_size, sz;
|
||||
grub_size_t alloc_size;
|
||||
grub_err_t err = GRUB_ERR_NONE;
|
||||
|
||||
/* Support none (plain) hash */
|
||||
|
@ -146,11 +145,7 @@ plainmount_configure_password (grub_cryptodisk_t dev, const char *hash,
|
|||
* Allocate buffer for the password and for an added prefix character
|
||||
* for each hash round ('alloc_size' may not be a multiple of 'len').
|
||||
*/
|
||||
if (grub_add (alloc_size, (alloc_size / len), &sz) ||
|
||||
grub_add (sz, 1, &sz))
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow detected while allocating size of password buffer"));
|
||||
|
||||
p = grub_zalloc (sz);
|
||||
p = grub_zalloc (alloc_size + (alloc_size / len) + 1);
|
||||
derived_hash = grub_zalloc (GRUB_CRYPTODISK_MAX_KEYLEN * 2);
|
||||
if (p == NULL || derived_hash == NULL)
|
||||
{
|
||||
|
|
|
@ -66,7 +66,7 @@ efiemu_convert_pointer (grub_efi_uintn_t debug_disposition,
|
|||
|
||||
grub_efi_status_t __grub_efi_api
|
||||
efiemu_get_variable (grub_efi_char16_t *variable_name,
|
||||
const grub_packed_guid_t *vendor_guid,
|
||||
const grub_guid_t *vendor_guid,
|
||||
grub_efi_uint32_t *attributes,
|
||||
grub_efi_uintn_t *data_size,
|
||||
void *data);
|
||||
|
@ -74,11 +74,11 @@ efiemu_get_variable (grub_efi_char16_t *variable_name,
|
|||
grub_efi_status_t __grub_efi_api
|
||||
efiemu_get_next_variable_name (grub_efi_uintn_t *variable_name_size,
|
||||
grub_efi_char16_t *variable_name,
|
||||
grub_packed_guid_t *vendor_guid);
|
||||
grub_guid_t *vendor_guid);
|
||||
|
||||
grub_efi_status_t __grub_efi_api
|
||||
efiemu_set_variable (grub_efi_char16_t *variable_name,
|
||||
const grub_packed_guid_t *vendor_guid,
|
||||
const grub_guid_t *vendor_guid,
|
||||
grub_efi_uint32_t attributes,
|
||||
grub_efi_uintn_t data_size,
|
||||
void *data);
|
||||
|
@ -416,7 +416,7 @@ EFI_FUNC (efiemu_convert_pointer) (grub_efi_uintn_t debug_disposition,
|
|||
|
||||
/* Find variable by name and GUID. */
|
||||
static struct efi_variable *
|
||||
find_variable (const grub_packed_guid_t *vendor_guid,
|
||||
find_variable (const grub_guid_t *vendor_guid,
|
||||
grub_efi_char16_t *variable_name)
|
||||
{
|
||||
grub_uint8_t *ptr;
|
||||
|
@ -438,7 +438,7 @@ find_variable (const grub_packed_guid_t *vendor_guid,
|
|||
|
||||
grub_efi_status_t __grub_efi_api
|
||||
EFI_FUNC (efiemu_get_variable) (grub_efi_char16_t *variable_name,
|
||||
const grub_packed_guid_t *vendor_guid,
|
||||
const grub_guid_t *vendor_guid,
|
||||
grub_efi_uint32_t *attributes,
|
||||
grub_efi_uintn_t *data_size,
|
||||
void *data)
|
||||
|
@ -464,7 +464,7 @@ EFI_FUNC (efiemu_get_variable) (grub_efi_char16_t *variable_name,
|
|||
grub_efi_status_t __grub_efi_api EFI_FUNC
|
||||
(efiemu_get_next_variable_name) (grub_efi_uintn_t *variable_name_size,
|
||||
grub_efi_char16_t *variable_name,
|
||||
grub_packed_guid_t *vendor_guid)
|
||||
grub_guid_t *vendor_guid)
|
||||
{
|
||||
struct efi_variable *efivar;
|
||||
LOG ('l');
|
||||
|
@ -503,7 +503,7 @@ grub_efi_status_t __grub_efi_api EFI_FUNC
|
|||
|
||||
grub_efi_status_t __grub_efi_api
|
||||
EFI_FUNC (efiemu_set_variable) (grub_efi_char16_t *variable_name,
|
||||
const grub_packed_guid_t *vendor_guid,
|
||||
const grub_guid_t *vendor_guid,
|
||||
grub_efi_uint32_t attributes,
|
||||
grub_efi_uintn_t data_size,
|
||||
void *data)
|
||||
|
@ -597,30 +597,9 @@ struct grub_efi_runtime_services efiemu_runtime_services =
|
|||
.set_virtual_address_map = efiemu_set_virtual_address_map,
|
||||
.convert_pointer = efiemu_convert_pointer,
|
||||
|
||||
/*
|
||||
The code is structured in a way to accept unaligned inputs
|
||||
in most cases and supply 4-byte aligned outputs.
|
||||
|
||||
Efiemu case is a bit ugly because there inputs and outputs are
|
||||
reversed and so we need careful casts to account for this
|
||||
inversion.
|
||||
*/
|
||||
.get_variable = (grub_efi_status_t
|
||||
(__grub_efi_api *) (grub_efi_char16_t *variable_name,
|
||||
const grub_guid_t *vendor_guid,
|
||||
grub_efi_uint32_t *attributes,
|
||||
grub_efi_uintn_t *data_size,
|
||||
void *data)) efiemu_get_variable,
|
||||
.get_next_variable_name = (grub_efi_status_t
|
||||
(__grub_efi_api *) (grub_efi_uintn_t *variable_name_size,
|
||||
grub_efi_char16_t *variable_name,
|
||||
grub_guid_t *vendor_guid)) efiemu_get_next_variable_name,
|
||||
.set_variable = (grub_efi_status_t
|
||||
(__grub_efi_api *) (grub_efi_char16_t *variable_name,
|
||||
const grub_guid_t *vendor_guid,
|
||||
grub_efi_uint32_t attributes,
|
||||
grub_efi_uintn_t data_size,
|
||||
void *data)) efiemu_set_variable,
|
||||
.get_variable = efiemu_get_variable,
|
||||
.get_next_variable_name = efiemu_get_next_variable_name,
|
||||
.set_variable = efiemu_set_variable,
|
||||
.get_next_high_monotonic_count = efiemu_get_next_high_monotonic_count,
|
||||
|
||||
.reset_system = efiemu_reset_system
|
||||
|
|
|
@ -26,7 +26,6 @@
|
|||
#include <grub/types.h>
|
||||
#include <grub/fshelp.h>
|
||||
#include <grub/charset.h>
|
||||
#include <grub/lockdown.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -704,16 +703,11 @@ static struct grub_fs grub_affs_fs =
|
|||
|
||||
GRUB_MOD_INIT(affs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
{
|
||||
grub_affs_fs.mod = mod;
|
||||
grub_fs_register (&grub_affs_fs);
|
||||
}
|
||||
grub_fs_register (&grub_affs_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
||||
GRUB_MOD_FINI(affs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_unregister (&grub_affs_fs);
|
||||
grub_fs_unregister (&grub_affs_fs);
|
||||
}
|
||||
|
|
|
@ -21,7 +21,6 @@
|
|||
#include <grub/fs.h>
|
||||
#include <grub/disk.h>
|
||||
#include <grub/dl.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -69,7 +68,6 @@ handle_symlink (struct grub_archelp_data *data,
|
|||
char *rest;
|
||||
char *linktarget;
|
||||
grub_size_t linktarget_len;
|
||||
grub_size_t sz;
|
||||
|
||||
*restart = 0;
|
||||
|
||||
|
@ -100,12 +98,7 @@ handle_symlink (struct grub_archelp_data *data,
|
|||
if (linktarget[0] == '\0')
|
||||
return GRUB_ERR_NONE;
|
||||
linktarget_len = grub_strlen (linktarget);
|
||||
|
||||
if (grub_add (linktarget_len, grub_strlen (*name), &sz) ||
|
||||
grub_add (sz, 2, &sz))
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, N_("link target length overflow"));
|
||||
|
||||
target = grub_malloc (sz);
|
||||
target = grub_malloc (linktarget_len + grub_strlen (*name) + 2);
|
||||
if (!target)
|
||||
return grub_errno;
|
||||
|
||||
|
@ -187,14 +180,6 @@ grub_archelp_dir (struct grub_archelp_data *data,
|
|||
if (p)
|
||||
*p = 0;
|
||||
|
||||
if ((*n == 0) && ((mode & GRUB_ARCHELP_ATTR_TYPE)
|
||||
!= GRUB_ARCHELP_ATTR_DIR))
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FILE_TYPE, N_("not a directory"));
|
||||
grub_free (name);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
if (((!prev) || (grub_strcmp (prev, name) != 0)) && *n != 0)
|
||||
{
|
||||
struct grub_dirhook_info info;
|
||||
|
|
|
@ -30,7 +30,6 @@
|
|||
#include <grub/types.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/fshelp.h>
|
||||
#include <grub/lockdown.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -809,7 +808,7 @@ find_file (const char *path, grub_disk_t disk,
|
|||
.disk = disk,
|
||||
.sb = sb,
|
||||
};
|
||||
struct grub_fshelp_node *found = NULL;
|
||||
struct grub_fshelp_node *found;
|
||||
|
||||
err = read_extent (disk, sb, &sb->root_dir, 0, 0, &root.ino,
|
||||
sizeof (root.ino));
|
||||
|
@ -1107,11 +1106,7 @@ GRUB_MOD_INIT (bfs)
|
|||
{
|
||||
COMPILE_TIME_ASSERT (1 << LOG_EXTENT_SIZE ==
|
||||
sizeof (struct grub_bfs_extent));
|
||||
if (!grub_is_lockdown ())
|
||||
{
|
||||
grub_bfs_fs.mod = mod;
|
||||
grub_fs_register (&grub_bfs_fs);
|
||||
}
|
||||
grub_fs_register (&grub_bfs_fs);
|
||||
}
|
||||
|
||||
#ifdef MODE_AFS
|
||||
|
@ -1120,6 +1115,5 @@ GRUB_MOD_FINI (afs)
|
|||
GRUB_MOD_FINI (bfs)
|
||||
#endif
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_unregister (&grub_bfs_fs);
|
||||
grub_fs_unregister (&grub_bfs_fs);
|
||||
}
|
||||
|
|
|
@ -1276,8 +1276,8 @@ grub_btrfs_mount (grub_device_t dev)
|
|||
}
|
||||
|
||||
data->n_devices_allocated = 16;
|
||||
data->devices_attached = grub_calloc (data->n_devices_allocated,
|
||||
sizeof (data->devices_attached[0]));
|
||||
data->devices_attached = grub_malloc (sizeof (data->devices_attached[0])
|
||||
* data->n_devices_allocated);
|
||||
if (!data->devices_attached)
|
||||
{
|
||||
grub_free (data);
|
||||
|
@ -1538,10 +1538,7 @@ grub_btrfs_extent_read (struct grub_btrfs_data *data,
|
|||
err = lower_bound (data, &key_in, &key_out, tree,
|
||||
&elemaddr, &elemsize, &desc, 0);
|
||||
if (err)
|
||||
{
|
||||
grub_free (desc.data);
|
||||
return -1;
|
||||
}
|
||||
return -1;
|
||||
if (key_out.object_id != ino
|
||||
|| key_out.type != GRUB_BTRFS_ITEM_TYPE_EXTENT_ITEM)
|
||||
{
|
||||
|
@ -1606,8 +1603,6 @@ grub_btrfs_extent_read (struct grub_btrfs_data *data,
|
|||
csize = grub_le_to_cpu64 (key_out.offset) - pos;
|
||||
if (csize > len)
|
||||
csize = len;
|
||||
|
||||
grub_memset (buf, 0, csize);
|
||||
buf += csize;
|
||||
pos += csize;
|
||||
len -= csize;
|
||||
|
@ -1804,7 +1799,6 @@ find_path (struct grub_btrfs_data *data,
|
|||
char *path_alloc = NULL;
|
||||
char *origpath = NULL;
|
||||
unsigned symlinks_max = 32;
|
||||
grub_size_t sz;
|
||||
|
||||
err = get_root (data, key, tree, type);
|
||||
if (err)
|
||||
|
@ -1895,15 +1889,9 @@ find_path (struct grub_btrfs_data *data,
|
|||
struct grub_btrfs_dir_item *cdirel;
|
||||
if (elemsize > allocated)
|
||||
{
|
||||
if (grub_mul (2, elemsize, &allocated) ||
|
||||
grub_add (allocated, 1, &sz))
|
||||
{
|
||||
grub_free (path_alloc);
|
||||
grub_free (origpath);
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, N_("directory item size overflow"));
|
||||
}
|
||||
allocated = 2 * elemsize;
|
||||
grub_free (direl);
|
||||
direl = grub_malloc (sz);
|
||||
direl = grub_malloc (allocated + 1);
|
||||
if (!direl)
|
||||
{
|
||||
grub_free (path_alloc);
|
||||
|
@ -1965,16 +1953,8 @@ find_path (struct grub_btrfs_data *data,
|
|||
grub_free (origpath);
|
||||
return err;
|
||||
}
|
||||
|
||||
if (grub_add (grub_le_to_cpu64 (inode.size), grub_strlen (path), &sz) ||
|
||||
grub_add (sz, 1, &sz))
|
||||
{
|
||||
grub_free (direl);
|
||||
grub_free (path_alloc);
|
||||
grub_free (origpath);
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, N_("buffer size overflow"));
|
||||
}
|
||||
tmp = grub_malloc (sz);
|
||||
tmp = grub_malloc (grub_le_to_cpu64 (inode.size)
|
||||
+ grub_strlen (path) + 1);
|
||||
if (!tmp)
|
||||
{
|
||||
grub_free (direl);
|
||||
|
@ -2096,7 +2076,6 @@ grub_btrfs_dir (grub_device_t device, const char *path,
|
|||
grub_uint64_t tree;
|
||||
grub_uint8_t type;
|
||||
grub_size_t est_size = 0;
|
||||
grub_size_t sz;
|
||||
|
||||
if (!data)
|
||||
return grub_errno;
|
||||
|
@ -2118,7 +2097,6 @@ grub_btrfs_dir (grub_device_t device, const char *path,
|
|||
if (err)
|
||||
{
|
||||
grub_btrfs_unmount (data);
|
||||
grub_free (desc.data);
|
||||
return err;
|
||||
}
|
||||
if (key_out.type != GRUB_BTRFS_ITEM_TYPE_DIR_ITEM
|
||||
|
@ -2139,15 +2117,9 @@ grub_btrfs_dir (grub_device_t device, const char *path,
|
|||
}
|
||||
if (elemsize > allocated)
|
||||
{
|
||||
if (grub_mul (2, elemsize, &allocated) ||
|
||||
grub_add (allocated, 1, &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("directory element size overflow"));
|
||||
r = -grub_errno;
|
||||
break;
|
||||
}
|
||||
allocated = 2 * elemsize;
|
||||
grub_free (direl);
|
||||
direl = grub_malloc (sz);
|
||||
direl = grub_malloc (allocated + 1);
|
||||
if (!direl)
|
||||
{
|
||||
r = -grub_errno;
|
||||
|
@ -2439,7 +2411,6 @@ static struct grub_fs grub_btrfs_fs = {
|
|||
|
||||
GRUB_MOD_INIT (btrfs)
|
||||
{
|
||||
grub_btrfs_fs.mod = mod;
|
||||
grub_fs_register (&grub_btrfs_fs);
|
||||
}
|
||||
|
||||
|
|
|
@ -26,7 +26,6 @@
|
|||
#include <grub/dl.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/cbfs_core.h>
|
||||
#include <grub/lockdown.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -391,17 +390,12 @@ GRUB_MOD_INIT (cbfs)
|
|||
#if (defined (__i386__) || defined (__x86_64__)) && !defined (GRUB_UTIL) && !defined (GRUB_MACHINE_EMU) && !defined (GRUB_MACHINE_XEN)
|
||||
init_cbfsdisk ();
|
||||
#endif
|
||||
if (!grub_is_lockdown ())
|
||||
{
|
||||
grub_cbfs_fs.mod = mod;
|
||||
grub_fs_register (&grub_cbfs_fs);
|
||||
}
|
||||
grub_fs_register (&grub_cbfs_fs);
|
||||
}
|
||||
|
||||
GRUB_MOD_FINI (cbfs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_unregister (&grub_cbfs_fs);
|
||||
grub_fs_unregister (&grub_cbfs_fs);
|
||||
#if (defined (__i386__) || defined (__x86_64__)) && !defined (GRUB_UTIL) && !defined (GRUB_MACHINE_EMU) && !defined (GRUB_MACHINE_XEN)
|
||||
fini_cbfsdisk ();
|
||||
#endif
|
||||
|
|
|
@ -52,7 +52,6 @@ read_number (const grub_uint16_t *arr, grub_size_t size)
|
|||
|
||||
GRUB_MOD_INIT (cpio)
|
||||
{
|
||||
grub_cpio_fs.mod = mod;
|
||||
grub_fs_register (&grub_cpio_fs);
|
||||
}
|
||||
|
||||
|
|
|
@ -52,7 +52,6 @@ read_number (const grub_uint16_t *arr, grub_size_t size)
|
|||
|
||||
GRUB_MOD_INIT (cpio_be)
|
||||
{
|
||||
grub_cpio_fs.mod = mod;
|
||||
grub_fs_register (&grub_cpio_fs);
|
||||
}
|
||||
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
#include <grub/dl.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/archelp.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -49,7 +48,6 @@ grub_cpio_find_file (struct grub_archelp_data *data, char **name,
|
|||
struct head hd;
|
||||
grub_size_t namesize;
|
||||
grub_uint32_t modeval;
|
||||
grub_size_t sz;
|
||||
|
||||
data->hofs = data->next_hofs;
|
||||
|
||||
|
@ -62,21 +60,11 @@ grub_cpio_find_file (struct grub_archelp_data *data, char **name,
|
|||
#endif
|
||||
)
|
||||
return grub_error (GRUB_ERR_BAD_FS, "invalid cpio archive");
|
||||
|
||||
if (grub_cast (read_number (hd.filesize, ARRAY_SIZE (hd.filesize)), &data->size))
|
||||
return grub_error (GRUB_ERR_BAD_FS, N_("data size overflow"));
|
||||
|
||||
data->size = read_number (hd.filesize, ARRAY_SIZE (hd.filesize));
|
||||
if (mtime)
|
||||
{
|
||||
if (grub_cast (read_number (hd.mtime, ARRAY_SIZE (hd.mtime)), mtime))
|
||||
return grub_error (GRUB_ERR_BAD_FS, N_("mtime overflow"));
|
||||
}
|
||||
|
||||
if (grub_cast (read_number (hd.mode, ARRAY_SIZE (hd.mode)), &modeval))
|
||||
return grub_error (GRUB_ERR_BAD_FS, N_("mode overflow"));
|
||||
|
||||
if (grub_cast (read_number (hd.namesize, ARRAY_SIZE (hd.namesize)), &namesize))
|
||||
return grub_error (GRUB_ERR_BAD_FS, N_("namesize overflow"));
|
||||
*mtime = read_number (hd.mtime, ARRAY_SIZE (hd.mtime));
|
||||
modeval = read_number (hd.mode, ARRAY_SIZE (hd.mode));
|
||||
namesize = read_number (hd.namesize, ARRAY_SIZE (hd.namesize));
|
||||
|
||||
/* Don't allow negative numbers. */
|
||||
if (namesize >= 0x80000000)
|
||||
|
@ -88,10 +76,7 @@ grub_cpio_find_file (struct grub_archelp_data *data, char **name,
|
|||
|
||||
*mode = modeval;
|
||||
|
||||
if (grub_add (namesize, 1, &sz))
|
||||
return grub_error (GRUB_ERR_OUT_OF_RANGE, N_("file name size overflow"));
|
||||
|
||||
*name = grub_malloc (sz);
|
||||
*name = grub_malloc (namesize + 1);
|
||||
if (*name == NULL)
|
||||
return grub_errno;
|
||||
|
||||
|
@ -125,17 +110,10 @@ grub_cpio_get_link_target (struct grub_archelp_data *data)
|
|||
{
|
||||
char *ret;
|
||||
grub_err_t err;
|
||||
grub_size_t sz;
|
||||
|
||||
if (data->size == 0)
|
||||
return grub_strdup ("");
|
||||
|
||||
if (grub_add (data->size, 1, &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("target data size overflow"));
|
||||
return NULL;
|
||||
}
|
||||
ret = grub_malloc (sz);
|
||||
ret = grub_malloc (data->size + 1);
|
||||
if (!ret)
|
||||
return NULL;
|
||||
|
||||
|
|
1006
grub-core/fs/erofs.c
1006
grub-core/fs/erofs.c
File diff suppressed because it is too large
Load diff
|
@ -495,11 +495,6 @@ grub_ext2_read_block (grub_fshelp_node_t node, grub_disk_addr_t fileblock)
|
|||
struct grub_ext4_extent *ext;
|
||||
int i;
|
||||
grub_disk_addr_t ret;
|
||||
grub_uint16_t nent;
|
||||
/* Maximum number of extent entries in the inode's inline extent area. */
|
||||
const grub_uint16_t max_inline_ext = sizeof (inode->blocks) / sizeof (*ext) - 1; /* Minus 1 extent header. */
|
||||
/* Maximum number of extent entries in the external extent block. */
|
||||
const grub_uint16_t max_external_ext = EXT2_BLOCK_SIZE (data) / sizeof (*ext) - 1; /* Minus 1 extent header. */
|
||||
|
||||
if (grub_ext4_find_leaf (data, (struct grub_ext4_extent_header *) inode->blocks.dir_blocks,
|
||||
fileblock, &leaf) != GRUB_ERR_NONE)
|
||||
|
@ -513,23 +508,7 @@ grub_ext2_read_block (grub_fshelp_node_t node, grub_disk_addr_t fileblock)
|
|||
return 0;
|
||||
|
||||
ext = (struct grub_ext4_extent *) (leaf + 1);
|
||||
|
||||
nent = grub_le_to_cpu16 (leaf->entries);
|
||||
|
||||
/*
|
||||
* Determine the effective number of extent entries (nent) to process.
|
||||
* If the extent header (leaf) is stored inline in the inode’s block
|
||||
* area, i.e. at inode->blocks.dir_blocks, then only max_inline_ext
|
||||
* entries can fit. Otherwise, if the header was read from an external
|
||||
* extent block use the larger limit, max_external_ext, based on the
|
||||
* full block size.
|
||||
*/
|
||||
if (leaf == (struct grub_ext4_extent_header *) inode->blocks.dir_blocks)
|
||||
nent = grub_min (nent, max_inline_ext);
|
||||
else
|
||||
nent = grub_min (nent, max_external_ext);
|
||||
|
||||
for (i = 0; i < nent; i++)
|
||||
for (i = 0; i < grub_le_to_cpu16 (leaf->entries); i++)
|
||||
{
|
||||
if (fileblock < grub_le_to_cpu32 (ext[i].block))
|
||||
break;
|
||||
|
@ -1144,7 +1123,6 @@ static struct grub_fs grub_ext2_fs =
|
|||
|
||||
GRUB_MOD_INIT(ext2)
|
||||
{
|
||||
grub_ext2_fs.mod = mod;
|
||||
grub_fs_register (&grub_ext2_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
|
|
@ -28,7 +28,6 @@
|
|||
#include <grub/types.h>
|
||||
#include <grub/charset.h>
|
||||
#include <grub/fshelp.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -873,9 +872,6 @@ grub_f2fs_mount (grub_disk_t disk)
|
|||
return data;
|
||||
|
||||
fail:
|
||||
if (grub_errno == GRUB_ERR_NONE)
|
||||
grub_error (GRUB_ERR_BAD_FS, "not a F2FS filesystem");
|
||||
|
||||
grub_free (data);
|
||||
|
||||
return NULL;
|
||||
|
@ -959,7 +955,6 @@ grub_f2fs_read_symlink (grub_fshelp_node_t node)
|
|||
char *symlink;
|
||||
struct grub_fshelp_node *diro = node;
|
||||
grub_uint64_t filesize;
|
||||
grub_size_t sz;
|
||||
|
||||
if (!diro->inode_read)
|
||||
{
|
||||
|
@ -970,12 +965,7 @@ grub_f2fs_read_symlink (grub_fshelp_node_t node)
|
|||
|
||||
filesize = grub_f2fs_file_size(&diro->inode.i);
|
||||
|
||||
if (grub_add (filesize, 1, &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("symlink size overflow"));
|
||||
return 0;
|
||||
}
|
||||
symlink = grub_malloc (sz);
|
||||
symlink = grub_malloc (filesize + 1);
|
||||
if (!symlink)
|
||||
return 0;
|
||||
|
||||
|
@ -1004,7 +994,6 @@ grub_f2fs_check_dentries (struct grub_f2fs_dir_iter_ctx *ctx)
|
|||
enum FILE_TYPE ftype;
|
||||
int name_len;
|
||||
int ret;
|
||||
int sz;
|
||||
|
||||
if (grub_f2fs_test_bit_le (i, ctx->bitmap) == 0)
|
||||
{
|
||||
|
@ -1018,12 +1007,7 @@ grub_f2fs_check_dentries (struct grub_f2fs_dir_iter_ctx *ctx)
|
|||
if (name_len >= F2FS_NAME_LEN)
|
||||
return 0;
|
||||
|
||||
if (grub_add (name_len, 1, &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("directory entry name length overflow"));
|
||||
return 0;
|
||||
}
|
||||
filename = grub_malloc (sz);
|
||||
filename = grub_malloc (name_len + 1);
|
||||
if (!filename)
|
||||
return 0;
|
||||
|
||||
|
@ -1366,7 +1350,6 @@ static struct grub_fs grub_f2fs_fs = {
|
|||
|
||||
GRUB_MOD_INIT (f2fs)
|
||||
{
|
||||
grub_f2fs_fs.mod = mod;
|
||||
grub_fs_register (&grub_f2fs_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
|
|
@ -1312,7 +1312,6 @@ GRUB_MOD_INIT(fat)
|
|||
#endif
|
||||
{
|
||||
COMPILE_TIME_ASSERT (sizeof (struct grub_fat_dir_entry) == 32);
|
||||
grub_fat_fs.mod = mod;
|
||||
grub_fs_register (&grub_fat_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
|
|
@ -226,10 +226,7 @@ find_file (char *currpath,
|
|||
return grub_error (GRUB_ERR_SYMLINK_LOOP,
|
||||
N_("too deep nesting of symlinks"));
|
||||
|
||||
if (read_symlink != NULL)
|
||||
symlink = read_symlink (ctx->currnode->node);
|
||||
else
|
||||
return grub_error (GRUB_ERR_BAD_FS, "read_symlink is NULL");
|
||||
symlink = read_symlink (ctx->currnode->node);
|
||||
|
||||
if (!symlink)
|
||||
return grub_errno;
|
||||
|
|
|
@ -379,7 +379,7 @@ grub_hfs_mount (grub_disk_t disk)
|
|||
volume name. */
|
||||
key.parent_dir = grub_cpu_to_be32_compile_time (1);
|
||||
key.strlen = data->sblock.volname[0];
|
||||
grub_strlcpy ((char *) key.str, (char *) (data->sblock.volname + 1), sizeof (key.str));
|
||||
grub_strcpy ((char *) key.str, (char *) (data->sblock.volname + 1));
|
||||
|
||||
if (grub_hfs_find_node (data, (char *) &key, data->cat_root,
|
||||
0, (char *) &dir, sizeof (dir)) == 0)
|
||||
|
@ -1434,7 +1434,6 @@ static struct grub_fs grub_hfs_fs =
|
|||
|
||||
GRUB_MOD_INIT(hfs)
|
||||
{
|
||||
grub_hfs_fs.mod = mod;
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_register (&grub_hfs_fs);
|
||||
my_mod = mod;
|
||||
|
|
|
@ -405,7 +405,7 @@ grub_hfsplus_mount (grub_disk_t disk)
|
|||
|
||||
fail:
|
||||
|
||||
if (grub_errno == GRUB_ERR_OUT_OF_RANGE || grub_errno == GRUB_ERR_NONE)
|
||||
if (grub_errno == GRUB_ERR_OUT_OF_RANGE)
|
||||
grub_error (GRUB_ERR_BAD_FS, "not a HFS+ filesystem");
|
||||
|
||||
grub_free (data);
|
||||
|
@ -1176,7 +1176,6 @@ static struct grub_fs grub_hfsplus_fs =
|
|||
|
||||
GRUB_MOD_INIT(hfsplus)
|
||||
{
|
||||
grub_hfsplus_fs.mod = mod;
|
||||
grub_fs_register (&grub_hfsplus_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
|
|
@ -244,19 +244,14 @@ hfsplus_open_compressed_real (struct grub_hfsplus_file *node)
|
|||
return 0;
|
||||
}
|
||||
node->compress_index_size = grub_le_to_cpu32 (index_size);
|
||||
node->compress_index = grub_calloc (node->compress_index_size,
|
||||
sizeof (node->compress_index[0]));
|
||||
node->compress_index = grub_malloc (node->compress_index_size
|
||||
* sizeof (node->compress_index[0]));
|
||||
if (!node->compress_index)
|
||||
{
|
||||
node->compressed = 0;
|
||||
grub_free (attr_node);
|
||||
return grub_errno;
|
||||
}
|
||||
|
||||
/*
|
||||
* The node->compress_index_size * sizeof (node->compress_index[0]) is safe here
|
||||
* due to relevant checks done in grub_calloc() above.
|
||||
*/
|
||||
if (grub_hfsplus_read_file (node, 0, 0,
|
||||
0x104 + sizeof (index_size),
|
||||
node->compress_index_size
|
||||
|
|
|
@ -551,9 +551,6 @@ grub_iso9660_mount (grub_disk_t disk)
|
|||
return data;
|
||||
|
||||
fail:
|
||||
if (grub_errno == GRUB_ERR_NONE)
|
||||
grub_error (GRUB_ERR_BAD_FS, "not a ISO9660 filesystem");
|
||||
|
||||
grub_free (data);
|
||||
return 0;
|
||||
}
|
||||
|
@ -628,19 +625,9 @@ susp_iterate_dir (struct grub_iso9660_susp_entry *entry,
|
|||
filename type is stored. */
|
||||
/* FIXME: Fix this slightly improper cast. */
|
||||
if (entry->data[0] & GRUB_ISO9660_RR_DOT)
|
||||
{
|
||||
if (ctx->filename_alloc)
|
||||
grub_free (ctx->filename);
|
||||
ctx->filename_alloc = 0;
|
||||
ctx->filename = (char *) ".";
|
||||
}
|
||||
ctx->filename = (char *) ".";
|
||||
else if (entry->data[0] & GRUB_ISO9660_RR_DOTDOT)
|
||||
{
|
||||
if (ctx->filename_alloc)
|
||||
grub_free (ctx->filename);
|
||||
ctx->filename_alloc = 0;
|
||||
ctx->filename = (char *) "..";
|
||||
}
|
||||
ctx->filename = (char *) "..";
|
||||
else if (entry->len >= 5)
|
||||
{
|
||||
grub_size_t off = 0, csize = 1;
|
||||
|
@ -1260,7 +1247,6 @@ static struct grub_fs grub_iso9660_fs =
|
|||
|
||||
GRUB_MOD_INIT(iso9660)
|
||||
{
|
||||
grub_iso9660_fs.mod = mod;
|
||||
grub_fs_register (&grub_iso9660_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
|
|
@ -26,7 +26,6 @@
|
|||
#include <grub/types.h>
|
||||
#include <grub/charset.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/lockdown.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -42,13 +41,6 @@ GRUB_MOD_LICENSE ("GPLv3+");
|
|||
|
||||
#define GRUB_JFS_TREE_LEAF 2
|
||||
|
||||
/*
|
||||
* Define max entries stored in-line in an inode.
|
||||
* https://jfs.sourceforge.net/project/pub/jfslayout.pdf
|
||||
*/
|
||||
#define GRUB_JFS_INODE_INLINE_ENTRIES 8
|
||||
#define GRUB_JFS_DIR_MAX_SLOTS 128
|
||||
|
||||
struct grub_jfs_sblock
|
||||
{
|
||||
/* The magic for JFS. It should contain the string "JFS1". */
|
||||
|
@ -211,9 +203,9 @@ struct grub_jfs_inode
|
|||
grub_uint8_t freecnt;
|
||||
grub_uint8_t freelist;
|
||||
grub_uint32_t idotdot;
|
||||
grub_uint8_t sorted[GRUB_JFS_INODE_INLINE_ENTRIES];
|
||||
grub_uint8_t sorted[8];
|
||||
} header;
|
||||
struct grub_jfs_leaf_dirent dirents[GRUB_JFS_INODE_INLINE_ENTRIES];
|
||||
struct grub_jfs_leaf_dirent dirents[8];
|
||||
} GRUB_PACKED dir;
|
||||
/* Fast symlink. */
|
||||
struct
|
||||
|
@ -266,21 +258,7 @@ static grub_dl_t my_mod;
|
|||
|
||||
static grub_err_t grub_jfs_lookup_symlink (struct grub_jfs_data *data, grub_uint32_t ino);
|
||||
|
||||
/*
|
||||
* An extent's offset, physical and logical, is represented as a 40-bit value.
|
||||
* This 40-bit value is split into two parts:
|
||||
* - offset1: the most signficant 8 bits of the offset,
|
||||
* - offset2: the least significant 32 bits of the offset.
|
||||
*
|
||||
* This function calculates and returns the 64-bit offset of an extent.
|
||||
*/
|
||||
static grub_uint64_t
|
||||
get_ext_offset (grub_uint8_t offset1, grub_uint32_t offset2)
|
||||
{
|
||||
return (((grub_uint64_t) offset1 << 32) | grub_le_to_cpu32 (offset2));
|
||||
}
|
||||
|
||||
static grub_uint64_t
|
||||
static grub_int64_t
|
||||
getblk (struct grub_jfs_treehead *treehead,
|
||||
struct grub_jfs_tree_extent *extents,
|
||||
int max_extents,
|
||||
|
@ -289,33 +267,28 @@ getblk (struct grub_jfs_treehead *treehead,
|
|||
{
|
||||
int found = -1;
|
||||
int i;
|
||||
grub_uint64_t ext_offset, ext_blk;
|
||||
|
||||
grub_errno = GRUB_ERR_NONE;
|
||||
|
||||
for (i = 0; i < grub_le_to_cpu16 (treehead->count) - 2 &&
|
||||
i < max_extents; i++)
|
||||
{
|
||||
ext_offset = get_ext_offset (extents[i].offset1, extents[i].offset2);
|
||||
ext_blk = get_ext_offset (extents[i].extent.blk1, extents[i].extent.blk2);
|
||||
|
||||
if (treehead->flags & GRUB_JFS_TREE_LEAF)
|
||||
{
|
||||
/* Read the leafnode. */
|
||||
if (ext_offset <= blk
|
||||
if (grub_le_to_cpu32 (extents[i].offset2) <= blk
|
||||
&& ((grub_le_to_cpu16 (extents[i].extent.length))
|
||||
+ (extents[i].extent.length2 << 16)
|
||||
+ ext_offset) > blk)
|
||||
return (blk - ext_offset + ext_blk);
|
||||
+ grub_le_to_cpu32 (extents[i].offset2)) > blk)
|
||||
return (blk - grub_le_to_cpu32 (extents[i].offset2)
|
||||
+ grub_le_to_cpu32 (extents[i].extent.blk2));
|
||||
}
|
||||
else
|
||||
if (blk >= ext_offset)
|
||||
if (blk >= grub_le_to_cpu32 (extents[i].offset2))
|
||||
found = i;
|
||||
}
|
||||
|
||||
if (found != -1)
|
||||
{
|
||||
grub_uint64_t ret = 0;
|
||||
grub_int64_t ret = -1;
|
||||
struct
|
||||
{
|
||||
struct grub_jfs_treehead treehead;
|
||||
|
@ -324,12 +297,13 @@ getblk (struct grub_jfs_treehead *treehead,
|
|||
|
||||
tree = grub_zalloc (sizeof (*tree));
|
||||
if (!tree)
|
||||
return 0;
|
||||
return -1;
|
||||
|
||||
if (!grub_disk_read (data->disk,
|
||||
(grub_disk_addr_t) ext_blk
|
||||
<< (grub_le_to_cpu16 (data->sblock.log2_blksz) - GRUB_DISK_SECTOR_BITS),
|
||||
0, sizeof (*tree), (char *) tree))
|
||||
((grub_disk_addr_t) grub_le_to_cpu32 (extents[found].extent.blk2))
|
||||
<< (grub_le_to_cpu16 (data->sblock.log2_blksz)
|
||||
- GRUB_DISK_SECTOR_BITS), 0,
|
||||
sizeof (*tree), (char *) tree))
|
||||
{
|
||||
if (grub_memcmp (&tree->treehead, treehead, sizeof (struct grub_jfs_treehead)) ||
|
||||
grub_memcmp (&tree->extents, extents, 254 * sizeof (struct grub_jfs_tree_extent)))
|
||||
|
@ -337,20 +311,19 @@ getblk (struct grub_jfs_treehead *treehead,
|
|||
else
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "jfs: infinite recursion detected");
|
||||
ret = 0;
|
||||
ret = -1;
|
||||
}
|
||||
}
|
||||
grub_free (tree);
|
||||
return ret;
|
||||
}
|
||||
|
||||
grub_error (GRUB_ERR_READ_ERROR, "jfs: block %" PRIuGRUB_UINT64_T " not found", blk);
|
||||
return 0;
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Get the block number for the block BLK in the node INODE in the
|
||||
mounted filesystem DATA. */
|
||||
static grub_uint64_t
|
||||
static grub_int64_t
|
||||
grub_jfs_blkno (struct grub_jfs_data *data, struct grub_jfs_inode *inode,
|
||||
grub_uint64_t blk)
|
||||
{
|
||||
|
@ -381,7 +354,7 @@ grub_jfs_read_inode (struct grub_jfs_data *data, grub_uint32_t ino,
|
|||
sizeof (iag_inodes), &iag_inodes))
|
||||
return grub_errno;
|
||||
|
||||
inoblk = get_ext_offset (iag_inodes[inoext].blk1, iag_inodes[inoext].blk2);
|
||||
inoblk = grub_le_to_cpu32 (iag_inodes[inoext].blk2);
|
||||
inoblk <<= (grub_le_to_cpu16 (data->sblock.log2_blksz)
|
||||
- GRUB_DISK_SECTOR_BITS);
|
||||
inoblk += inonum;
|
||||
|
@ -480,13 +453,6 @@ grub_jfs_opendir (struct grub_jfs_data *data, struct grub_jfs_inode *inode)
|
|||
/* Check if the entire tree is contained within the inode. */
|
||||
if (inode->file.tree.flags & GRUB_JFS_TREE_LEAF)
|
||||
{
|
||||
if (inode->dir.header.count > GRUB_JFS_INODE_INLINE_ENTRIES)
|
||||
{
|
||||
grub_free (diro);
|
||||
grub_error (GRUB_ERR_BAD_FS, N_("invalid JFS inode"));
|
||||
return 0;
|
||||
}
|
||||
|
||||
diro->leaf = inode->dir.dirents;
|
||||
diro->next_leaf = (struct grub_jfs_leaf_next_dirent *) de;
|
||||
diro->sorted = inode->dir.header.sorted;
|
||||
|
@ -502,16 +468,7 @@ grub_jfs_opendir (struct grub_jfs_data *data, struct grub_jfs_inode *inode)
|
|||
return 0;
|
||||
}
|
||||
|
||||
if (inode->dir.header.sorted[0] >= GRUB_JFS_DIR_MAX_SLOTS)
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, N_("invalid directory slot index"));
|
||||
grub_free (diro->dirpage);
|
||||
grub_free (diro);
|
||||
return 0;
|
||||
}
|
||||
|
||||
blk = get_ext_offset (de[inode->dir.header.sorted[0]].ex.blk1,
|
||||
de[inode->dir.header.sorted[0]].ex.blk2);
|
||||
blk = grub_le_to_cpu32 (de[inode->dir.header.sorted[0]].ex.blk2);
|
||||
blk <<= (grub_le_to_cpu16 (data->sblock.log2_blksz) - GRUB_DISK_SECTOR_BITS);
|
||||
|
||||
/* Read in the nodes until we are on the leaf node level. */
|
||||
|
@ -529,7 +486,7 @@ grub_jfs_opendir (struct grub_jfs_data *data, struct grub_jfs_inode *inode)
|
|||
|
||||
de = (struct grub_jfs_internal_dirent *) diro->dirpage->dirent;
|
||||
index = diro->dirpage->sorted[diro->dirpage->header.sindex * 32];
|
||||
blk = (get_ext_offset (de[index].ex.blk1, de[index].ex.blk2)
|
||||
blk = (grub_le_to_cpu32 (de[index].ex.blk2)
|
||||
<< (grub_le_to_cpu16 (data->sblock.log2_blksz)
|
||||
- GRUB_DISK_SECTOR_BITS));
|
||||
} while (!(diro->dirpage->header.flags & GRUB_JFS_TREE_LEAF));
|
||||
|
@ -759,6 +716,7 @@ grub_jfs_find_file (struct grub_jfs_data *data, const char *path,
|
|||
grub_uint32_t dirino = grub_le_to_cpu32 (data->currinode.inode);
|
||||
|
||||
grub_jfs_closedir (diro);
|
||||
diro = 0;
|
||||
|
||||
if (grub_jfs_read_inode (data, ino, &data->currinode))
|
||||
break;
|
||||
|
@ -1005,16 +963,11 @@ static struct grub_fs grub_jfs_fs =
|
|||
|
||||
GRUB_MOD_INIT(jfs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
{
|
||||
grub_jfs_fs.mod = mod;
|
||||
grub_fs_register (&grub_jfs_fs);
|
||||
}
|
||||
grub_fs_register (&grub_jfs_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
||||
GRUB_MOD_FINI(jfs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_unregister (&grub_jfs_fs);
|
||||
grub_fs_unregister (&grub_jfs_fs);
|
||||
}
|
||||
|
|
|
@ -25,7 +25,6 @@
|
|||
#include <grub/dl.h>
|
||||
#include <grub/types.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/lockdown.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -735,11 +734,7 @@ GRUB_MOD_INIT(minix)
|
|||
#endif
|
||||
#endif
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
{
|
||||
grub_minix_fs.mod = mod;
|
||||
grub_fs_register (&grub_minix_fs);
|
||||
}
|
||||
grub_fs_register (&grub_minix_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
||||
|
@ -761,6 +756,5 @@ GRUB_MOD_FINI(minix)
|
|||
#endif
|
||||
#endif
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_unregister (&grub_minix_fs);
|
||||
grub_fs_unregister (&grub_minix_fs);
|
||||
}
|
||||
|
|
|
@ -64,7 +64,6 @@ read_number (const char *str, grub_size_t size)
|
|||
|
||||
GRUB_MOD_INIT (newc)
|
||||
{
|
||||
grub_cpio_fs.mod = mod;
|
||||
grub_fs_register (&grub_cpio_fs);
|
||||
}
|
||||
|
||||
|
|
|
@ -34,7 +34,6 @@
|
|||
#include <grub/dl.h>
|
||||
#include <grub/types.h>
|
||||
#include <grub/fshelp.h>
|
||||
#include <grub/lockdown.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -1232,16 +1231,11 @@ GRUB_MOD_INIT (nilfs2)
|
|||
grub_nilfs2_dat_entry));
|
||||
COMPILE_TIME_ASSERT (1 << LOG_INODE_SIZE
|
||||
== sizeof (struct grub_nilfs2_inode));
|
||||
if (!grub_is_lockdown ())
|
||||
{
|
||||
grub_nilfs2_fs.mod = mod;
|
||||
grub_fs_register (&grub_nilfs2_fs);
|
||||
}
|
||||
grub_fs_register (&grub_nilfs2_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
||||
GRUB_MOD_FINI (nilfs2)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_unregister (&grub_nilfs2_fs);
|
||||
grub_fs_unregister (&grub_nilfs2_fs);
|
||||
}
|
||||
|
|
|
@ -27,7 +27,6 @@
|
|||
#include <grub/fshelp.h>
|
||||
#include <grub/ntfs.h>
|
||||
#include <grub/charset.h>
|
||||
#include <grub/lockdown.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -53,193 +52,6 @@ u64at (void *ptr, grub_size_t ofs)
|
|||
return grub_le_to_cpu64 (grub_get_unaligned64 ((char *) ptr + ofs));
|
||||
}
|
||||
|
||||
static grub_uint16_t
|
||||
first_attr_off (void *mft_buf_ptr)
|
||||
{
|
||||
return u16at (mft_buf_ptr, 0x14);
|
||||
}
|
||||
|
||||
static grub_uint16_t
|
||||
res_attr_data_off (void *res_attr_ptr)
|
||||
{
|
||||
return u16at (res_attr_ptr, 0x14);
|
||||
}
|
||||
|
||||
static grub_uint32_t
|
||||
res_attr_data_len (void *res_attr_ptr)
|
||||
{
|
||||
return u32at (res_attr_ptr, 0x10);
|
||||
}
|
||||
|
||||
/*
|
||||
* Check if the attribute is valid and doesn't exceed the allocated region.
|
||||
* This accounts for resident and non-resident data.
|
||||
*
|
||||
* This is based off the documentation from the linux-ntfs project:
|
||||
* https://flatcap.github.io/linux-ntfs/ntfs/concepts/attribute_header.html
|
||||
*/
|
||||
static bool
|
||||
validate_attribute (grub_uint8_t *attr, void *end)
|
||||
{
|
||||
grub_size_t attr_size = 0;
|
||||
grub_size_t min_size = 0;
|
||||
grub_size_t run_size = 0;
|
||||
grub_size_t spare = (grub_uint8_t *) end - attr;
|
||||
/*
|
||||
* Just used as a temporary variable to try and deal with cases where someone
|
||||
* tries to overlap fields.
|
||||
*/
|
||||
grub_size_t curr = 0;
|
||||
|
||||
/* Need verify we can entirely read the attributes header. */
|
||||
if (attr + GRUB_NTFS_ATTRIBUTE_HEADER_SIZE >= (grub_uint8_t *) end)
|
||||
goto fail;
|
||||
|
||||
/*
|
||||
* So, the rest of this code uses a 16bit int for the attribute length but
|
||||
* from reading the all the documentation I could find it says this field is
|
||||
* actually 32bit. But let's be consistent with the rest of the code.
|
||||
*
|
||||
* https://elixir.bootlin.com/linux/v6.10.7/source/fs/ntfs3/ntfs.h#L370
|
||||
*/
|
||||
attr_size = u16at (attr, GRUB_NTFS_ATTRIBUTE_LENGTH);
|
||||
|
||||
if (attr_size > spare)
|
||||
goto fail;
|
||||
|
||||
/* Not an error case, just reached the end of the attributes. */
|
||||
if (attr_size == 0)
|
||||
return false;
|
||||
|
||||
/*
|
||||
* Extra validation by trying to calculate a minimum possible size for this
|
||||
* attribute. +8 from the size of the resident data struct which is the
|
||||
* minimum that can be added.
|
||||
*/
|
||||
min_size = GRUB_NTFS_ATTRIBUTE_HEADER_SIZE + 8;
|
||||
|
||||
if (min_size > attr_size)
|
||||
goto fail;
|
||||
|
||||
/* Is the data is resident (0) or not (1). */
|
||||
if (attr[GRUB_NTFS_ATTRIBUTE_RESIDENT] == 0)
|
||||
{
|
||||
/* Read the offset and size of the attribute. */
|
||||
curr = u16at (attr, GRUB_NTFS_ATTRIBUTE_RES_OFFSET);
|
||||
curr += u32at (attr, GRUB_NTFS_ATTRIBUTE_RES_LENGTH);
|
||||
if (curr > min_size)
|
||||
min_size = curr;
|
||||
}
|
||||
else
|
||||
{
|
||||
/*
|
||||
* If the data is non-resident, the minimum size is 64 which is where
|
||||
* the data runs start. We already have a minimum size of 24. So, just
|
||||
* adding 40 to get to the real value.
|
||||
*/
|
||||
min_size += 40;
|
||||
if (min_size > attr_size)
|
||||
goto fail;
|
||||
/* If the compression unit size is > 0, +8 bytes*/
|
||||
if (u16at (attr, GRUB_NTFS_ATTRIBUTE_COMPRESSION_UNIT_SIZE) > 0)
|
||||
min_size += 8;
|
||||
|
||||
/*
|
||||
* Need to consider the data runs now. Each member of the run has byte
|
||||
* that describes the size of the data length and offset. Each being
|
||||
* 4 bits in the byte.
|
||||
*/
|
||||
curr = u16at (attr, GRUB_NTFS_ATTRIBUTE_DATA_RUNS);
|
||||
|
||||
if (curr + 1 > min_size)
|
||||
min_size = curr + 1;
|
||||
|
||||
if (min_size > attr_size)
|
||||
goto fail;
|
||||
|
||||
/*
|
||||
* Each attribute can store multiple data runs which are stored
|
||||
* continuously in the attribute. They exist as one header byte
|
||||
* with up to 14 bytes following it depending on the lengths.
|
||||
* We stop when we hit a header that is just a NUL byte.
|
||||
*
|
||||
* https://flatcap.github.io/linux-ntfs/ntfs/concepts/data_runs.html
|
||||
*/
|
||||
while (attr[curr] != 0)
|
||||
{
|
||||
/*
|
||||
* We stop when we hit a header that is just a NUL byte. The data
|
||||
* run header is stored as a single byte where the top 4 bits refer
|
||||
* to the number of bytes used to store the total length of the
|
||||
* data run, and the number of bytes used to store the offset.
|
||||
* These directly follow the header byte, so we use them to update
|
||||
* the minimum size. Increment by one more than run size to move on
|
||||
* to the next run size header byte. An example is a run size field
|
||||
* value of 0x32, 3 + 2 = 5 bytes follow the run size. Increment
|
||||
* by 5 to get to the end of this data run then one more to get to
|
||||
* the start of the next run size byte.
|
||||
*/
|
||||
run_size = (attr[curr] & 0x7) + ((attr[curr] >> 4) & 0x7);
|
||||
curr += (run_size + 1);
|
||||
min_size += (run_size + 1);
|
||||
if (min_size > attr_size)
|
||||
goto fail;
|
||||
}
|
||||
}
|
||||
|
||||
/* Name offset, doing this after data residence checks. */
|
||||
if (u16at (attr, GRUB_NTFS_ATTRIBUTE_NAME_OFFSET) != 0)
|
||||
{
|
||||
curr = u16at (attr, GRUB_NTFS_ATTRIBUTE_NAME_OFFSET);
|
||||
/*
|
||||
* Multiple the name length by 2 as its UTF-16. Can be zero if this in an
|
||||
* unamed attribute.
|
||||
*/
|
||||
curr += attr[GRUB_NTFS_ATTRIBUTE_NAME_LENGTH] * 2;
|
||||
if (curr > min_size)
|
||||
min_size = curr;
|
||||
}
|
||||
|
||||
/* Padded to 8 bytes. */
|
||||
if (min_size % 8 != 0)
|
||||
min_size += 8 - (min_size % 8);
|
||||
|
||||
/*
|
||||
* At this point min_size should be exactly attr_size but being flexible
|
||||
* here to avoid any issues.
|
||||
*/
|
||||
if (min_size > attr_size)
|
||||
goto fail;
|
||||
|
||||
return true;
|
||||
|
||||
fail:
|
||||
grub_dprintf ("ntfs", "spare=%" PRIuGRUB_SIZE " min_size=%" PRIuGRUB_SIZE " attr_size=%" PRIuGRUB_SIZE "\n",
|
||||
spare, min_size, attr_size);
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Return the next attribute if it exists, otherwise return NULL. */
|
||||
static grub_uint8_t *
|
||||
next_attribute (grub_uint8_t *curr_attribute, void *end, bool validate)
|
||||
{
|
||||
grub_uint8_t *next = curr_attribute;
|
||||
|
||||
/*
|
||||
* Need to verify we aren't exceeding the end of the buffer by reading the
|
||||
* header for the current attribute
|
||||
*/
|
||||
if (curr_attribute + GRUB_NTFS_ATTRIBUTE_HEADER_SIZE >= (grub_uint8_t *) end)
|
||||
return NULL;
|
||||
|
||||
next += u16at (curr_attribute, 4);
|
||||
if (validate && validate_attribute (next, end) == false)
|
||||
return NULL;
|
||||
|
||||
return next;
|
||||
}
|
||||
|
||||
|
||||
grub_ntfscomp_func_t grub_ntfscomp_func;
|
||||
|
||||
static grub_err_t
|
||||
|
@ -248,7 +60,6 @@ fixup (grub_uint8_t *buf, grub_size_t len, const grub_uint8_t *magic)
|
|||
grub_uint16_t ss;
|
||||
grub_uint8_t *pu;
|
||||
grub_uint16_t us;
|
||||
grub_uint16_t pu_offset;
|
||||
|
||||
COMPILE_TIME_ASSERT ((1 << GRUB_NTFS_BLK_SHR) == GRUB_DISK_SECTOR_SIZE);
|
||||
|
||||
|
@ -258,10 +69,7 @@ fixup (grub_uint8_t *buf, grub_size_t len, const grub_uint8_t *magic)
|
|||
ss = u16at (buf, 6) - 1;
|
||||
if (ss != len)
|
||||
return grub_error (GRUB_ERR_BAD_FS, "size not match");
|
||||
pu_offset = u16at (buf, 4);
|
||||
if (pu_offset >= (len * GRUB_DISK_SECTOR_SIZE - (2 * ss)))
|
||||
return grub_error (GRUB_ERR_BAD_FS, "pu offset size incorrect");
|
||||
pu = buf + pu_offset;
|
||||
pu = buf + u16at (buf, 4);
|
||||
us = u16at (pu, 0);
|
||||
buf -= 2;
|
||||
while (ss > 0)
|
||||
|
@ -293,20 +101,13 @@ static grub_err_t read_data (struct grub_ntfs_attr *at, grub_uint8_t *pa,
|
|||
grub_disk_read_hook_t read_hook,
|
||||
void *read_hook_data);
|
||||
|
||||
static grub_err_t
|
||||
static void
|
||||
init_attr (struct grub_ntfs_attr *at, struct grub_ntfs_file *mft)
|
||||
{
|
||||
at->mft = mft;
|
||||
at->flags = (mft == &mft->data->mmft) ? GRUB_NTFS_AF_MMFT : 0;
|
||||
at->attr_nxt = mft->buf + first_attr_off (mft->buf);
|
||||
at->end = mft->buf + (mft->data->mft_size << GRUB_NTFS_BLK_SHR);
|
||||
|
||||
if (at->attr_nxt > at->end)
|
||||
return grub_error (GRUB_ERR_BAD_FS, "attributes start outside the MFT");
|
||||
|
||||
at->attr_nxt = mft->buf + u16at (mft->buf, 0x14);
|
||||
at->attr_end = at->emft_buf = at->edat_buf = at->sbuf = NULL;
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -320,26 +121,16 @@ free_attr (struct grub_ntfs_attr *at)
|
|||
static grub_uint8_t *
|
||||
find_attr (struct grub_ntfs_attr *at, grub_uint8_t attr)
|
||||
{
|
||||
grub_uint8_t *mft_end;
|
||||
grub_uint16_t nsize;
|
||||
grub_uint16_t nxt_offset;
|
||||
grub_uint32_t edat_offset;
|
||||
|
||||
/* GRUB_NTFS_AF_ALST indicates the attribute list type */
|
||||
if (at->flags & GRUB_NTFS_AF_ALST)
|
||||
{
|
||||
retry:
|
||||
while (at->attr_nxt)
|
||||
while (at->attr_nxt < at->attr_end)
|
||||
{
|
||||
at->attr_cur = at->attr_nxt;
|
||||
/*
|
||||
* Go to the next attribute in the list but do not validate
|
||||
* because this is the attribute list type.
|
||||
*/
|
||||
at->attr_nxt = next_attribute (at->attr_cur, at->attr_end, false);
|
||||
at->attr_nxt += u16at (at->attr_cur, 4);
|
||||
if ((*at->attr_cur == attr) || (attr == 0))
|
||||
{
|
||||
grub_uint8_t *new_pos, *end;
|
||||
grub_uint8_t *new_pos;
|
||||
|
||||
if (at->flags & GRUB_NTFS_AF_MMFT)
|
||||
{
|
||||
|
@ -363,41 +154,15 @@ find_attr (struct grub_ntfs_attr *at, grub_uint8_t attr)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
/*
|
||||
* Only time emft_bufs is defined is in this function, with this
|
||||
* size.
|
||||
*/
|
||||
grub_size_t emft_buf_size =
|
||||
at->mft->data->mft_size << GRUB_NTFS_BLK_SHR;
|
||||
|
||||
/*
|
||||
* Needs to be enough space for the successful case to even
|
||||
* bother.
|
||||
*/
|
||||
if (first_attr_off (at->emft_buf) >= (emft_buf_size - 0x18 - 2))
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS,
|
||||
"can\'t find 0x%X in attribute list",
|
||||
(unsigned char) *at->attr_cur);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
new_pos = &at->emft_buf[first_attr_off (at->emft_buf)];
|
||||
end = &at->emft_buf[emft_buf_size];
|
||||
at->end = end;
|
||||
|
||||
while (new_pos && *new_pos != 0xFF)
|
||||
new_pos = &at->emft_buf[u16at (at->emft_buf, 0x14)];
|
||||
while (*new_pos != 0xFF)
|
||||
{
|
||||
if ((*new_pos == *at->attr_cur)
|
||||
&& (u16at (new_pos, 0xE) == u16at (at->attr_cur, 0x18)))
|
||||
{
|
||||
return new_pos;
|
||||
}
|
||||
/*
|
||||
* Go to the next attribute in the list but do not validate
|
||||
* because this is the attribute list type.
|
||||
*/
|
||||
new_pos = next_attribute (new_pos, end, false);
|
||||
new_pos += u16at (new_pos, 4);
|
||||
}
|
||||
grub_error (GRUB_ERR_BAD_FS,
|
||||
"can\'t find 0x%X in attribute list",
|
||||
|
@ -408,33 +173,18 @@ find_attr (struct grub_ntfs_attr *at, grub_uint8_t attr)
|
|||
return NULL;
|
||||
}
|
||||
at->attr_cur = at->attr_nxt;
|
||||
mft_end = at->mft->buf + (at->mft->data->mft_size << GRUB_NTFS_BLK_SHR);
|
||||
while (at->attr_cur >= at->mft->buf && at->attr_cur < (mft_end - 4)
|
||||
&& *at->attr_cur != 0xFF)
|
||||
while (*at->attr_cur != 0xFF)
|
||||
{
|
||||
/*
|
||||
* We can't use validate_attribute here because this logic
|
||||
* seems to be used for both parsing through attributes
|
||||
* and attribute lists.
|
||||
*/
|
||||
nsize = u16at (at->attr_cur, 4);
|
||||
if (at->attr_cur + grub_max (GRUB_NTFS_ATTRIBUTE_HEADER_SIZE, nsize) >= at->end)
|
||||
{
|
||||
at->attr_nxt = at->attr_cur;
|
||||
break;
|
||||
}
|
||||
else
|
||||
at->attr_nxt = at->attr_cur + nsize;
|
||||
|
||||
at->attr_nxt += u16at (at->attr_cur, 4);
|
||||
if (*at->attr_cur == GRUB_NTFS_AT_ATTRIBUTE_LIST)
|
||||
at->attr_end = at->attr_cur;
|
||||
if ((*at->attr_cur == attr) || (attr == 0) || (nsize == 0))
|
||||
if ((*at->attr_cur == attr) || (attr == 0))
|
||||
return at->attr_cur;
|
||||
at->attr_cur = at->attr_nxt;
|
||||
}
|
||||
if (at->attr_end)
|
||||
{
|
||||
grub_uint8_t *pa, *pa_end;
|
||||
grub_uint8_t *pa;
|
||||
|
||||
at->emft_buf = grub_malloc (at->mft->data->mft_size << GRUB_NTFS_BLK_SHR);
|
||||
if (at->emft_buf == NULL)
|
||||
|
@ -458,54 +208,21 @@ find_attr (struct grub_ntfs_attr *at, grub_uint8_t attr)
|
|||
return NULL;
|
||||
}
|
||||
at->attr_nxt = at->edat_buf;
|
||||
edat_offset = u32at (pa, 0x30);
|
||||
if (edat_offset >= n)
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "edat offset is out of bounds");
|
||||
return NULL;
|
||||
}
|
||||
at->attr_end = at->edat_buf + edat_offset;
|
||||
pa_end = at->edat_buf + n;
|
||||
at->attr_end = at->edat_buf + u32at (pa, 0x30);
|
||||
}
|
||||
else
|
||||
{
|
||||
at->attr_nxt = at->attr_end + res_attr_data_off (pa);
|
||||
edat_offset = u32at (pa, 4);
|
||||
if ((at->attr_end + edat_offset) >= (at->end))
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "edat offset is out of bounds");
|
||||
return NULL;
|
||||
}
|
||||
at->attr_end = at->attr_end + edat_offset;
|
||||
pa_end = at->mft->buf + (at->mft->data->mft_size << GRUB_NTFS_BLK_SHR);
|
||||
at->attr_nxt = at->attr_end + u16at (pa, 0x14);
|
||||
at->attr_end = at->attr_end + u32at (pa, 4);
|
||||
}
|
||||
at->flags |= GRUB_NTFS_AF_ALST;
|
||||
|
||||
/* From this point on pa_end is the end of the buffer */
|
||||
at->end = pa_end;
|
||||
|
||||
if (at->attr_end >= pa_end || at->attr_nxt >= pa_end)
|
||||
return NULL;
|
||||
|
||||
while (at->attr_nxt)
|
||||
while (at->attr_nxt < at->attr_end)
|
||||
{
|
||||
if ((*at->attr_nxt == attr) || (attr == 0))
|
||||
break;
|
||||
|
||||
nxt_offset = u16at (at->attr_nxt, 4);
|
||||
at->attr_nxt += nxt_offset;
|
||||
|
||||
/*
|
||||
* Stop and set attr_nxt to NULL when either the next offset is zero,
|
||||
* or when the pointer is within four bytes of the end of the buffer
|
||||
* since we could attempt to access attr_nxt + 4 bytes offset above to
|
||||
* get the next 16-bit 'nxt_offset' value.
|
||||
*/
|
||||
if (nxt_offset == 0 || at->attr_nxt >= (pa_end - 4))
|
||||
at->attr_nxt = NULL;
|
||||
at->attr_nxt += u16at (at->attr_nxt, 4);
|
||||
}
|
||||
|
||||
if ((at->attr_nxt + GRUB_NTFS_ATTRIBUTE_HEADER_SIZE) >= at->attr_end || at->attr_nxt == NULL)
|
||||
if (at->attr_nxt >= at->attr_end)
|
||||
return NULL;
|
||||
|
||||
if ((at->flags & GRUB_NTFS_AF_MMFT) && (attr == GRUB_NTFS_AT_DATA))
|
||||
|
@ -513,42 +230,22 @@ find_attr (struct grub_ntfs_attr *at, grub_uint8_t attr)
|
|||
at->flags |= GRUB_NTFS_AF_GPOS;
|
||||
at->attr_cur = at->attr_nxt;
|
||||
pa = at->attr_cur;
|
||||
|
||||
if ((pa >= pa_end) || (pa_end - pa < 0x18))
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "can\'t parse attribute list");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
grub_set_unaligned32 ((char *) pa + 0x10,
|
||||
grub_cpu_to_le32 (at->mft->data->mft_start));
|
||||
grub_set_unaligned32 ((char *) pa + 0x14,
|
||||
grub_cpu_to_le32 (at->mft->data->mft_start
|
||||
+ 1));
|
||||
pa = at->attr_nxt + u16at (pa, 4);
|
||||
|
||||
if (pa >= pa_end)
|
||||
pa = NULL;
|
||||
|
||||
while (pa)
|
||||
while (pa < at->attr_end)
|
||||
{
|
||||
if (*pa != attr)
|
||||
break;
|
||||
|
||||
if ((pa >= pa_end) || (pa_end - pa < 0x18))
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "can\'t parse attribute list");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (read_attr
|
||||
(at, pa + 0x10,
|
||||
u32at (pa, 0x10) * (at->mft->data->mft_size << GRUB_NTFS_BLK_SHR),
|
||||
at->mft->data->mft_size << GRUB_NTFS_BLK_SHR, 0, 0, 0))
|
||||
return NULL;
|
||||
pa += u16at (pa, 4);
|
||||
if (pa >= pa_end)
|
||||
pa = NULL;
|
||||
}
|
||||
at->attr_nxt = at->attr_cur;
|
||||
at->flags &= ~GRUB_NTFS_AF_GPOS;
|
||||
|
@ -563,31 +260,24 @@ locate_attr (struct grub_ntfs_attr *at, struct grub_ntfs_file *mft,
|
|||
grub_uint8_t attr)
|
||||
{
|
||||
grub_uint8_t *pa;
|
||||
grub_uint8_t *last_pa;
|
||||
|
||||
if (init_attr (at, mft) != GRUB_ERR_NONE)
|
||||
return NULL;
|
||||
|
||||
init_attr (at, mft);
|
||||
pa = find_attr (at, attr);
|
||||
if (pa == NULL)
|
||||
return NULL;
|
||||
if ((at->flags & GRUB_NTFS_AF_ALST) == 0)
|
||||
{
|
||||
/* Used to make sure we're not stuck in a loop. */
|
||||
last_pa = NULL;
|
||||
while (1)
|
||||
{
|
||||
pa = find_attr (at, attr);
|
||||
if (pa == NULL || pa == last_pa)
|
||||
if (pa == NULL)
|
||||
break;
|
||||
if (at->flags & GRUB_NTFS_AF_ALST)
|
||||
return pa;
|
||||
last_pa = pa;
|
||||
}
|
||||
grub_errno = GRUB_ERR_NONE;
|
||||
free_attr (at);
|
||||
if (init_attr (at, mft) != GRUB_ERR_NONE)
|
||||
return NULL;
|
||||
init_attr (at, mft);
|
||||
pa = find_attr (at, attr);
|
||||
}
|
||||
return pa;
|
||||
|
@ -639,7 +329,7 @@ retry:
|
|||
goto retry;
|
||||
}
|
||||
}
|
||||
return grub_error (GRUB_ERR_BAD_FS, "run list overflow");
|
||||
return grub_error (GRUB_ERR_BAD_FS, "run list overflown");
|
||||
}
|
||||
ctx->curr_vcn = ctx->next_vcn;
|
||||
ctx->next_vcn += read_run_data (run, c1, 0); /* length of current VCN */
|
||||
|
@ -678,8 +368,6 @@ read_data (struct grub_ntfs_attr *at, grub_uint8_t *pa, grub_uint8_t *dest,
|
|||
grub_disk_read_hook_t read_hook, void *read_hook_data)
|
||||
{
|
||||
struct grub_ntfs_rlst cc, *ctx;
|
||||
grub_uint8_t *end_ptr = (pa + len);
|
||||
grub_uint16_t run_offset;
|
||||
|
||||
if (len == 0)
|
||||
return 0;
|
||||
|
@ -695,28 +383,13 @@ read_data (struct grub_ntfs_attr *at, grub_uint8_t *pa, grub_uint8_t *dest,
|
|||
|
||||
if (pa[8] == 0)
|
||||
{
|
||||
if (ofs + len > res_attr_data_len (pa))
|
||||
if (ofs + len > u32at (pa, 0x10))
|
||||
return grub_error (GRUB_ERR_BAD_FS, "read out of range");
|
||||
|
||||
if (res_attr_data_len (pa) > (at->mft->data->mft_size << GRUB_NTFS_BLK_SHR))
|
||||
return grub_error (GRUB_ERR_BAD_FS, "resident attribute too large");
|
||||
|
||||
if (pa >= at->mft->buf + (at->mft->data->mft_size << GRUB_NTFS_BLK_SHR))
|
||||
return grub_error (GRUB_ERR_BAD_FS, "resident attribute out of range");
|
||||
|
||||
if (res_attr_data_off (pa) + res_attr_data_len (pa) >
|
||||
(grub_addr_t) at->mft->buf + (at->mft->data->mft_size << GRUB_NTFS_BLK_SHR) - (grub_addr_t) pa)
|
||||
return grub_error (GRUB_ERR_BAD_FS, "resident attribute out of range");
|
||||
|
||||
grub_memcpy (dest, pa + res_attr_data_off (pa) + ofs, len);
|
||||
grub_memcpy (dest, pa + u32at (pa, 0x14) + ofs, len);
|
||||
return 0;
|
||||
}
|
||||
|
||||
run_offset = u16at (pa, 0x20);
|
||||
if ((run_offset + pa) >= end_ptr || ((run_offset + pa) >= (at->end)))
|
||||
return grub_error (GRUB_ERR_BAD_FS, "run offset out of range");
|
||||
|
||||
ctx->cur_run = pa + run_offset;
|
||||
ctx->cur_run = pa + u16at (pa, 0x20);
|
||||
|
||||
ctx->next_vcn = u32at (pa, 0x10);
|
||||
ctx->curr_lcn = 0;
|
||||
|
@ -779,8 +452,6 @@ read_attr (struct grub_ntfs_attr *at, grub_uint8_t *dest, grub_disk_addr_t ofs,
|
|||
grub_uint8_t *pp;
|
||||
grub_err_t ret;
|
||||
|
||||
if (at == NULL || at->attr_cur == NULL)
|
||||
return grub_error (GRUB_ERR_BAD_FS, "attribute not found");
|
||||
save_cur = at->attr_cur;
|
||||
at->attr_nxt = at->attr_cur;
|
||||
attr = *at->attr_nxt;
|
||||
|
@ -797,17 +468,14 @@ read_attr (struct grub_ntfs_attr *at, grub_uint8_t *dest, grub_disk_addr_t ofs,
|
|||
else
|
||||
vcn = ofs >> (at->mft->data->log_spc + GRUB_NTFS_BLK_SHR);
|
||||
pa = at->attr_nxt + u16at (at->attr_nxt, 4);
|
||||
if (validate_attribute (pa, at->attr_end) == false)
|
||||
pa = NULL;
|
||||
|
||||
while (pa)
|
||||
while (pa < at->attr_end)
|
||||
{
|
||||
if (*pa != attr)
|
||||
break;
|
||||
if (u32at (pa, 8) > vcn)
|
||||
break;
|
||||
at->attr_nxt = pa;
|
||||
pa = next_attribute (pa, at->attr_end, true);
|
||||
pa += u16at (pa, 4);
|
||||
}
|
||||
}
|
||||
pp = find_attr (at, attr);
|
||||
|
@ -861,7 +529,7 @@ init_file (struct grub_ntfs_file *mft, grub_uint64_t mftno)
|
|||
(unsigned long long) mftno);
|
||||
|
||||
if (!pa[8])
|
||||
mft->size = res_attr_data_len (pa);
|
||||
mft->size = u32at (pa, 0x10);
|
||||
else
|
||||
mft->size = u64at (pa, 0x30);
|
||||
|
||||
|
@ -869,7 +537,7 @@ init_file (struct grub_ntfs_file *mft, grub_uint64_t mftno)
|
|||
mft->attr.attr_end = 0; /* Don't jump to attribute list */
|
||||
}
|
||||
else
|
||||
return init_attr (&mft->attr, mft);
|
||||
init_attr (&mft->attr, mft);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -877,11 +545,8 @@ init_file (struct grub_ntfs_file *mft, grub_uint64_t mftno)
|
|||
static void
|
||||
free_file (struct grub_ntfs_file *mft)
|
||||
{
|
||||
if (mft)
|
||||
{
|
||||
free_attr (&mft->attr);
|
||||
grub_free (mft->buf);
|
||||
}
|
||||
free_attr (&mft->attr);
|
||||
grub_free (mft->buf);
|
||||
}
|
||||
|
||||
static char *
|
||||
|
@ -907,21 +572,17 @@ get_utf8 (grub_uint8_t *in, grub_size_t len)
|
|||
}
|
||||
|
||||
static int
|
||||
list_file (struct grub_ntfs_file *diro, grub_uint8_t *pos, grub_uint8_t *end_pos,
|
||||
list_file (struct grub_ntfs_file *diro, grub_uint8_t *pos,
|
||||
grub_fshelp_iterate_dir_hook_t hook, void *hook_data)
|
||||
{
|
||||
grub_uint8_t *np;
|
||||
int ns;
|
||||
grub_uint16_t pos_incr;
|
||||
|
||||
while (1)
|
||||
{
|
||||
grub_uint8_t namespace;
|
||||
char *ustr;
|
||||
|
||||
if ((pos >= end_pos) || (end_pos - pos < 0x52))
|
||||
break;
|
||||
|
||||
if (pos[0xC] & 2) /* end signature */
|
||||
break;
|
||||
|
||||
|
@ -929,9 +590,6 @@ list_file (struct grub_ntfs_file *diro, grub_uint8_t *pos, grub_uint8_t *end_pos
|
|||
ns = *(np++);
|
||||
namespace = *(np++);
|
||||
|
||||
if (2 * ns > end_pos - pos - 0x52)
|
||||
break;
|
||||
|
||||
/*
|
||||
* Ignore files in DOS namespace, as they will reappear as Win32
|
||||
* names.
|
||||
|
@ -975,12 +633,7 @@ list_file (struct grub_ntfs_file *diro, grub_uint8_t *pos, grub_uint8_t *end_pos
|
|||
|
||||
grub_free (ustr);
|
||||
}
|
||||
pos_incr = u16at (pos, 8);
|
||||
if (pos_incr > 0)
|
||||
pos += pos_incr;
|
||||
else
|
||||
return 0;
|
||||
|
||||
pos += u16at (pos, 8);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -1091,9 +744,6 @@ grub_ntfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
int ret = 0;
|
||||
grub_size_t bitmap_len;
|
||||
struct grub_ntfs_file *mft;
|
||||
/* Used to make sure we're not stuck in a loop. */
|
||||
grub_uint8_t *last_pos = NULL;
|
||||
grub_uint32_t tmp_len;
|
||||
|
||||
mft = (struct grub_ntfs_file *) dir;
|
||||
|
||||
|
@ -1107,57 +757,40 @@ grub_ntfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
bmp = NULL;
|
||||
|
||||
at = &attr;
|
||||
if (init_attr (at, mft) != GRUB_ERR_NONE)
|
||||
return 0;
|
||||
|
||||
init_attr (at, mft);
|
||||
while (1)
|
||||
{
|
||||
cur_pos = find_attr (at, GRUB_NTFS_AT_INDEX_ROOT);
|
||||
if (cur_pos == NULL || cur_pos == last_pos)
|
||||
if (cur_pos == NULL)
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "no $INDEX_ROOT");
|
||||
goto done;
|
||||
}
|
||||
last_pos = cur_pos;
|
||||
|
||||
/* Resident, Namelen=4, Offset=0x18, Flags=0x00, Name="$I30" */
|
||||
if ((u32at (cur_pos, 8) != 0x180400) ||
|
||||
(u32at (cur_pos, 0x18) != 0x490024) ||
|
||||
(u32at (cur_pos, 0x1C) != 0x300033))
|
||||
continue;
|
||||
cur_pos += res_attr_data_off (cur_pos);
|
||||
if(cur_pos >= at->end)
|
||||
continue;
|
||||
cur_pos += u16at (cur_pos, 0x14);
|
||||
if (*cur_pos != 0x30) /* Not filename index */
|
||||
continue;
|
||||
break;
|
||||
}
|
||||
|
||||
cur_pos += 0x10; /* Skip index root */
|
||||
ret = list_file (mft, cur_pos + u16at (cur_pos, 0),
|
||||
at->mft->buf + (at->mft->data->mft_size << GRUB_NTFS_BLK_SHR),
|
||||
hook, hook_data);
|
||||
ret = list_file (mft, cur_pos + u16at (cur_pos, 0), hook, hook_data);
|
||||
if (ret)
|
||||
goto done;
|
||||
|
||||
bitmap = NULL;
|
||||
bitmap_len = 0;
|
||||
free_attr (at);
|
||||
/* No need to check errors here, as it will already be fine */
|
||||
init_attr (at, mft);
|
||||
|
||||
last_pos = NULL;
|
||||
while ((cur_pos = find_attr (at, GRUB_NTFS_AT_BITMAP)) != NULL)
|
||||
{
|
||||
int ofs;
|
||||
|
||||
if (cur_pos == last_pos)
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "bitmap attribute loop");
|
||||
goto done;
|
||||
}
|
||||
last_pos = cur_pos;
|
||||
|
||||
ofs = cur_pos[0xA];
|
||||
/* Namelen=4, Name="$I30" */
|
||||
if ((cur_pos[9] == 4) &&
|
||||
|
@ -1166,7 +799,7 @@ grub_ntfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
{
|
||||
int is_resident = (cur_pos[8] == 0);
|
||||
|
||||
bitmap_len = ((is_resident) ? res_attr_data_len (cur_pos) :
|
||||
bitmap_len = ((is_resident) ? u32at (cur_pos, 0x10) :
|
||||
u32at (cur_pos, 0x28));
|
||||
|
||||
bmp = grub_malloc (bitmap_len);
|
||||
|
@ -1175,26 +808,7 @@ grub_ntfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
|
||||
if (is_resident)
|
||||
{
|
||||
if (bitmap_len > (at->mft->data->mft_size << GRUB_NTFS_BLK_SHR))
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "resident bitmap too large");
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (cur_pos >= at->mft->buf + (at->mft->data->mft_size << GRUB_NTFS_BLK_SHR))
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "resident bitmap out of range");
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (res_attr_data_off (cur_pos) + res_attr_data_len (cur_pos) >
|
||||
(grub_addr_t) at->mft->buf + (at->mft->data->mft_size << GRUB_NTFS_BLK_SHR) - (grub_addr_t) cur_pos)
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "resident bitmap out of range");
|
||||
goto done;
|
||||
}
|
||||
|
||||
grub_memcpy (bmp, cur_pos + res_attr_data_off (cur_pos),
|
||||
grub_memcpy (bmp, cur_pos + u16at (cur_pos, 0x14),
|
||||
bitmap_len);
|
||||
}
|
||||
else
|
||||
|
@ -1205,15 +819,7 @@ grub_ntfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
"fails to read non-resident $BITMAP");
|
||||
goto done;
|
||||
}
|
||||
tmp_len = u32at (cur_pos, 0x30);
|
||||
if (tmp_len <= bitmap_len)
|
||||
bitmap_len = tmp_len;
|
||||
else
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS,
|
||||
"bitmap len too large for non-resident $BITMAP");
|
||||
goto done;
|
||||
}
|
||||
bitmap_len = u32at (cur_pos, 0x30);
|
||||
}
|
||||
|
||||
bitmap = bmp;
|
||||
|
@ -1222,7 +828,6 @@ grub_ntfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
}
|
||||
|
||||
free_attr (at);
|
||||
last_pos = NULL;
|
||||
cur_pos = locate_attr (at, mft, GRUB_NTFS_AT_INDEX_ALLOCATION);
|
||||
while (cur_pos != NULL)
|
||||
{
|
||||
|
@ -1232,9 +837,6 @@ grub_ntfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
(u32at (cur_pos, 0x44) == 0x300033))
|
||||
break;
|
||||
cur_pos = find_attr (at, GRUB_NTFS_AT_INDEX_ALLOCATION);
|
||||
if (cur_pos == last_pos)
|
||||
break;
|
||||
last_pos = cur_pos;
|
||||
}
|
||||
|
||||
if ((!cur_pos) && (bitmap))
|
||||
|
@ -1264,7 +866,6 @@ grub_ntfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
(const grub_uint8_t *) "INDX")))
|
||||
goto done;
|
||||
ret = list_file (mft, &indx[0x18 + u16at (indx, 0x18)],
|
||||
indx + (mft->data->idx_size << GRUB_NTFS_BLK_SHR),
|
||||
hook, hook_data);
|
||||
if (ret)
|
||||
goto done;
|
||||
|
@ -1530,7 +1131,6 @@ grub_ntfs_label (grub_device_t device, char **label)
|
|||
struct grub_ntfs_data *data = 0;
|
||||
struct grub_fshelp_node *mft = 0;
|
||||
grub_uint8_t *pa;
|
||||
grub_err_t err;
|
||||
|
||||
grub_dl_ref (my_mod);
|
||||
|
||||
|
@ -1556,35 +1156,15 @@ grub_ntfs_label (grub_device_t device, char **label)
|
|||
goto fail;
|
||||
}
|
||||
|
||||
err = init_attr (&mft->attr, mft);
|
||||
if (err != GRUB_ERR_NONE)
|
||||
return err;
|
||||
|
||||
init_attr (&mft->attr, mft);
|
||||
pa = find_attr (&mft->attr, GRUB_NTFS_AT_VOLUME_NAME);
|
||||
|
||||
if (pa == NULL || pa >= mft->buf + (mft->data->mft_size << GRUB_NTFS_BLK_SHR))
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "can\'t parse volume label");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
if (mft->buf + (mft->data->mft_size << GRUB_NTFS_BLK_SHR) - pa < 0x16)
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "can\'t parse volume label");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
if ((pa) && (pa[8] == 0) && (res_attr_data_len (pa)))
|
||||
if ((pa) && (pa[8] == 0) && (u32at (pa, 0x10)))
|
||||
{
|
||||
int len;
|
||||
|
||||
len = res_attr_data_len (pa) / 2;
|
||||
pa += res_attr_data_off (pa);
|
||||
if (mft->buf + (mft->data->mft_size << GRUB_NTFS_BLK_SHR) - pa >= 2 * len &&
|
||||
pa >= mft->buf && (pa + len < (mft->buf + (mft->data->mft_size << GRUB_NTFS_BLK_SHR))))
|
||||
*label = get_utf8 (pa, len);
|
||||
else
|
||||
grub_error (GRUB_ERR_BAD_FS, "can\'t parse volume label");
|
||||
len = u32at (pa, 0x10) / 2;
|
||||
pa += u16at (pa, 0x14);
|
||||
*label = get_utf8 (pa, len);
|
||||
}
|
||||
|
||||
fail:
|
||||
|
@ -1651,16 +1231,11 @@ static struct grub_fs grub_ntfs_fs =
|
|||
|
||||
GRUB_MOD_INIT (ntfs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
{
|
||||
grub_ntfs_fs.mod = mod;
|
||||
grub_fs_register (&grub_ntfs_fs);
|
||||
}
|
||||
grub_fs_register (&grub_ntfs_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
||||
GRUB_MOD_FINI (ntfs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_unregister (&grub_ntfs_fs);
|
||||
grub_fs_unregister (&grub_ntfs_fs);
|
||||
}
|
||||
|
|
|
@ -22,7 +22,6 @@
|
|||
#include <grub/disk.h>
|
||||
#include <grub/dl.h>
|
||||
#include <grub/ntfs.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -30,7 +29,7 @@ static grub_err_t
|
|||
decomp_nextvcn (struct grub_ntfs_comp *cc)
|
||||
{
|
||||
if (cc->comp_head >= cc->comp_tail)
|
||||
return grub_error (GRUB_ERR_BAD_FS, "compression block overflow");
|
||||
return grub_error (GRUB_ERR_BAD_FS, "compression block overflown");
|
||||
if (grub_disk_read
|
||||
(cc->disk,
|
||||
(cc->comp_table[cc->comp_head].next_lcn -
|
||||
|
@ -311,7 +310,6 @@ ntfscomp (grub_uint8_t *dest, grub_disk_addr_t ofs,
|
|||
{
|
||||
grub_err_t ret;
|
||||
grub_disk_addr_t vcn;
|
||||
int log_sz;
|
||||
|
||||
if (ctx->attr->sbuf)
|
||||
{
|
||||
|
@ -351,12 +349,7 @@ ntfscomp (grub_uint8_t *dest, grub_disk_addr_t ofs,
|
|||
}
|
||||
|
||||
ctx->comp.comp_head = ctx->comp.comp_tail = 0;
|
||||
if (grub_add (ctx->comp.log_spc, GRUB_NTFS_BLK_SHR, &log_sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("compression buffer size overflow"));
|
||||
return 0;
|
||||
}
|
||||
ctx->comp.cbuf = grub_malloc (1 << log_sz);
|
||||
ctx->comp.cbuf = grub_malloc (1 << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR));
|
||||
if (!ctx->comp.cbuf)
|
||||
return 0;
|
||||
|
||||
|
|
|
@ -52,7 +52,6 @@ read_number (const char *str, grub_size_t size)
|
|||
|
||||
GRUB_MOD_INIT (odc)
|
||||
{
|
||||
grub_cpio_fs.mod = mod;
|
||||
grub_fs_register (&grub_cpio_fs);
|
||||
}
|
||||
|
||||
|
|
|
@ -192,7 +192,6 @@ static struct grub_fs grub_procfs_fs =
|
|||
|
||||
GRUB_MOD_INIT (procfs)
|
||||
{
|
||||
grub_procfs_fs.mod = mod;
|
||||
grub_disk_dev_register (&grub_procfs_dev);
|
||||
grub_fs_register (&grub_procfs_fs);
|
||||
}
|
||||
|
|
|
@ -39,7 +39,6 @@
|
|||
#include <grub/types.h>
|
||||
#include <grub/fshelp.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/lockdown.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -1418,16 +1417,11 @@ static struct grub_fs grub_reiserfs_fs =
|
|||
|
||||
GRUB_MOD_INIT(reiserfs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
{
|
||||
grub_reiserfs_fs.mod = mod;
|
||||
grub_fs_register (&grub_reiserfs_fs);
|
||||
}
|
||||
grub_fs_register (&grub_reiserfs_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
||||
GRUB_MOD_FINI(reiserfs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_unregister (&grub_reiserfs_fs);
|
||||
grub_fs_unregister (&grub_reiserfs_fs);
|
||||
}
|
||||
|
|
|
@ -23,7 +23,6 @@
|
|||
#include <grub/disk.h>
|
||||
#include <grub/fs.h>
|
||||
#include <grub/fshelp.h>
|
||||
#include <grub/lockdown.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -476,15 +475,10 @@ static struct grub_fs grub_romfs_fs =
|
|||
|
||||
GRUB_MOD_INIT(romfs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
{
|
||||
grub_romfs_fs.mod = mod;
|
||||
grub_fs_register (&grub_romfs_fs);
|
||||
}
|
||||
grub_fs_register (&grub_romfs_fs);
|
||||
}
|
||||
|
||||
GRUB_MOD_FINI(romfs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_unregister (&grub_romfs_fs);
|
||||
grub_fs_unregister (&grub_romfs_fs);
|
||||
}
|
||||
|
|
|
@ -26,7 +26,6 @@
|
|||
#include <grub/types.h>
|
||||
#include <grub/fshelp.h>
|
||||
#include <grub/charset.h>
|
||||
#include <grub/lockdown.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
@ -429,9 +428,6 @@ grub_sfs_mount (grub_disk_t disk)
|
|||
- 24 /* offsetof (struct grub_sfs_objc, objects) */
|
||||
- 25); /* offsetof (struct grub_sfs_obj, filename) */
|
||||
data->label = grub_zalloc (max_len + 1);
|
||||
if (data->label == NULL)
|
||||
goto fail;
|
||||
|
||||
grub_strncpy (data->label, (char *) rootobjc->objects[0].filename, max_len);
|
||||
|
||||
grub_free (rootobjc_data);
|
||||
|
@ -783,16 +779,11 @@ static struct grub_fs grub_sfs_fs =
|
|||
|
||||
GRUB_MOD_INIT(sfs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
{
|
||||
grub_sfs_fs.mod = mod;
|
||||
grub_fs_register (&grub_sfs_fs);
|
||||
}
|
||||
grub_fs_register (&grub_sfs_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
||||
GRUB_MOD_FINI(sfs)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_unregister (&grub_sfs_fs);
|
||||
grub_fs_unregister (&grub_sfs_fs);
|
||||
}
|
||||
|
|
|
@ -460,11 +460,11 @@ grub_squash_read_symlink (grub_fshelp_node_t node)
|
|||
{
|
||||
char *ret;
|
||||
grub_err_t err;
|
||||
grub_uint32_t sz;
|
||||
grub_size_t sz;
|
||||
|
||||
if (grub_add (grub_le_to_cpu32 (node->ino.symlink.namelen), 1, &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("symlink name length overflow"));
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow is detected"));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
@ -580,7 +580,6 @@ grub_squash_iterate_dir (grub_fshelp_node_t dir,
|
|||
struct grub_squash_dirent di;
|
||||
struct grub_squash_inode ino;
|
||||
grub_size_t sz;
|
||||
grub_uint16_t nlen;
|
||||
|
||||
err = read_chunk (dir->data, &di, sizeof (di),
|
||||
grub_le_to_cpu64 (dir->data->sb.diroffset)
|
||||
|
@ -596,12 +595,7 @@ grub_squash_iterate_dir (grub_fshelp_node_t dir,
|
|||
if (err)
|
||||
return 0;
|
||||
|
||||
if (grub_add (grub_le_to_cpu16 (di.namelen), 2, &nlen))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("name length overflow"));
|
||||
return 0;
|
||||
}
|
||||
buf = grub_malloc (nlen);
|
||||
buf = grub_malloc (grub_le_to_cpu16 (di.namelen) + 2);
|
||||
if (!buf)
|
||||
return 0;
|
||||
err = read_chunk (dir->data, buf,
|
||||
|
@ -822,10 +816,10 @@ direct_read (struct grub_squash_data *data,
|
|||
break;
|
||||
}
|
||||
total_blocks = ((total_size + data->blksz - 1) >> data->log2_blksz);
|
||||
ino->block_sizes = grub_calloc (total_blocks,
|
||||
sizeof (ino->block_sizes[0]));
|
||||
ino->cumulated_block_sizes = grub_calloc (total_blocks,
|
||||
sizeof (ino->cumulated_block_sizes[0]));
|
||||
ino->block_sizes = grub_malloc (total_blocks
|
||||
* sizeof (ino->block_sizes[0]));
|
||||
ino->cumulated_block_sizes = grub_malloc (total_blocks
|
||||
* sizeof (ino->cumulated_block_sizes[0]));
|
||||
if (!ino->block_sizes || !ino->cumulated_block_sizes)
|
||||
{
|
||||
grub_free (ino->block_sizes);
|
||||
|
@ -1050,7 +1044,6 @@ static struct grub_fs grub_squash_fs =
|
|||
|
||||
GRUB_MOD_INIT(squash4)
|
||||
{
|
||||
grub_squash_fs.mod = mod;
|
||||
grub_fs_register (&grub_squash_fs);
|
||||
}
|
||||
|
||||
|
|
|
@ -25,7 +25,6 @@
|
|||
#include <grub/mm.h>
|
||||
#include <grub/dl.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -77,10 +76,8 @@ grub_cpio_find_file (struct grub_archelp_data *data, char **name,
|
|||
{
|
||||
struct head hd;
|
||||
int reread = 0, have_longname = 0, have_longlink = 0;
|
||||
grub_size_t sz;
|
||||
|
||||
data->hofs = data->next_hofs;
|
||||
*name = NULL;
|
||||
|
||||
for (reread = 0; reread < 3; reread++)
|
||||
{
|
||||
|
@ -99,13 +96,8 @@ grub_cpio_find_file (struct grub_archelp_data *data, char **name,
|
|||
if (hd.typeflag == 'L')
|
||||
{
|
||||
grub_err_t err;
|
||||
grub_size_t namesize;
|
||||
|
||||
if (grub_cast (read_number (hd.size, sizeof (hd.size)), &namesize) ||
|
||||
grub_add (namesize, 1, &sz))
|
||||
return grub_error (GRUB_ERR_BAD_FS, N_("name size overflow"));
|
||||
|
||||
*name = grub_malloc (sz);
|
||||
grub_size_t namesize = read_number (hd.size, sizeof (hd.size));
|
||||
*name = grub_malloc (namesize + 1);
|
||||
if (*name == NULL)
|
||||
return grub_errno;
|
||||
err = grub_disk_read (data->disk, 0,
|
||||
|
@ -124,21 +116,16 @@ grub_cpio_find_file (struct grub_archelp_data *data, char **name,
|
|||
if (hd.typeflag == 'K')
|
||||
{
|
||||
grub_err_t err;
|
||||
grub_size_t linksize;
|
||||
|
||||
if (grub_cast (read_number (hd.size, sizeof (hd.size)), &linksize) ||
|
||||
grub_add (linksize, 1, &sz))
|
||||
return grub_error (GRUB_ERR_BAD_FS, N_("link size overflow"));
|
||||
|
||||
if (data->linkname_alloc < sz)
|
||||
grub_size_t linksize = read_number (hd.size, sizeof (hd.size));
|
||||
if (data->linkname_alloc < linksize + 1)
|
||||
{
|
||||
char *n;
|
||||
n = grub_calloc (2, sz);
|
||||
n = grub_calloc (2, linksize + 1);
|
||||
if (!n)
|
||||
return grub_errno;
|
||||
grub_free (data->linkname);
|
||||
data->linkname = n;
|
||||
data->linkname_alloc = 2 * (sz);
|
||||
data->linkname_alloc = 2 * (linksize + 1);
|
||||
}
|
||||
|
||||
err = grub_disk_read (data->disk, 0,
|
||||
|
@ -161,10 +148,7 @@ grub_cpio_find_file (struct grub_archelp_data *data, char **name,
|
|||
while (extra_size < sizeof (hd.prefix)
|
||||
&& hd.prefix[extra_size])
|
||||
extra_size++;
|
||||
|
||||
if (grub_add (sizeof (hd.name) + 2, extra_size, &sz))
|
||||
return grub_error (GRUB_ERR_BAD_FS, N_("long name size overflow"));
|
||||
*name = grub_malloc (sz);
|
||||
*name = grub_malloc (sizeof (hd.name) + extra_size + 2);
|
||||
if (*name == NULL)
|
||||
return grub_errno;
|
||||
if (hd.prefix[0])
|
||||
|
@ -176,22 +160,15 @@ grub_cpio_find_file (struct grub_archelp_data *data, char **name,
|
|||
(*name)[extra_size + sizeof (hd.name)] = 0;
|
||||
}
|
||||
|
||||
if (grub_cast (read_number (hd.size, sizeof (hd.size)), &data->size))
|
||||
return grub_error (GRUB_ERR_BAD_FS, N_("data size overflow"));
|
||||
|
||||
data->size = read_number (hd.size, sizeof (hd.size));
|
||||
data->dofs = data->hofs + GRUB_DISK_SECTOR_SIZE;
|
||||
data->next_hofs = data->dofs + ((data->size + GRUB_DISK_SECTOR_SIZE - 1) &
|
||||
~(GRUB_DISK_SECTOR_SIZE - 1));
|
||||
if (mtime)
|
||||
{
|
||||
if (grub_cast (read_number (hd.mtime, sizeof (hd.mtime)), mtime))
|
||||
return grub_error (GRUB_ERR_BAD_FS, N_("mtime overflow"));
|
||||
}
|
||||
*mtime = read_number (hd.mtime, sizeof (hd.mtime));
|
||||
if (mode)
|
||||
{
|
||||
if (grub_cast (read_number (hd.mode, sizeof (hd.mode)), mode))
|
||||
return grub_error (GRUB_ERR_BAD_FS, N_("mode overflow"));
|
||||
|
||||
*mode = read_number (hd.mode, sizeof (hd.mode));
|
||||
switch (hd.typeflag)
|
||||
{
|
||||
/* Hardlink. */
|
||||
|
@ -225,10 +202,6 @@ grub_cpio_find_file (struct grub_archelp_data *data, char **name,
|
|||
}
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
if (*name == NULL)
|
||||
return grub_error (GRUB_ERR_BAD_FS, "invalid tar archive");
|
||||
|
||||
return GRUB_ERR_NONE;
|
||||
}
|
||||
|
||||
|
@ -363,7 +336,6 @@ static struct grub_fs grub_cpio_fs = {
|
|||
|
||||
GRUB_MOD_INIT (tar)
|
||||
{
|
||||
grub_cpio_fs.mod = mod;
|
||||
grub_fs_register (&grub_cpio_fs);
|
||||
}
|
||||
|
||||
|
|
|
@ -27,7 +27,6 @@
|
|||
#include <grub/fshelp.h>
|
||||
#include <grub/charset.h>
|
||||
#include <grub/datetime.h>
|
||||
#include <grub/lockdown.h>
|
||||
#include <grub/udf.h>
|
||||
#include <grub/safemath.h>
|
||||
|
||||
|
@ -1456,16 +1455,11 @@ static struct grub_fs grub_udf_fs = {
|
|||
|
||||
GRUB_MOD_INIT (udf)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
{
|
||||
grub_udf_fs.mod = mod;
|
||||
grub_fs_register (&grub_udf_fs);
|
||||
}
|
||||
grub_fs_register (&grub_udf_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
||||
GRUB_MOD_FINI (udf)
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_unregister (&grub_udf_fs);
|
||||
grub_fs_unregister (&grub_udf_fs);
|
||||
}
|
||||
|
|
|
@ -25,7 +25,6 @@
|
|||
#include <grub/dl.h>
|
||||
#include <grub/types.h>
|
||||
#include <grub/i18n.h>
|
||||
#include <grub/lockdown.h>
|
||||
|
||||
GRUB_MOD_LICENSE ("GPLv3+");
|
||||
|
||||
|
@ -464,7 +463,7 @@ grub_ufs_lookup_symlink (struct grub_ufs_data *data, int ino)
|
|||
/* Check against zero is paylindromic, no need to swap. */
|
||||
if (data->inode.nblocks == 0
|
||||
&& INODE_SIZE (data) <= sizeof (data->inode.symlink))
|
||||
grub_strlcpy (symlink, (char *) data->inode.symlink, sz);
|
||||
grub_strcpy (symlink, (char *) data->inode.symlink);
|
||||
else
|
||||
{
|
||||
if (grub_ufs_read_file (data, 0, 0, 0, sz, symlink) < 0)
|
||||
|
@ -900,11 +899,7 @@ GRUB_MOD_INIT(ufs1)
|
|||
#endif
|
||||
#endif
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
{
|
||||
grub_ufs_fs.mod = mod;
|
||||
grub_fs_register (&grub_ufs_fs);
|
||||
}
|
||||
grub_fs_register (&grub_ufs_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
||||
|
@ -918,7 +913,6 @@ GRUB_MOD_FINI(ufs1)
|
|||
#endif
|
||||
#endif
|
||||
{
|
||||
if (!grub_is_lockdown ())
|
||||
grub_fs_unregister (&grub_ufs_fs);
|
||||
grub_fs_unregister (&grub_ufs_fs);
|
||||
}
|
||||
|
||||
|
|
|
@ -79,8 +79,6 @@ GRUB_MOD_LICENSE ("GPLv3+");
|
|||
/* Inode flags2 flags */
|
||||
#define XFS_DIFLAG2_BIGTIME_BIT 3
|
||||
#define XFS_DIFLAG2_BIGTIME (1 << XFS_DIFLAG2_BIGTIME_BIT)
|
||||
#define XFS_DIFLAG2_NREXT64_BIT 4
|
||||
#define XFS_DIFLAG2_NREXT64 (1 << XFS_DIFLAG2_NREXT64_BIT)
|
||||
|
||||
/* incompat feature flags */
|
||||
#define XFS_SB_FEAT_INCOMPAT_FTYPE (1 << 0) /* filetype in dirent */
|
||||
|
@ -88,10 +86,6 @@ GRUB_MOD_LICENSE ("GPLv3+");
|
|||
#define XFS_SB_FEAT_INCOMPAT_META_UUID (1 << 2) /* metadata UUID */
|
||||
#define XFS_SB_FEAT_INCOMPAT_BIGTIME (1 << 3) /* large timestamps */
|
||||
#define XFS_SB_FEAT_INCOMPAT_NEEDSREPAIR (1 << 4) /* needs xfs_repair */
|
||||
#define XFS_SB_FEAT_INCOMPAT_NREXT64 (1 << 5) /* large extent counters */
|
||||
#define XFS_SB_FEAT_INCOMPAT_EXCHRANGE (1 << 6) /* exchangerange supported */
|
||||
#define XFS_SB_FEAT_INCOMPAT_PARENT (1 << 7) /* parent pointers */
|
||||
#define XFS_SB_FEAT_INCOMPAT_METADIR (1 << 8) /* metadata dir tree */
|
||||
|
||||
/*
|
||||
* Directory entries with ftype are explicitly handled by GRUB code.
|
||||
|
@ -101,26 +95,13 @@ GRUB_MOD_LICENSE ("GPLv3+");
|
|||
*
|
||||
* We do not currently verify metadata UUID, so it is safe to read filesystems
|
||||
* with the XFS_SB_FEAT_INCOMPAT_META_UUID feature.
|
||||
*
|
||||
* We do not currently replay the log, so it is safe to read filesystems
|
||||
* with the XFS_SB_FEAT_INCOMPAT_EXCHRANGE feature.
|
||||
*
|
||||
* We do not currently read directory parent pointers, so it is safe to read
|
||||
* filesystems with the XFS_SB_FEAT_INCOMPAT_PARENT feature.
|
||||
*
|
||||
* We do not currently look at realtime or quota metadata, so it is safe to
|
||||
* read filesystems with the XFS_SB_FEAT_INCOMPAT_METADIR feature.
|
||||
*/
|
||||
#define XFS_SB_FEAT_INCOMPAT_SUPPORTED \
|
||||
(XFS_SB_FEAT_INCOMPAT_FTYPE | \
|
||||
XFS_SB_FEAT_INCOMPAT_SPINODES | \
|
||||
XFS_SB_FEAT_INCOMPAT_META_UUID | \
|
||||
XFS_SB_FEAT_INCOMPAT_BIGTIME | \
|
||||
XFS_SB_FEAT_INCOMPAT_NEEDSREPAIR | \
|
||||
XFS_SB_FEAT_INCOMPAT_NREXT64 | \
|
||||
XFS_SB_FEAT_INCOMPAT_EXCHRANGE | \
|
||||
XFS_SB_FEAT_INCOMPAT_PARENT | \
|
||||
XFS_SB_FEAT_INCOMPAT_METADIR)
|
||||
XFS_SB_FEAT_INCOMPAT_NEEDSREPAIR)
|
||||
|
||||
struct grub_xfs_sblock
|
||||
{
|
||||
|
@ -222,8 +203,7 @@ struct grub_xfs_inode
|
|||
grub_uint16_t mode;
|
||||
grub_uint8_t version;
|
||||
grub_uint8_t format;
|
||||
grub_uint8_t unused2[18];
|
||||
grub_uint64_t nextents_big;
|
||||
grub_uint8_t unused2[26];
|
||||
grub_uint64_t atime;
|
||||
grub_uint64_t mtime;
|
||||
grub_uint64_t ctime;
|
||||
|
@ -243,12 +223,6 @@ struct grub_xfs_inode
|
|||
/* Size of struct grub_xfs_inode v2, up to unused4 member included. */
|
||||
#define XFS_V2_INODE_SIZE (XFS_V3_INODE_SIZE - 76)
|
||||
|
||||
struct grub_xfs_dir_leaf_entry
|
||||
{
|
||||
grub_uint32_t hashval;
|
||||
grub_uint32_t address;
|
||||
} GRUB_PACKED;
|
||||
|
||||
struct grub_xfs_dirblock_tail
|
||||
{
|
||||
grub_uint32_t leaf_count;
|
||||
|
@ -342,8 +316,6 @@ static int grub_xfs_sb_valid(struct grub_xfs_data *data)
|
|||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
grub_error (GRUB_ERR_BAD_FS, "unsupported XFS filesystem version");
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -567,26 +539,11 @@ get_fsb (const void *keys, int idx)
|
|||
return grub_be_to_cpu64 (grub_get_unaligned64 (p));
|
||||
}
|
||||
|
||||
static int
|
||||
grub_xfs_inode_has_large_extent_counts (const struct grub_xfs_inode *inode)
|
||||
{
|
||||
return inode->version >= 3 &&
|
||||
(inode->flags2 & grub_cpu_to_be64_compile_time (XFS_DIFLAG2_NREXT64));
|
||||
}
|
||||
|
||||
static grub_uint64_t
|
||||
grub_xfs_get_inode_nextents (struct grub_xfs_inode *inode)
|
||||
{
|
||||
return (grub_xfs_inode_has_large_extent_counts (inode)) ?
|
||||
grub_be_to_cpu64 (inode->nextents_big) :
|
||||
grub_be_to_cpu32 (inode->nextents);
|
||||
}
|
||||
|
||||
static grub_disk_addr_t
|
||||
grub_xfs_read_block (grub_fshelp_node_t node, grub_disk_addr_t fileblock)
|
||||
{
|
||||
struct grub_xfs_btree_node *leaf = 0;
|
||||
grub_uint64_t ex, nrec;
|
||||
int ex, nrec;
|
||||
struct grub_xfs_extent *exts;
|
||||
grub_uint64_t ret = 0;
|
||||
|
||||
|
@ -611,18 +568,7 @@ grub_xfs_read_block (grub_fshelp_node_t node, grub_disk_addr_t fileblock)
|
|||
/ (2 * sizeof (grub_uint64_t));
|
||||
do
|
||||
{
|
||||
grub_uint64_t i;
|
||||
grub_addr_t keys_end, data_end;
|
||||
|
||||
if (grub_mul (sizeof (grub_uint64_t), nrec, &keys_end) ||
|
||||
grub_add ((grub_addr_t) keys, keys_end, &keys_end) ||
|
||||
grub_add ((grub_addr_t) node->data, node->data->data_size, &data_end) ||
|
||||
keys_end > data_end)
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "invalid number of XFS root keys");
|
||||
grub_free (leaf);
|
||||
return 0;
|
||||
}
|
||||
int i;
|
||||
|
||||
for (i = 0; i < nrec; i++)
|
||||
{
|
||||
|
@ -669,7 +615,7 @@ grub_xfs_read_block (grub_fshelp_node_t node, grub_disk_addr_t fileblock)
|
|||
grub_addr_t exts_end = 0;
|
||||
grub_addr_t data_end = 0;
|
||||
|
||||
nrec = grub_xfs_get_inode_nextents (&node->inode);
|
||||
nrec = grub_be_to_cpu32 (node->inode.nextents);
|
||||
exts = (struct grub_xfs_extent *) grub_xfs_inode_data(&node->inode);
|
||||
|
||||
if (grub_mul (sizeof (struct grub_xfs_extent), nrec, &exts_end) ||
|
||||
|
@ -733,7 +679,6 @@ static char *
|
|||
grub_xfs_read_symlink (grub_fshelp_node_t node)
|
||||
{
|
||||
grub_ssize_t size = grub_be_to_cpu64 (node->inode.size);
|
||||
grub_size_t sz;
|
||||
|
||||
if (size < 0)
|
||||
{
|
||||
|
@ -755,12 +700,7 @@ grub_xfs_read_symlink (grub_fshelp_node_t node)
|
|||
if (node->data->hascrc)
|
||||
off = 56;
|
||||
|
||||
if (grub_add (size, 1, &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("symlink size overflow"));
|
||||
return 0;
|
||||
}
|
||||
symlink = grub_malloc (sz);
|
||||
symlink = grub_malloc (size + 1);
|
||||
if (!symlink)
|
||||
return 0;
|
||||
|
||||
|
@ -810,15 +750,8 @@ static int iterate_dir_call_hook (grub_uint64_t ino, const char *filename,
|
|||
{
|
||||
struct grub_fshelp_node *fdiro;
|
||||
grub_err_t err;
|
||||
grub_size_t sz;
|
||||
|
||||
if (grub_add (grub_xfs_fshelp_size(ctx->diro->data), 1, &sz))
|
||||
{
|
||||
grub_error (GRUB_ERR_OUT_OF_RANGE, N_("directory data size overflow"));
|
||||
grub_print_error ();
|
||||
return 0;
|
||||
}
|
||||
fdiro = grub_malloc (sz);
|
||||
fdiro = grub_malloc (grub_xfs_fshelp_size(ctx->diro->data) + 1);
|
||||
if (!fdiro)
|
||||
{
|
||||
grub_print_error ();
|
||||
|
@ -877,19 +810,14 @@ grub_xfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
if (iterate_dir_call_hook (parent, "..", &ctx))
|
||||
return 1;
|
||||
|
||||
for (i = 0; i < head->count &&
|
||||
(grub_uint8_t *) de < ((grub_uint8_t *) dir + grub_xfs_fshelp_size (dir->data)); i++)
|
||||
for (i = 0; i < head->count; i++)
|
||||
{
|
||||
grub_uint64_t ino;
|
||||
grub_uint8_t *inopos = grub_xfs_inline_de_inopos(dir->data, de);
|
||||
grub_uint8_t c;
|
||||
|
||||
if ((inopos + (smallino ? 4 : 8)) > (grub_uint8_t *) dir + grub_xfs_fshelp_size (dir->data))
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "invalid XFS inode");
|
||||
return 0;
|
||||
}
|
||||
|
||||
return grub_error (GRUB_ERR_BAD_FS, "not a correct XFS inode");
|
||||
|
||||
/* inopos might be unaligned. */
|
||||
if (smallino)
|
||||
|
@ -917,6 +845,10 @@ grub_xfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
de->name[de->len] = c;
|
||||
|
||||
de = grub_xfs_inline_next_de(dir->data, head, de);
|
||||
|
||||
if ((grub_uint8_t *) de >= (grub_uint8_t *) dir + grub_xfs_fshelp_size (dir->data))
|
||||
return grub_error (GRUB_ERR_BAD_FS, "invalid XFS directory entry");
|
||||
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
@ -945,9 +877,9 @@ grub_xfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
{
|
||||
struct grub_xfs_dir2_entry *direntry =
|
||||
grub_xfs_first_de(dir->data, dirblock);
|
||||
int entries = -1;
|
||||
char *end = dirblock + dirblk_size;
|
||||
grub_uint32_t magic;
|
||||
int entries;
|
||||
struct grub_xfs_dirblock_tail *tail =
|
||||
grub_xfs_dir_tail(dir->data, dirblock);
|
||||
|
||||
numread = grub_xfs_read_file (dir, 0, 0,
|
||||
blk << dirblk_log2,
|
||||
|
@ -958,36 +890,14 @@ grub_xfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* If this data block isn't actually part of the extent list then
|
||||
* grub_xfs_read_file() returns a block of zeros. So, if the magic
|
||||
* number field is all zeros then this block should be skipped.
|
||||
*/
|
||||
magic = *(grub_uint32_t *)(void *) dirblock;
|
||||
if (!magic)
|
||||
entries = (grub_be_to_cpu32 (tail->leaf_count)
|
||||
- grub_be_to_cpu32 (tail->leaf_stale));
|
||||
|
||||
if (!entries)
|
||||
continue;
|
||||
|
||||
/*
|
||||
* Leaf and tail information are only in the data block if the number
|
||||
* of extents is 1.
|
||||
*/
|
||||
if (grub_xfs_get_inode_nextents (&dir->inode) == 1)
|
||||
{
|
||||
struct grub_xfs_dirblock_tail *tail = grub_xfs_dir_tail (dir->data, dirblock);
|
||||
|
||||
end = (char *) tail;
|
||||
|
||||
/* Subtract the space used by leaf nodes. */
|
||||
end -= grub_be_to_cpu32 (tail->leaf_count) * sizeof (struct grub_xfs_dir_leaf_entry);
|
||||
|
||||
entries = grub_be_to_cpu32 (tail->leaf_count) - grub_be_to_cpu32 (tail->leaf_stale);
|
||||
|
||||
if (!entries)
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Iterate over all entries within this block. */
|
||||
while ((char *) direntry < (char *) end)
|
||||
while ((char *)direntry < (char *)tail)
|
||||
{
|
||||
grub_uint8_t *freetag;
|
||||
char *filename;
|
||||
|
@ -1007,11 +917,8 @@ grub_xfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
}
|
||||
|
||||
filename = (char *)(direntry + 1);
|
||||
if (filename + direntry->len + 1 > (char *) end)
|
||||
{
|
||||
grub_error (GRUB_ERR_BAD_FS, "invalid XFS directory entry");
|
||||
return 0;
|
||||
}
|
||||
if (filename + direntry->len - 1 > (char *) tail)
|
||||
return grub_error (GRUB_ERR_BAD_FS, "invalid XFS directory entry");
|
||||
|
||||
/* The byte after the filename is for the filetype, padding, or
|
||||
tag, which is not used by GRUB. So it can be overwritten. */
|
||||
|
@ -1024,17 +931,11 @@ grub_xfs_iterate_dir (grub_fshelp_node_t dir,
|
|||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
* The expected number of directory entries is only tracked for the
|
||||
* single extent case.
|
||||
*/
|
||||
if (grub_xfs_get_inode_nextents (&dir->inode) == 1)
|
||||
{
|
||||
/* Check if last direntry in this block is reached. */
|
||||
entries--;
|
||||
if (!entries)
|
||||
break;
|
||||
}
|
||||
/* Check if last direntry in this block is
|
||||
reached. */
|
||||
entries--;
|
||||
if (!entries)
|
||||
break;
|
||||
|
||||
/* Select the next directory entry. */
|
||||
direntry = grub_xfs_next_de(dir->data, direntry);
|
||||
|
@ -1105,7 +1006,7 @@ grub_xfs_mount (grub_disk_t disk)
|
|||
return data;
|
||||
fail:
|
||||
|
||||
if (grub_errno == GRUB_ERR_OUT_OF_RANGE || grub_errno == GRUB_ERR_NONE)
|
||||
if (grub_errno == GRUB_ERR_OUT_OF_RANGE)
|
||||
grub_error (GRUB_ERR_BAD_FS, "not an XFS filesystem");
|
||||
|
||||
grub_free (data);
|
||||
|
@ -1339,7 +1240,6 @@ static struct grub_fs grub_xfs_fs =
|
|||
|
||||
GRUB_MOD_INIT(xfs)
|
||||
{
|
||||
grub_xfs_fs.mod = mod;
|
||||
grub_fs_register (&grub_xfs_fs);
|
||||
my_mod = mod;
|
||||
}
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Add a link
Reference in a new issue