merge master to newports/alpha

This commit is contained in:
Vladimir Serbinenko committed 2013-11-08 18:46:53 +01:00
commit 7c58da503f
234 files changed
+15114 -3452

No files matched your search

+733 -5
View File
@@ -1,3 +1,736 @@
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* b/grub-core/term/serial.c: Add option for enabling/disabling
RTS/CTS flow control.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/lib/libgcrypt/cipher/idea.c (mul_inv): Remove signed
divisions.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/lib/libgcrypt/mpi/mpih-div.c (_gcry_mpih_divrem):
Use grub_fatal rather than divide by zero.
* grub-core/lib/libgcrypt/mpi/mpi-pow.c (gcry_mpi_powm): Likewise.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* include/grub/gui.h (grub_fixed_sfs_divide): Round rather than
truncate.
(grub_fixed_fsf_divide): Likewise.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/gfxmenu/gui_list.c (draw_scrollbar): Avoid
division by-zero and senseless negative divisions.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/gfxmenu/gui_circular_progress.c (circprog_paint): Avoid
division by-zero and senseless negative divisions.
(circprog_set_property): Don't accept negative num_ticks.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/gfxmenu/gui_progress_bar.c (draw_pixmap_bar): Avoid
division by-zero and senseless negative divisions.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* configure.ac: Use elf_*_fbsd on kfreebsd.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/tests/div_test.c: New test.
2013-11-08 Vladimir Testov <vladimir.testov@rosalab.ru>
* grub-core/gfxmenu/gui_box.c: Updated to work with area status.
* grub-core/gfxmenu/gui_canvas.c: Likewise.
* grub-core/gfxmenu/view.c: Likewise.
* grub-core/video/fb/video_fb.c: Introduce new functions:
grub_video_set_area_status, grub_video_get_area_status,
grub_video_set_region, grub_video_get_region.
* grub-core/video/bochs.c: Likewise.
* grub-core/video/capture.c: Likewise.
* grub-core/video/video.c: Likewise.
* grub-core/video/cirrus.c: Likewise.
* grub-core/video/efi_gop.c: Likewise.
* grub-core/video/efi_uga.c: Likewise.
* grub-core/video/emu/sdl.c: Likewise.
* grub-core/video/radeon_fuloong2e.c: Likewise.
* grub-core/video/sis315pro.c: Likewise.
* grub-core/video/sm712.c: Likewise.
* grub-core/video/i386/pc/vbe.c: Likewise.
* grub-core/video/i386/pc/vga.c: Likewise.
* grub-core/video/ieee1275.c: Likewise.
* grub-core/video/i386/coreboot/cbfb.c: Likewise.
* include/grub/video.h: Likewise.
* include/grub/video_fb.h: Likewise.
* include/grub/fbfill.h: Updated render_target structure.
grub_video_rect_t viewport, region, area
int area_offset_x, area_offset_y, area_enabled
* include/grub/gui.h: New helper function
grub_video_bounds_inside_region.
* docs/grub-dev.texi: Added information about new functions.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/mm.c (grub_real_malloc): Use AND rather than MOD
for alignment.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/lib/reed_solomon.c (grub_reed_solomon_recover): Add
missing attribute.
* grub-core/gdb/cstub.c (grub_gdb_trap): Likewise.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/misc.c (grub_divmod64): Don't fallback to
simple division on arm and ia64.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/arm/misc.S (__aeabi_unwind_cpp_pr0): Add dummy to
link with libgcc.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* include/grub/symbol.h (FUNCTION), (VARIABLE): Fix precedence logic.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* include/grub/symbol.h (FUNCTION), (VARIABLE) [__arm__]: Use % as
prefix symbol, not @.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* INSTALL: Add note about older gcc and clang.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* tests/util/grub-shell.in: Boot as hdd on ppc by default.
2013-11-08 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/loader/multiboot_mbi2.c (grub_multiboot_add_module): Fix
NULL pointer dereference.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/Makefile.am: Do not include libgcc.h when compiling with
clang.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/powerpc/dl.c: Add missing pragma to silence cast-align
warnings.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/net/net.c (grub_net_route_unregister): Remove unused
function.
* grub-core/loader/i386/xnu.c (hextoval): Likewise.
* grub-core/disk/geli.c (ascii2hex): Likewise.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* configure.ac: Run linker tests without -Werror.
Define TARGET_LDFLAGS_STATIC_LIBGCC and TARGET_LIBGCC.
Change all occurences of -static-libgcc resp -lgcc to
TARGET_LDFLAGS_STATIC_LIBGCC resp TARGET_LIBGCC.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* configure.ac: Don't add -no-itegrated-as on clang on non-x86.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
Allow compiling with clang (not really supported though).
* conf/Makefile.common (CFLAGS_PLATFORM): Don't add -mrtd -mregparm=3
unconditionally.
* configure.ac: Add -no-integrated-as when using clangfor asm files.
Add -mrtd -mregparm=3 on i386 when not using clang.
* grub-core/kern/misc.c (grub_memset): Add volatile when on clang.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/ieee1275/cmain.c: Add explicit attribute on asm
bindings.
* grub-core/lib/reed_solomon.c: Likewise.
* include/grub/i386/gdb.h: Likewise.
* include/grub/i386/pc/int.h: Likewise.
* include/grub/i386/pc/pxe.h: Likewise.
* include/grub/ieee1275/ieee1275.h: Likewise.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
Import libgcrypt 1.5.3.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* configure.ac: Don't add -Wcast-align on x86.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* configure.ac: Add -freg-struct-return on all platforms that
support it.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* acinclude.m4: Use -Werror on parameter tests.
* configure.ac: Likewise.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* acinclude.m4: Add missing TARGET_CCASFLAGS on asm tests.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* configure.ac: Check that -malign-loops works rather than assuming that
either -falign-loops or -malign-loops work.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* configure.ac: Remove -fnested-functions. We don't need it anymore.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* configure.ac: Prevent cflags leaking to subsequent tests by always
resetting cflags to target_cflags in target tests.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/parser.c (grub_parser_split_cmdline): Remove nested
function.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/misc.c (grub_vsnprintf_real): Remove nested functions.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/lib/arg.c (grub_arg_parse): Remove nested function.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/normal/cmdline.c (grub_cmdline_get):
Remove nested functions.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* tests/test_sha512sum.in: Make it work on emu.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/normal/charset.c (bidi_line_wrap): Eliminate nested
functions.
(grub_bidi_line_logical_to_visual): Likewise.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
Remove vestiges of -Wunsafe-loop-optimisations.
* conf/Makefile.common (CFLAGS_GNULIB): Remove
-Wno-unsafe-loop-optimisations.
* grub-core/commands/legacycfg.c: Remove -Wunsafe-loop-optimisations
pragma.
* grub-core/io/gzio.c: Likewise.
* grub-core/script/parser.y: Likewise.
* grub-core/script/yylex.l: Likewise.
* util/grub-mkfont.c: Likewise.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* util/grub-mkfont.c (process_cursive): Remove nested function.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* include/grub/misc.h (grub_dprintf): Use unnamed vararg.
(grub_boot_time): Likewise.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* include/grub/symbol.h (FUNCTION): Use @function rather than
"function".
(VARIABLE): Likewise.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/net/bootp.c (OFFSET_OF): Explicitly cast to grub_size_t.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/net/bootp.c (set_env_limn_ro): Make pointer const.
(parse_dhcp_vendor): Likewise.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* util/grub-mkimagexx.c (relocate_symbols): Remove unneeded brackets.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/gettext/gettext.c (main_context), (secondary_context):
Define after defining type and not before.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/fs/zfs/zfscrypt.c (grub_ccm_decrypt): Return right error
type.
(grub_gcm_decrypt): Likewise.
(algo_decrypt): Likewise.
(grub_zfs_decrypt_real): Transform error type.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/disk/geli.c (geli_rekey): Fix error return type.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/disk/usbms.c (grub_usbms_cbi_cmd): Fix error type.
(grub_usbms_cbi_reset): Likewise.
(grub_usbms_bo_reset): Likewise.
(grub_usbms_reset): Likewise.
(grub_usbms_attach): Likewise.
(grub_usbms_transfer_cbi): Likewise.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/io/lzopio.c (test_header): Simplify code and remove useless
"checksum = checksum;".
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/fs/reiserfs.c (grub_reiserfs_iterate_dir): Fix type of
entry_type.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/commands/legacycfg.c (grub_cmd_legacy_kernel): Fix
BIOS disk check.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/bus/usb/ehci.c (grub_ehci_restore_hw): Return right enum
type.
(grub_ehci_fini_hw): Likewise.
* grub-core/bus/usb/usbhub.c (grub_usb_add_hub): Likewise.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* include/grub/usb.h (grub_usb_controller_dev): Make portstatus
return grub_usb_err_t for cosistency. All users updated.
2013-11-07 Vladimir Serbinenko <phcoder@gmail.com>
* util/mkimage.c (SzAlloc): Use attribute unused rather than dubious
assigning to itself.
2013-11-05 Gustavo Luiz Duarte <gustavold@linux.vnet.ibm.com>
2013-11-05 Paulo Flabiano Smorigo <pfsmorigo@br.ibm.com>
Issue separate DNS queries for ipv4 and ipv6
Adding multiple questions on a single DNS query is not supportted by
most DNS servers. This patch issues two separate DNS queries
sequentially for ipv4 and then for ipv6.
Fixes: https://savannah.gnu.org/bugs/?39710
* grub-core/net/bootp.c (parse_dhcp_vendor): Add DNS option.
* grub-core/net/dns.c (grub_dns_qtype_id): New enum.
* (grub_net_dns_lookup): Now using separated dns packages.
* (grub_cmd_nslookup): Add error condition.
* (grub_cmd_list_dns): Print DNS option.
* (grub_cmd_add_dns): Add four parameters: --only-ipv4, --only-ipv6,
--prefer-ipv4, and --prefer-ipv6.
* include/grub/net.h (grub_dns_option_t): New enum.
* (grub_net_network_level_address): option added.
2013-11-05 Vladimir Testov <vladimir.testov@rosalab.ru>
* grub-core/video/fb/video_fb.c: Merge two blit functions
into one.
2013-11-05 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/term/terminfo.c: Add sequences for home and end.
2013-11-05 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/lib/legacy_parse.c: Fix handling of hercules and add
graphics console.
2013-11-05 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/video/i386/pc/vga.c: Fix double bufferring and
add mode 0x12.
2013-11-04 Vladimir Serbinenko <phcoder@gmail.com>
* docs/grub.texi (Vendor power-on keys): Add XPS M1330M based on old
e-mail by Per Öberg.
2013-11-04 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/commands/i386/nthibr.c (GRUB_MOD_INIT): Fix typo in command
name.
2013-11-04 Andrey Borzenkov <arvidjaar@gmail.com>
* configure.ac: Explicitly disable emusdl, emuusb and emupci on non-
emu platforms.
* grub-core/Makefile.core.def: Enable emupci and emuucb only for emu.
2013-11-04 Vladimir Serbinenko <phcoder@gmail.com>
* docs/grub.texi: Document usage of menuentry id.
2013-11-04 Vladimir Serbinenko <phcoder@gmail.com>
* docs/grub.texi: Add few mentions about EFI, debug and videoinfo.
2013-11-04 Peter Lustig <peter.lustig.7db@gmail.com>
* grub-core/commands/i386/nthibr.c: New command.
2013-11-04 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/tests/video_checksum.c: Add 2560x1440 mode to testing.
2013-11-04 Vladimir Serbinenko <phcoder@gmail.com>
* include/grub/term.h (grub_term_coordinate): Extend to 16-bit per
coordinate.
2013-11-04 Vladimir Serbinenko <phcoder@gmail.com>
Support GRUB_DISABLE_SUBMENU config.
Inspired by patch from Prarit Bhargava.
2013-11-03 Vladimir Serbinenko <phcoder@gmail.com>
* docs/grub.texi: Mention RSA support.
2013-11-03 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/commands/verify.c: Add RSA support.
2013-11-03 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/disk/ahci.c (grub_ahci_pciinit): Detect ATAPI devices.
* grub-core/disk/ata.c (grub_ata_identify): Use atapi_identify if
device is known to be ATAPI.
2013-11-03 Mike Frysinger <vapier>
* configure.ac: Don't add target-prefix.
2013-11-03 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/commands/loadenv.c (grub_cmd_save_env): Remove unset
variables.
2013-11-03 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/gettext/gettext.c (grub_gettext_init_ext): Ignore errors
if language is English.
2013-11-03 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/osdep/linux/getroot.c: Fix cast-align problems.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* configure.ac: Don't add -m32/-m64 on emu.
2013-11-02 neil
* grub-core/osdep/linux/blocklist.c: Include linux/types.h for some
broken linux headers.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* util/grub.d/30_os-prober.in: Add unhiding of partition if on msdos.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/lib/reed_solomon.c (grub_reed_solomon_recover): Don't do
Reed-Solomon recovery if more than half of redundancy info is 0.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* util/grub-mount.c: Handle symlinks to directories.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/fs/fshelp.c (find_file): Save ctx->next when calling
find_file recursively for symlink.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* tests/util/grub-shell.in: Copy themes.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* util/grub-mkimagexx.c (locate_sections): Reject mislinked images.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* configure.ac: Use 0x8000 for address instead of 8000.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/loader/sparc64/ieee1275/linux.c (get_physbase): Fix
signature.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/disk/efi/efidisk.c (grub_efidisk_readwrite): Remove unused
variable.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* configure.ac (TARGET_CFLAGS): Add -march=i386 on i386.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/fs/hfspluscomp.c (hfsplus_read_compressed_real): Call
file_progress_read_hook.
* grub-core/fs/ntfscomp.c (hfsplus_read_compressed_real): Likewise.
2013-11-02 Vladimir Serbinenko <phcoder@gmail.com>
* conf/Makefile.common (CFLAGS_PLATFORM): Remove poisoning of float
and double.
2013-11-01 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/fs/tar.c (grub_cpio_read): Add read_hook.
2013-11-01 Vladimir Serbinenko <phcoder@gmail.com>
Rewrite blocklist functions in order to get progress when
reading large extents and decrease amount of blocklist hook calls.
2013-11-01 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/term/serial.c (options), (grub_cmd_serial): Fix handling
of SI suffixes.
2013-11-01 Vladimir Serbinenko <phcoder@gmail.com>
Support --base-clock for serial command to handle weird cards with
non-standard base clock.
2013-11-01 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/fs/ext2.c (grub_ext2_read_symlink): Use memcpy rather
strncpy.
* grub-core/fs/jfs.c (grub_jfs_lookup_symlink): Likewise.
* grub-core/kern/misc.c (grub_strncpy): Move from here ...
* include/grub/misc.h (grub_strncpy): ... to here. Make inline.
* grub-core/net/net.c (grub_net_addr_to_str): Use COMPILE_TIME_ASSERT
+ strcpy rather than strncpy.
2013-11-01 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/fs/zfs/zfs.c (nvpair_name): Use correct type for size.
(check_pool_label): Likewise. Fixes overflow.
(nvlist_find_value): Fix comparison.
2013-11-01 Vladimir Serbinenko <phcoder@gmail.com>
* include/grub/misc.h (grub_strcat): Removed. All users changed to
more appropriate functions.
2013-11-01 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/efi/efi.c (grub_efi_get_filename): Avoid inefficient
realloc.
2013-11-01 Vladimir Serbinenko <phcoder@gmail.com>
* util/grub-mkrescue.in: Do not use UUID search on EFI.
2013-11-01 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/dl.c: Unify section-finding algorithm. Saves 30 bytes
on core size.
2013-10-30 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/mm.c (grub_realloc): Don't copy more data than we have.
2013-10-30 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/io/gzio.c (huft_build): Use zalloc for safety.
(initialize_tables): reset tl and td to NULL after freeing.
2013-10-28 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/loader/multiboot_mbi2.c: Implement network tag.
2013-10-28 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/loader/multiboot_mbi2.c: Add EFI memory map to the list
of supported tags.
2013-10-28 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/loader/multiboot_mbi2.c: Implement EFI memory map.
2013-10-28 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/loader/multiboot.c: Add support for multiboot kernels
quirks.
2013-10-28 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/loader/i386/linux.c (allocate_pages): Allocate at least
a page in protected space.
2013-10-28 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/loader/multiboot.c (grub_cmd_module): Don't attempt to
allocate space for zero-sized modules.
2013-10-28 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/loader/xnu_resume.c (grub_xnu_resume): Reject empty images.
2013-10-28 Francesco Lavra <francescolavra.fl@gmail.com>
* grub-core/lib/fdt.c: Fix miscellaneous bugs.
2013-10-28 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/lib/progress.c (grub_file_progress_hook_real): Add missing
safeguards. Fixes a crash with i386/pc/console.c.
2013-10-28 Vladimir Serbinenko <phcoder@gmail.com>
* include/grub/emu/hostdisk.h: Add proper declaration for grub_host_init
and grub_hostfs_init.
2013-10-28 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/emu/hostdisk.c (grub_util_check_file_presence): Use
windows method on other platforms without good stat as well.
2013-10-28 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/osdep/linux/getroot.c: Add new btrfs defines.
2013-10-28 Vladimir Serbinenko <phcoder@gmail.com>
Make / in btrfs refer to real root, not the default volume.
Modify mkrelpath to work even if device is mounted with subvolid option.
2013-10-28 Andrey Borzenkov <arvidjaar@gmail.com>
* Makefile.util.def: Add grub-core/kern/disk_common.c to library
extra_dist.
* grub-core/Makefile.core.def: Add kern/disk_common.c to disk module
extra_dist.
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* util/grub-mkfont.c (main): Show error message when FT_Set_Pixel_Sizes
fails.
2013-10-27 BVK Chaitanya <bvk.groups@gmail.com>
* docs/autoiso.cfg: New file.
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* configure.ac: Remove leftover COND_BUILD_GRUB_MKFONT and
COND_GRUB_PE2ELF conditions.
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/loader/i386/bsd.c (grub_cmd_openbsd): Accept "sd", "cd",
"vnd", "rd" and "fd" disks.
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
Move grub_disk_write out of kernel into disk.mod.
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/misc.c (grub_vsnprintf_real): Unify int and wchar
handling.
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/misc.c (grub_abort): Make static
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/misc.c (grub_vsnprintf_real): Don't attempt to
transform invalid unicode codepoints.
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/misc.c (grub_vsnprintf_real): Remove needless explicit
\0 checking.
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/lib/legacy_parse.c: Add support for "nd" disk.
2013-10-26 Vladimir Serbinenko <phcoder@gmail.com>
Consolidate cpuid code.
2013-10-26 Vladimir Serbinenko <phcoder@gmail.com>
Move cpuid code to cpuid.h and TSC code to tsc.c.
2013-10-26 Grégoire Sutre <gregoire.sutre@gmail.com>
* util/grub.d/00_header.in: Don't use LANG if it's not set.
2013-10-26 Grégoire Sutre <gregoire.sutre@gmail.com>
* util/grub-mkconfig.in: Replace $0 with $self.
* util/grub-reboot.in: Likewise.
* util/grub-set-default.in: Likewise.
2013-10-26 BVK Chaitanya <bvk.groups@gmail.com>
* docs/osdetect.cfg: New file.
2013-10-26 BVK Chaitanya <bvk.groups@gmail.com>
* tests/util/grub-shell.in: Add new --debug option.
2013-10-26 BVK Chaitanya <bvk.groups@gmail.com>
* tests/test_unset.in: New test.
2013-10-26 BVK Chaitanya <bvk.groups@gmail.com>
* tests/test_sha512sum.in: New test.
2013-10-26 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/fs/iso9660.c: Replace strncat with memcpy.
* include/grub/misc.h: Remove strncat.
* grub-core/lib/posix_wrap/string.h: Likewise.
2013-10-26 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/net/tftp.c: Retransmit ack when rereceiving old packet.
Try to handle more than 0xFFFF packets.
Reported by: Bernhard Übelacker <bernhardu>.
He also spotted few overflows in first version of this patch.
2013-10-26 Vladimir Serbinenko <phcoder@gmail.com>
* tests/date_unit_test.c: New test.
@@ -534,11 +1267,6 @@
currently used so this doesn't really have any effect.
Reported by: Douglas Ray <dougray>
2013-10-17 Vladimir Serbinenko <phcoder@gmail.com>
* util/grub-mkstandalone.in: Remove needless copying since we already
pass the files to tar.
2013-10-17 Vladimir Serbinenko <phcoder@gmail.com>
* autogen.sh: Don't set LC_CTYPE as it doesn't create problem for
+4
View File
@@ -12,6 +12,10 @@ you don't have any of them, please obtain and install them before
configuring the GRUB.
* GCC 4.1.3 or later
Note: older versions may work but support is limited
Note: clang 3.2 or later works for i386 and x86_64 targets but results in
much bigger binaries.
Note: clang 3.4 or later works for powerpc
* GNU Make
* GNU Bison 2.3 or later
* GNU gettext 0.17 or later
+14
View File
@@ -9,11 +9,13 @@ library = {
common = grub-core/kern/command.c;
common = grub-core/kern/device.c;
common = grub-core/kern/disk.c;
common = grub-core/lib/disk.c;
common = util/getroot.c;
common = grub-core/osdep/unix/getroot.c;
common = grub-core/osdep/getroot.c;
common = grub-core/osdep/devmapper/getroot.c;
common = grub-core/osdep/relpath.c;
extra_dist = grub-core/kern/disk_common.c;
extra_dist = grub-core/osdep/unix/relpath.c;
extra_dist = grub-core/osdep/aros/relpath.c;
extra_dist = grub-core/osdep/windows/relpath.c;
@@ -857,6 +859,18 @@ script = {
common = tests/grub_script_strcmp.in;
};
script = {
testcase;
name = test_sha512sum;
common = tests/test_sha512sum.in;
};
script = {
testcase;
name = test_unset;
common = tests/test_unset.in;
};
script = {
testcase;
name = grub_func_test;
+3 -3
View File
@@ -212,7 +212,7 @@ else
sed -e s/@ADDR32@/addr32\;/ < conftest.s.in > conftest.s
fi
if AC_TRY_COMMAND([${CC-cc} ${CFLAGS} -c conftest.s]) && test -s conftest.o; then
if AC_TRY_COMMAND([${CC-cc} ${TARGET_CCASFLAGS} ${CFLAGS} -c conftest.s]) && test -s conftest.o; then
grub_cv_i386_asm_addr32=yes
else
grub_cv_i386_asm_addr32=no
@@ -266,7 +266,7 @@ AC_CACHE_VAL(grub_cv_i386_asm_prefix_requirement,
l1: addr32 movb %al, l1
EOF
if AC_TRY_COMMAND([${CC-cc} ${CFLAGS} -c conftest.s]) && test -s conftest.o; then
if AC_TRY_COMMAND([${CC-cc} ${TARGET_CCASFLAGS} ${CFLAGS} -c conftest.s]) && test -s conftest.o; then
grub_cv_i386_asm_prefix_requirement=yes
else
grub_cv_i386_asm_prefix_requirement=no
@@ -391,7 +391,7 @@ AC_MSG_CHECKING([whether `$CC' accepts `-mstack-arg-probe'])
AC_LANG_CONFTEST([AC_LANG_SOURCE([[
void foo (void) { volatile char a[8]; a[3]; }
]])])
[if eval "$ac_compile -S -mstack-arg-probe -o conftest.s" 2> /dev/null; then]
[if eval "$ac_compile -S -mstack-arg-probe -Werror -o conftest.s" 2> /dev/null; then]
AC_MSG_RESULT([yes])
[# Should we clear up other files as well, having called `AC_LANG_CONFTEST'?
rm -f conftest.s
+4 -37
View File
@@ -6,18 +6,6 @@ export LC_COLLATE := C
unexport LC_ALL
# Platform specific options
if COND_i386_pc
CFLAGS_PLATFORM += -mrtd -mregparm=3 -freg-struct-return
endif
if COND_i386_qemu
CFLAGS_PLATFORM += -mrtd -mregparm=3 -freg-struct-return
endif
if COND_i386_coreboot
CFLAGS_PLATFORM += -mrtd -mregparm=3 -freg-struct-return
endif
if COND_i386_ieee1275
CFLAGS_PLATFORM += -mrtd -mregparm=3 -freg-struct-return
endif
if COND_mips_loongson
CFLAGS_PLATFORM += -mexplicit-relocs
CPPFLAGS_PLATFORM = -DUSE_ASCII_FALLBACK
@@ -37,11 +25,6 @@ endif
# Other options
if ! COND_emu
CFLAGS_PLATFORM += -Dfloat=__grub_poison
CFLAGS_PLATFORM += -Ddouble=__grub_poison
endif
CPPFLAGS_DEFAULT = -DGRUB_FILE=\"$(subst $(srcdir)/,,$<)\"
CPPFLAGS_DEFAULT += -I$(builddir)
CPPFLAGS_DEFAULT += -I$(srcdir)
@@ -54,26 +37,10 @@ CPPFLAGS_DEFAULT += -I$(top_srcdir)/grub-core/lib/libgcrypt-grub/src/
CCASFLAGS_DEFAULT = $(CPPFLAGS_DEFAULT) -DASM_FILE=1
BUILD_CPPFLAGS += $(CPPFLAGS_DEFAULT)
LDADD_KERNEL =
if ! COND_i386_pc
if ! COND_i386_efi
if ! COND_i386_qemu
if ! COND_i386_coreboot
if ! COND_i386_multiboot
if ! COND_i386_ieee1275
if ! COND_x86_64_efi
LDADD_KERNEL += -lgcc
endif
endif
endif
endif
endif
endif
endif
LDADD_KERNEL = $(TARGET_LIBGCC)
CFLAGS_KERNEL = $(CFLAGS_CPU) $(CFLAGS_PLATFORM) -ffreestanding
LDFLAGS_KERNEL = $(LDFLAGS_CPU) $(LDFLAGS_PLATFORM) -nostdlib $(TARGET_LDFLAGS_OLDMAGIC) -static-libgcc
LDFLAGS_KERNEL = $(LDFLAGS_CPU) $(LDFLAGS_PLATFORM) -nostdlib $(TARGET_LDFLAGS_OLDMAGIC) $(TARGET_LDFLAGS_STATIC_LIBGCC)
CPPFLAGS_KERNEL = $(CPPFLAGS_CPU) $(CPPFLAGS_PLATFORM) -DGRUB_KERNEL=1
CCASFLAGS_KERNEL = $(CCASFLAGS_CPU) $(CCASFLAGS_PLATFORM)
if COND_CYGWIN
@@ -107,13 +74,13 @@ 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-old-style-definition -Wno-unsafe-loop-optimizations
CFLAGS_GNULIB = -Wno-undef -Wno-sign-compare -Wno-unused -Wno-unused-parameter -Wno-redundant-decls -Wno-unreachable-code -Wno-conversion -Wno-old-style-definition
CPPFLAGS_GNULIB = -I$(top_builddir)/grub-core/gnulib -I$(top_srcdir)/grub-core/gnulib
CFLAGS_POSIX = -fno-builtin
CPPFLAGS_POSIX = -I$(top_srcdir)/grub-core/lib/posix_wrap
CFLAGS_GCRY = -Wno-error -Wno-missing-field-initializers -Wno-redundant-decls $(CFLAGS_POSIX)
CFLAGS_GCRY = -Wno-error -Wno-missing-field-initializers -Wno-redundant-decls -Wno-undef $(CFLAGS_POSIX)
CPPFLAGS_GCRY = -I$(top_srcdir)/grub-core/lib/libgcrypt_wrap $(CPPFLAGS_POSIX) -D_GCRYPT_IN_LIBGCRYPT=1 -I$(top_srcdir)/include/grub/gcrypt
CPPFLAGS_EFIEMU = -I$(top_srcdir)/grub-core/efiemu/runtime
+2
View File
@@ -6,6 +6,8 @@
#define __powerpc__ 1
#endif
#define GCRYPT_NO_DEPRECATED 1
/* Define to 1 to enable disk cache statistics. */
#define DISK_CACHE_STATS @DISK_CACHE_STATS@
#define BOOT_TIME_STATS @BOOT_TIME_STATS@
+148 -96
View File
@@ -41,7 +41,9 @@ AC_CONFIG_AUX_DIR([build-aux])
# Checks for host and target systems.
AC_CANONICAL_HOST
save_program_prefix="${program_prefix}"
AC_CANONICAL_TARGET
program_prefix="${save_program_prefix}"
AM_INIT_AUTOMAKE()
AC_PREREQ(2.60)
@@ -165,10 +167,12 @@ case "$target_cpu"-"$platform" in
*) AC_MSG_ERROR([platform "$platform" is not supported for target CPU "$target_cpu"]) ;;
esac
case "$target_cpu" in
i386 | powerpc) target_m32=1 ;;
x86_64 | sparc64) target_m64=1 ;;
esac
if test x$platform != xemu ; then
case "$target_cpu" in
i386 | powerpc) target_m32=1 ;;
x86_64 | sparc64) target_m64=1 ;;
esac
fi
case "$target_os" in
windows* | mingw32*) target_os=cygwin ;;
@@ -388,7 +392,7 @@ AC_SUBST([LIBUTIL])
AC_CACHE_CHECK([whether -Wtrampolines work], [grub_cv_host_cc_wtrampolines], [
SAVED_CFLAGS="$CFLAGS"
CFLAGS="$HOST_CFLAGS -Wtrampolines"
CFLAGS="$HOST_CFLAGS -Wtrampolines -Werror"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[#include <stdarg.h>
int va_arg_func (int fixed, va_list args);]], [[]])],
[grub_cv_host_cc_wtrampolines=yes],
@@ -470,27 +474,89 @@ AC_SUBST(TARGET_NMFLAGS_MINUS_P)
AC_SUBST(TARGET_NMFLAGS_DEFINED_ONLY)
# debug flags.
WARN_FLAGS="-Wall -W -Wshadow -Wold-style-definition -Wpointer-arith -Wundef -Wextra -Wattributes -Wcast-align -Wchar-subscripts -Wcomment -Wdeprecated-declarations -Wdisabled-optimization -Wdiv-by-zero -Wendif-labels -Wfloat-equal -Wformat-extra-args -Wformat-security -Wformat-y2k -Wimplicit -Wimplicit-function-declaration -Wimplicit-int -Winit-self -Wint-to-pointer-cast -Winvalid-pch -Wmain -Wmissing-braces -Wmissing-field-initializers -Wmissing-format-attribute -Wmultichar -Wnonnull -Woverflow -Wparentheses -Wpointer-arith -Wpointer-to-int-cast -Wreturn-type -Wsequence-point -Wshadow -Wsign-compare -Wstrict-aliasing -Wswitch -Wtrigraphs -Wundef -Wunknown-pragmas -Wunused -Wunused-function -Wunused-label -Wunused-parameter -Wunused-value -Wunused-variable -Wvariadic-macros -Wvolatile-register-var -Wwrite-strings -Wnested-externs -Wstrict-prototypes -Wpointer-sign"
HOST_CFLAGS="$HOST_CFLAGS $WARN_FLAGS"
WARN_FLAGS="-Wall -W -Wshadow -Wold-style-definition -Wpointer-arith -Wundef -Wextra -Wattributes -Wchar-subscripts -Wcomment -Wdeprecated-declarations -Wdisabled-optimization -Wdiv-by-zero -Wendif-labels -Wfloat-equal -Wformat-extra-args -Wformat-security -Wformat-y2k -Wimplicit -Wimplicit-function-declaration -Wimplicit-int -Winit-self -Wint-to-pointer-cast -Winvalid-pch -Wmain -Wmissing-braces -Wmissing-field-initializers -Wmissing-format-attribute -Wmultichar -Wnonnull -Woverflow -Wparentheses -Wpointer-arith -Wpointer-to-int-cast -Wreturn-type -Wsequence-point -Wshadow -Wsign-compare -Wstrict-aliasing -Wswitch -Wtrigraphs -Wundef -Wunknown-pragmas -Wunused -Wunused-function -Wunused-label -Wunused-parameter -Wunused-value -Wunused-variable -Wvariadic-macros -Wvolatile-register-var -Wwrite-strings -Wnested-externs -Wstrict-prototypes -Wpointer-sign"
HOST_CFLAGS="$HOST_CFLAGS $WARN_FLAGS -Wcast-align"
TARGET_CFLAGS="$TARGET_CFLAGS $WARN_FLAGS -g -Wredundant-decls -Wmissing-prototypes -Wmissing-declarations"
TARGET_CCASFLAGS="$TARGET_CCASFLAGS -g"
if test "x$target_cpu" != xi386 && test "x$target_cpu" != xx86_64; then
TARGET_CFLAGS="$TARGET_CFLAGS -Wcast-align"
fi
AC_CACHE_CHECK([if compiling with clang], [grub_cv_cc_target_clang]
[AC_COMPILE_IFELSE(
[AC_LANG_PROGRAM([], [[
#ifdef __clang__
#error "is clang"
#endif
]])],
[grub_cv_cc_target_clang=no], [grub_cv_cc_target_clang=yes])])
# clang doesn't support .code16
if test "x$grub_cv_cc_target_clang" = xyes && ( test "x$target_cpu" = xi386 || test "x$target_cpu" = xx86_64 ); then
TARGET_CCASFLAGS="$TARGET_CCASFLAGS -no-integrated-as"
fi
if test "x$target_cpu" = xi386 && test "x$platform" != xemu; then
TARGET_CFLAGS="$TARGET_CFLAGS -march=i386"
fi
if test "x$target_m32" = x1; then
# Force 32-bit mode.
TARGET_CFLAGS="$TARGET_CFLAGS -m32"
TARGET_CCASFLAGS="$TARGET_CCASFLAGS -m32"
TARGET_CPPFLAGS="$TARGET_CPPFLAGS -m32"
TARGET_LDFLAGS="$TARGET_LDFLAGS -m32"
TARGET_MODULE_FORMAT="elf32"
fi
if test "x$target_m64" = x1; then
# Force 64-bit mode.
TARGET_CFLAGS="$TARGET_CFLAGS -m64"
TARGET_CCASFLAGS="$TARGET_CCASFLAGS -m64"
TARGET_CPPFLAGS="$TARGET_CPPFLAGS -m64"
TARGET_LDFLAGS="$TARGET_LDFLAGS -m64"
TARGET_MODULE_FORMAT="elf64"
fi
if test "x$grub_cv_cc_target_clang" = xno && test "x$target_cpu" = xi386 && test "x$platform" != xemu && test "x$platform" != xefi; then
TARGET_CFLAGS="$TARGET_CFLAGS -mrtd -mregparm=3"
fi
# Force no alignment to save space on i386.
if test "x$target_cpu" = xi386; then
AC_CACHE_CHECK([whether -falign-loops works], [grub_cv_cc_falign_loop], [
CFLAGS="$CFLAGS -falign-loops=1"
CFLAGS="$TARGET_CFLAGS -falign-loops=1 -Werror"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[]], [[]])],
[grub_cv_cc_falign_loop=yes],
[grub_cv_cc_falign_loop=no])
])
AC_CACHE_CHECK([whether -malign-loops works], [grub_cv_cc_malign_loop], [
CFLAGS="$TARGET_CFLAGS -malign-loops=1 -Werror"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[]], [[]])],
[grub_cv_cc_malign_loop=yes],
[grub_cv_cc_malign_loop=no])
])
if test "x$grub_cv_cc_falign_loop" = xyes; then
TARGET_CFLAGS="$TARGET_CFLAGS -falign-jumps=1 -falign-loops=1 -falign-functions=1"
else
elif test "x$grub_cv_cc_malign_loop" = xyes; then
TARGET_CFLAGS="$TARGET_CFLAGS -malign-jumps=1 -malign-loops=1 -malign-functions=1"
fi
fi
AC_CACHE_CHECK([whether -freg-struct-return works], [grub_cv_cc_freg_struct_return], [
CFLAGS="$TARGET_CFLAGS -freg-struct-return -Werror"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[]], [[]])],
[grub_cv_cc_freg_struct_return=yes],
[grub_cv_cc_freg_struct_return=no])
])
if test "x$grub_cv_cc_freg_struct_return" = xyes; then
TARGET_CFLAGS="$TARGET_CFLAGS -freg-struct-return"
fi
if ( test "x$target_cpu" = xi386 || test "x$target_cpu" = xx86_64 ) && test "x$platform" != xemu; then
# Some toolchains enable these features by default, but they need
# registers that aren't set up properly in GRUB.
@@ -502,12 +568,10 @@ fi
# these and they just use up vital space. Restore the old compiler
# behaviour.
AC_CACHE_CHECK([whether -fno-dwarf2-cfi-asm works], [grub_cv_cc_fno_dwarf2_cfi_asm], [
SAVE_CFLAGS="$CFLAGS"
CFLAGS="$CFLAGS -fno-dwarf2-cfi-asm"
CFLAGS="$TARGET_CFLAGS -fno-dwarf2-cfi-asm"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[]], [[]])],
[grub_cv_cc_fno_dwarf2_cfi_asm=yes],
[grub_cv_cc_fno_dwarf2_cfi_asm=no])
CFLAGS="$SAVE_CFLAGS"
])
if test "x$grub_cv_cc_fno_dwarf2_cfi_asm" = xyes; then
@@ -516,7 +580,7 @@ fi
if test x"$target_os" = xcygwin; then
AC_CACHE_CHECK([whether option -fno-reorder-functions works], grub_cv_cc_no_reorder_functions, [
CFLAGS="$CFLAGS -fno-reorder-functions"
CFLAGS="$TARGET_CFLAGS -fno-reorder-functions"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[]], [[]])],
[grub_cv_cc_no_reorder_functions=yes],
[grub_cv_cc_no_reorder_functions=no])
@@ -532,12 +596,10 @@ fi
# these and they just use up vital space. Restore the old compiler
# behaviour.
AC_CACHE_CHECK([whether -fno-asynchronous-unwind-tables works], [grub_cv_cc_fno_asynchronous_unwind_tables], [
SAVE_CFLAGS="$CFLAGS"
CFLAGS="$CFLAGS -fno-dwarf2-cfi-asm"
CFLAGS="$TARGET_CFLAGS -fno-dwarf2-cfi-asm"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[]], [[]])],
[grub_cv_cc_fno_asynchronous_unwind_tables=yes],
[grub_cv_cc_fno_asynchronous_unwind_tables=no])
CFLAGS="$SAVE_CFLAGS"
])
if test "x$grub_cv_cc_fno_asynchronous_unwind_tables" = xyes; then
@@ -546,9 +608,6 @@ fi
grub_apple_target_cc
if test x$grub_cv_apple_target_cc = xyes ; then
TARGET_CPPFLAGS="$TARGET_CPPFLAGS -fnested-functions"
CFLAGS="$CFLAGS -fnested-functions"
TARGET_APPLE_CC=1
AC_CHECK_PROG([TARGET_OBJCONV], [objconv], [objconv], [])
if test "x$TARGET_OBJCONV" = x ; then
@@ -612,12 +671,10 @@ if test x"$platform" = xefi ; then
fi
if test x"$efiemu_excuse" = x ; then
AC_CACHE_CHECK([whether options required for efiemu work], grub_cv_cc_efiemu, [
SAVED_CFLAGS="$CFLAGS"
CFLAGS="$CFLAGS -m64 -mcmodel=large -mno-red-zone -nostdlib"
CFLAGS="$TARGET_CFLAGS -m64 -mcmodel=large -mno-red-zone -nostdlib"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[]], [[]])],
[grub_cv_cc_efiemu=yes],
[grub_cv_cc_efiemu=no])
CFLAGS="$SAVED_CFLAGS"
])
if test x$grub_cv_cc_efiemu = xno; then
efiemu_excuse="cannot compile with -m64 -mcmodel=large -mno-red-zone -nostdlib"
@@ -633,28 +690,10 @@ enable_efiemu=no
fi
AC_SUBST([enable_efiemu])
if test "x$target_m32" = x1; then
# Force 32-bit mode.
TARGET_CFLAGS="$TARGET_CFLAGS -m32"
TARGET_CCASFLAGS="$TARGET_CCASFLAGS -m32"
TARGET_CPPFLAGS="$TARGET_CPPFLAGS -m32"
TARGET_LDFLAGS="$TARGET_LDFLAGS -m32"
TARGET_MODULE_FORMAT="elf32"
fi
if test "x$target_m64" = x1; then
# Force 64-bit mode.
TARGET_CFLAGS="$TARGET_CFLAGS -m64"
TARGET_CCASFLAGS="$TARGET_CCASFLAGS -m64"
TARGET_CPPFLAGS="$TARGET_CPPFLAGS -m64"
TARGET_LDFLAGS="$TARGET_LDFLAGS -m64"
TARGET_MODULE_FORMAT="elf64"
fi
case "$target_os" in
cygwin)
;;
freebsd)
freebsd | kfreebsd*-gnu)
if test x"$target_cpu" = xi386; then
TARGET_LDFLAGS="$TARGET_LDFLAGS -Wl,-melf_i386_fbsd"
fi
@@ -691,8 +730,7 @@ esac
if test "$target_cpu" = x86_64; then
# Use large model to support 4G memory
AC_CACHE_CHECK([whether option -mcmodel=large works], grub_cv_cc_mcmodel, [
SAVED_CFLAGS=$CFLAGS
CFLAGS="$CFLAGS -m64 -mcmodel=large"
CFLAGS="$TARGET_CFLAGS -m64 -mcmodel=large"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[]], [[]])],
[grub_cv_cc_mcmodel=yes],
[grub_cv_cc_mcmodel=no])
@@ -707,7 +745,7 @@ fi
if test "$target_cpu"-"$platform" = x86_64-efi; then
# EFI writes to stack below %rsp, we must not use the red zone
AC_CACHE_CHECK([whether option -mno-red-zone works], grub_cv_cc_no_red_zone, [
CFLAGS="$CFLAGS -m64 -mno-red-zone"
CFLAGS="$TARGET_CFLAGS -m64 -mno-red-zone"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[]], [[]])],
[grub_cv_cc_no_red_zone=yes],
[grub_cv_cc_no_red_zone=no])
@@ -761,47 +799,6 @@ if test "$target_cpu" = arm; then
fi
fi
AC_ARG_ENABLE([werror],
[AS_HELP_STRING([--disable-werror],
[do not use -Werror when building GRUB])])
if test x"$enable_werror" != xno ; then
TARGET_CFLAGS="$TARGET_CFLAGS -Werror"
HOST_CFLAGS="$HOST_CFLAGS -Werror"
fi
TARGET_CPP="$TARGET_CC -E"
TARGET_CCAS=$TARGET_CC
GRUB_TARGET_CPU="${target_cpu}"
GRUB_PLATFORM="${platform}"
AC_SUBST(GRUB_TARGET_CPU)
AC_SUBST(GRUB_PLATFORM)
AC_SUBST(TARGET_OBJCONV)
AC_SUBST(TARGET_CPP)
AC_SUBST(TARGET_CCAS)
AC_SUBST(TARGET_OBJ2ELF)
AC_SUBST(TARGET_APPLE_CC)
AC_SUBST(TARGET_MODULE_FORMAT)
AC_SUBST(TARGET_CFLAGS)
AC_SUBST(TARGET_LDFLAGS)
AC_SUBST(TARGET_CPPFLAGS)
AC_SUBST(TARGET_CCASFLAGS)
AC_SUBST(TARGET_IMG_LDSCRIPT)
AC_SUBST(TARGET_IMG_LDFLAGS)
AC_SUBST(TARGET_IMG_CFLAGS)
AC_SUBST(TARGET_IMG_BASE_LDOPT)
AC_SUBST(HOST_CFLAGS)
AC_SUBST(HOST_LDFLAGS)
AC_SUBST(HOST_CPPFLAGS)
AC_SUBST(HOST_CCASFLAGS)
AC_SUBST(BUILD_LIBM)
# Set them to their new values for the tests below.
CC="$TARGET_CC"
if test "x$TARGET_APPLE_CC" = x1 ; then
@@ -810,17 +807,19 @@ else
CFLAGS="$TARGET_CFLAGS -nostdlib -Wl,--defsym,___main=0x8100 -Wno-error"
fi
CPPFLAGS="$TARGET_CPPFLAGS"
if test x$target_cpu = xi386 || test x$target_cpu = xx86_64 ; then
LIBS=
if test x$target_cpu = xi386 || test x$target_cpu = xx86_64 || test "x$grub_cv_cc_target_clang" = xyes ; then
TARGET_LIBGCC=
else
LIBS=-lgcc
TARGET_LIBGCC=-lgcc
fi
LIBS="$TARGET_LIBGCC"
grub_ASM_USCORE
if test x$grub_cv_asm_uscore = xyes; then
CFLAGS="$CFLAGS -Wl,--defsym,_abort=_main"
CFLAGS="$TARGET_CFLAGS -Wl,--defsym,_abort=_main"
else
CFLAGS="$CFLAGS -Wl,--defsym,abort=main"
CFLAGS="$TARGET_CFLAGS -Wl,--defsym,abort=main"
fi
# Check for libgcc symbols
@@ -843,7 +842,7 @@ if test "x$target_cpu" = xi386; then
if test "$platform" != emu && test "x$TARGET_APPLE_CC" != x1 ; then
if test ! -z "$TARGET_IMG_LDSCRIPT"; then
# Check symbols provided by linker script.
CFLAGS="$TARGET_CFLAGS -nostdlib ${TARGET_IMG_LDFLAGS_AC} ${TARGET_IMG_BASE_LDOPT},8000 -Wl,--defsym,___main=0x8100"
CFLAGS="$TARGET_CFLAGS -nostdlib ${TARGET_IMG_LDFLAGS_AC} ${TARGET_IMG_BASE_LDOPT},0x8000 -Wl,--defsym,___main=0x8100"
fi
grub_CHECK_BSS_START_SYMBOL
grub_CHECK_END_SYMBOL
@@ -871,13 +870,11 @@ fi
fi
AC_CACHE_CHECK([whether -Wtrampolines work], [grub_cv_cc_wtrampolines], [
SAVED_CFLAGS="$CFLAGS"
CFLAGS="$TARGET_CFLAGS -Wtrampolines"
CFLAGS="$TARGET_CFLAGS -Wtrampolines -Werror"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[#include <stdarg.h>
int va_arg_func (int fixed, va_list args);]], [[]])],
[grub_cv_cc_wtrampolines=yes],
[grub_cv_cc_wtrampolines=no])
CFLAGS="$SAVED_CFLAGS"
])
if test x"$grub_cv_cc_wtrampolines" = xyes ; then
@@ -1021,6 +1018,13 @@ fi
AC_SUBST([enable_grub_emu_sdl])
AC_SUBST([enable_grub_emu_usb])
AC_SUBST([enable_grub_emu_pci])
else
# Ignore --enable-emu-* if platform is not emu
enable_grub_emu_sdl=no
enable_grub_emu_usb=no
enable_grub_emu_pci=no
fi
AC_ARG_ENABLE([grub-mkfont],
@@ -1316,11 +1320,61 @@ AC_SUBST(PACKAGE)
AC_SUBST(VERSION)
AC_SUBST(NEED_REGISTER_FRAME_INFO)
AC_ARG_ENABLE([werror],
[AS_HELP_STRING([--disable-werror],
[do not use -Werror when building GRUB])])
if test x"$enable_werror" != xno ; then
TARGET_CFLAGS="$TARGET_CFLAGS -Werror"
HOST_CFLAGS="$HOST_CFLAGS -Werror"
fi
if test "x$grub_cv_cc_target_clang" = xno; then
TARGET_LDFLAGS_STATIC_LIBGCC="-static-libgcc"
else
TARGET_LDFLAGS_STATIC_LIBGCC=
fi
TARGET_CPP="$TARGET_CC -E"
TARGET_CCAS=$TARGET_CC
GRUB_TARGET_CPU="${target_cpu}"
GRUB_PLATFORM="${platform}"
AC_SUBST(GRUB_TARGET_CPU)
AC_SUBST(GRUB_PLATFORM)
AC_SUBST(TARGET_OBJCONV)
AC_SUBST(TARGET_LIBGCC)
AC_SUBST(TARGET_LDFLAGS_STATIC_LIBGCC)
AC_SUBST(TARGET_CPP)
AC_SUBST(TARGET_CCAS)
AC_SUBST(TARGET_OBJ2ELF)
AC_SUBST(TARGET_APPLE_CC)
AC_SUBST(TARGET_MODULE_FORMAT)
AC_SUBST(TARGET_CFLAGS)
AC_SUBST(TARGET_LDFLAGS)
AC_SUBST(TARGET_CPPFLAGS)
AC_SUBST(TARGET_CCASFLAGS)
AC_SUBST(TARGET_IMG_LDSCRIPT)
AC_SUBST(TARGET_IMG_LDFLAGS)
AC_SUBST(TARGET_IMG_CFLAGS)
AC_SUBST(TARGET_IMG_BASE_LDOPT)
AC_SUBST(HOST_CFLAGS)
AC_SUBST(HOST_LDFLAGS)
AC_SUBST(HOST_CPPFLAGS)
AC_SUBST(HOST_CCASFLAGS)
AC_SUBST(BUILD_LIBM)
#
# Automake conditionals
#
AM_CONDITIONAL([COND_emu], [test x$platform = xemu])
AM_CONDITIONAL([COND_clang], [test x$grub_cv_cc_target_clang = xyes])
AM_CONDITIONAL([COND_i386_pc], [test x$target_cpu = xi386 -a x$platform = xpc])
AM_CONDITIONAL([COND_i386_efi], [test x$target_cpu = xi386 -a x$platform = xefi])
AM_CONDITIONAL([COND_ia64_efi], [test x$target_cpu = xia64 -a x$platform = xefi])
@@ -1355,10 +1409,8 @@ AM_CONDITIONAL([COND_GRUB_EMU_USB], [test x$enable_grub_emu_usb = xyes])
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_BUILD_GRUB_MKFONT], [test x$enable_build_grub_mkfont = xyes])
AM_CONDITIONAL([COND_GRUB_MOUNT], [test x$enable_grub_mount = xyes])
AM_CONDITIONAL([COND_HAVE_FONT_SOURCE], [test x$FONT_SOURCE != x])
AM_CONDITIONAL([COND_GRUB_PE2ELF], [test x$TARGET_OBJ2ELF != x])
AM_CONDITIONAL([COND_APPLE_CC], [test x$TARGET_APPLE_CC = x1])
AM_CONDITIONAL([COND_ENABLE_EFIEMU], [test x$enable_efiemu = xyes])
AM_CONDITIONAL([COND_ENABLE_CACHE_STATS], [test x$DISK_CACHE_STATS = x1])
+244
View File
@@ -0,0 +1,244 @@
# Sample GRUB script to autodetect operating systems
#
# Copyright (C) 2010 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/>.
function pathname { regexp -s 2:"$2" '^(\(.*\))?(/.*)$' "$1"; }
function devname { regexp -s "$2" '^(\(.*\)).*$' "$1"; }
function loopback_iso_entry {
realdev="$1"
isopath="$2"
loopdev="$3"
if test -f /boot/grub/loopback.cfg; then
cfgpath=/boot/grub/loopback.cfg
elif test -f /grub/loopback.cfg; then
cfgpath=/grub/loopback.cfg
else
return 1;
fi
echo loopback.cfg $isopath: yes
menuentry "Boot GRUB Loopback Config from ${realdev}${isopath}" "$realdev" "$isopath" "$cfgpath" {
set device="$2"
set iso_path="$3"
set cfg_path="$4"
export iso_path
loopback loopdev_cfg "${device}${iso_path}"
set root=(loopdev_cfg)
configfile $cfg_path
loopback -d loopdev_cfg
}
return 0
}
function grml_iso_entry {
realdev="$1"
isopath="$2"
loopdev="$3"
result=1
for dir in /boot/grml /boot/grmlsmall /boot/grmlmedium; do
if ! test -f ${dir}/linux26 -a -f ${dir}/initrd.gz; then continue; fi
echo grml $isopath: yes
result=0
menuentry "GRML Linux from ${realdev}${isopath}" \
"$realdev" "$isopath" "$dir" {
set device="$2"
set isopath="$3"
set grmldir="$4"
loopback loopdev_grml "${device}${isopath}"
set root=(loopdev_grml)
linux $grmldir/linux26 findiso="$isopath" apm=power-off quiet \
boot=live nomce
initrd $grmldir/initrd.gz
loopback -d loopdev_grml
}
done
return $result
}
function pmagic_iso_entry {
realdev="$1"
isopath="$2"
loopdev="$3"
if ! test -f /pmagic/bzImage -a -f /pmagic/initramfs; then return 1; fi
echo pmagic $isopath: yes
menuentry "Parted Magic from ${realdev}${isopath}" "$realdev" "$isopath" {
set device="$2"
set isopath="$3"
loopback loopdev_pmagic "${device}${isopath}"
set root=(loopdev_pmagic)
linux /pmagic/bzImage iso_filename="$isopath" edd=off noapic \
load_ramdisk=1 prompt_ramdisk=0 rw sleep=10 loglevel=0 \
keymap=$langcode
initrd /pmagic/initramfs
loopback -d loopdev_pmagic
}
return 0
}
function sidux_iso_entry {
realdev="$1"
isopath="$2"
loopdev="$3"
result=1
for kernel in /boot/vmlinuz-*-sidux-*; do
if ! test -f "$kernel"; then continue; fi
regexp -s 1:v1 -s 2:v2 '/boot/vmlinuz-(.*)-sidux-(.*)' "$kernel"
initrd="/boot/initrd.img-$v1-sidux-$v2"
if ! test -f "$initrd"; then continue; fi
result=0
echo sidux $isopath: yes
menuentry "Sidux vmlinux-$v1-sidux-$v2 from ${realdev}${isopath}" "$realdev" "$isopath" "$kernel" "$initrd" {
set device="$2"
set isopath="$3"
set kernel="$4"
set initrd="$5"
loopback loopdev_sidux "${device}${isopath}"
set root=(loopdev_sidux)
linux $kernel fromiso=$isopath boot=fll quiet
initrd $initrd
loopback -d loopdev_sidux
}
done
return $result
}
function slax_iso_entry {
realdev="$1"
isopath="$2"
loopdev="$3"
if ! test -f /boot/vmlinuz -a -f /boot/initrd.gz; then return 1; fi
echo slax $isopath: yes
menuentry "Slax Linux from ${realdev}${isopath}" "$realdev" "$isopath" {
set device="$2"
set isopath="$3"
loopback loopdev_slax "${device}${isopath}"
set root=(loopdev_slax)
linux /boot/vmlinuz from=$isopath ramdisk_size=6666 root=/dev/ram0 rw
initrd /boot/initrd.gz
loopback -d loopdev_slax
}
return 0
}
function tinycore_iso_entry {
realpath="$1"
isopath="$2"
loopdev="$3"
if ! test -f /boot/bzImage -a -f /boot/tinycore.gz; then return 1; fi
echo tinycore $isopath: yes
menuentry "Tinycore Linux from ${realdev}${isopath}" "$realdev" "$isopath" {
set device="$2"
set isopath="$3"
loopback loopdev_tiny "${device}${isopath}"
set root=(loopdev_tiny)
linux /boot/bzImage
initrd /boot/tinycore.gz
loopback -d loopdev_tiny
}
return 0
}
function casper_iso_entry {
realpath="$1"
isopath="$2"
loopdev="$3"
if ! test -f /casper/vmlinuz; then return 1; fi
initrd=
for f in /casper/initrd.*z; do
if ! test -f "$f"; then continue; fi
pathname "$f" initrd
done
if test -z "$initrd"; then return 1; fi
echo casper $isopath: yes
menuentry "Casper based Linux from ${realdev}${isopath}" "$realdev" "$isopath" "$initrd" {
set device="$2"
set isopath="$3"
set initrd="$4"
loopback loopdev_casper "${device}${isopath}"
set root=(loopdev_casper)
linux /casper/vmlinuz boot=casper iso-scan/filename="$isopath" quiet splash noprompt keyb="$langcode" \
debian-installer/language="$langcode" console-setup/layoutcode?="$langcode" --
initrd $initrd
loopback -d loopdev_casper
}
return 0
}
function scan_isos {
isodirs="$1"
for dev in (*); do
for dir in $isodirs; do
for file in ${dev}${dir}/*.iso ${dev}${dir}/*.ISO; do
if ! test -f "$file"; then continue; fi
pathname $file isopath
if test -z "$dev" -o -z "$isopath"; then continue; fi
if ! loopback loopdev_scan "$file"; then continue; fi
saved_root=$root
set root=(loopdev_scan)
if loopback_iso_entry $dev $isopath (loopdev_scan); then true;
elif grml_iso_entry $dev $isopath (loopdev_scan); then true;
elif pmagic_iso_entry $dev $isopath (loopdev_scan); then true;
elif sidux_iso_entry $dev $isopath (loopdev_scan); then true;
elif slax_iso_entry $dev $isopath (loopdev_scan); then true;
elif tinycore_iso_entry $dev $isopath (loopdev_scan); then true;
elif casper_iso_entry $dev $isopath (loopdev_scan); then true;
else true; fi
set root=$saved_root
loopback -d loopdev_scan
done
done
done
return 0
}
# XXX Remove later
insmod serial
serial
terminal_output --append serial
# terminal_input --append serial
langcode="$lang"
insmod regexp
scan_isos /iso /boot/iso
+72
View File
@@ -1113,6 +1113,47 @@ struct grub_video_palette_data
Used to query indexed color palettes. If mode is RGB mode, colors will be copied from emulated palette data. In Indexed Color modes, palettes will be read from hardware. Color values will be converted to suit structure format. @code{start} will tell what hardware color index (or emulated color index) will be used as a source for first indice of @code{palette_data}, after that both hardware color index and @code{palette_data} index will be incremented until @code{count} number of colors have been read.
@end itemize
@subsection grub_video_set_area_status
@itemize
@item Prototype:
@example
grub_err_t
grub_video_set_area_status (grub_video_area_status_t area_status);
@end example
@example
enum grub_video_area_status_t
@{
GRUB_VIDEO_AREA_DISABLED,
GRUB_VIDEO_AREA_ENABLED
@};
@end example
@item Description:
Used to set area drawing mode for redrawing the specified region. Draw commands
are performed in the intersection of the viewport and the region called area.
Coordinates remain related to the viewport. If draw commands try to draw over
the area, they are clipped.
Set status to DISABLED if you need to draw everything.
Set status to ENABLED and region to the desired rectangle to redraw everything
inside the region leaving everything else intact.
Should be used for redrawing of active elements.
@end itemize
@subsection grub_video_get_area_status
@itemize
@item Prototype:
@example
grub_err_r
grub_video_get_area_status (grub_video_area_status_t *area_status);
@end example
@item Description:
Used to query the area status.
@end itemize
@subsection grub_video_set_viewport
@itemize
@item Prototype:
@@ -1139,6 +1180,37 @@ grub_video_get_viewport (unsigned int *x, unsigned int *y, unsigned int *width,
Used to query current viewport dimensions. Software developer can use this to choose best way to render contents of the viewport.
@end itemize
@subsection grub_video_set_region
@itemize
@item Prototype:
@example
grub_err_t
grub_video_set_region (unsigned int x, unsigned int y, unsigned int width, unsigned int height);
@end example
@item Description:
Used to specify the region of the screen which should be redrawn. Use absolute
values. When the region is set and area status is ENABLE all draw commands will
be performed inside the interseption of region and viewport named area.
If draw commands try to draw over viewport, they are clipped. If developer
requests larger than possible region, width and height will be clamped to fit
screen. Should be used for redrawing of active elements.
@end itemize
@subsection grub_video_get_region
@itemize
@item Prototype:
@example
grub_err_t
grub_video_get_region (unsigned int *x, unsigned int *y, unsigned int *width, unsigned int *height);
@end example
@item Description:
Used to query current region dimensions.
@end itemize
@subsection grub_video_map_color
@itemize
@item Prototype:
+80 -10
View File
@@ -701,6 +701,26 @@ you may run those commands directly to install GRUB, without using
with the internals of GRUB. Installing a boot loader on a running OS may be
extremely dangerous.
On EFI systems for fixed disk install you have to mount EFI System Partition.
If you mount it at @file{/boot/efi} then you don't need any special arguments:
@example
# @kbd{grub-install}
@end example
Otherwise you need to specify where your EFI System partition is mounted:
@example
# @kbd{grub-install --efi-directory=/mnt/efi}
@end example
For removable installs you have to use @option{--removable} and specify both
@option{--boot-directory} and @option{--efi-directory}:
@example
# @kbd{grub-install --efi-directory=/mnt/usb --boot-directory=/mnt/usb/boot --removable}
@end example
@node Making a GRUB bootable CD-ROM
@section Making a GRUB bootable CD-ROM
@@ -1234,14 +1254,14 @@ Valid keys in @file{/etc/default/grub} are as follows:
@item GRUB_DEFAULT
The default menu entry. This may be a number, in which case it identifies
the Nth entry in the generated menu counted from zero, or the title of a
menu entry, or the special string @samp{saved}. Using the title may be
menu entry, or the special string @samp{saved}. Using the id may be
useful if you want to set a menu entry as the default even though there may
be a variable number of entries before it.
For example, if you have:
@verbatim
menuentry 'Example GNU/Linux distribution' --class gnu-linux {
menuentry 'Example GNU/Linux distribution' --class gnu-linux --id example-gnu-linux {
...
}
@end verbatim
@@ -1249,9 +1269,13 @@ menuentry 'Example GNU/Linux distribution' --class gnu-linux {
then you can make this the default using:
@example
GRUB_DEFAULT='Example GNU/Linux distribution'
GRUB_DEFAULT=example-gnu-linux
@end example
Previously it was documented the way to use entry title. While this still
works it's not recommended since titles often contain unstable device names
and may be translated
If you set this to @samp{saved}, then the default menu entry will be that
saved by @samp{GRUB_SAVEDEFAULT}, @command{grub-set-default}, or
@command{grub-reboot}.
@@ -2447,6 +2471,8 @@ button. @samp{GRUB_BUTTON_CMOS_ADDRESS} is vendor-specific and partially
model-specific. Values known to the GRUB team are:
@table @key
@item Dell XPS M1330M
121:3
@item Dell XPS M1530
85:3
@item Dell Latitude E4300
@@ -3088,7 +3114,8 @@ to go beyond the current 16 colors.
This variable may be set to enable debugging output from various components
of GRUB. The value is a list of debug facility names separated by
whitespace or @samp{,}, or @samp{all} to enable all available debugging
output.
output. The facility names are the first argument to grub_dprintf. Consult
source for more details.
@node default
@@ -3096,7 +3123,21 @@ output.
If this variable is set, it identifies a menu entry that should be selected
by default, possibly after a timeout (@pxref{timeout}). The entry may be
identified by number or by title.
identified by number or by id.
For example, if you have:
@verbatim
menuentry 'Example GNU/Linux distribution' --class gnu-linux --id example-gnu-linux {
...
}
@end verbatim
then you can make this the default using:
@example
default=example-gnu-linux
@end example
If the entry is in a submenu, then it must be identified using the titles of
each of the submenus starting from the top level followed by the number or
@@ -3136,7 +3177,8 @@ If this variable is set, it sets the resolution used on the @samp{gfxterm}
graphical terminal. Note that you can only use modes which your graphics
card supports via VESA BIOS Extensions (VBE), so for example native LCD
panel resolutions may not be available. The default is @samp{auto}, which
selects a platform-specific default that should look reasonable.
selects a platform-specific default that should look reasonable. Supported
modes can be listed by @samp{videoinfo} command in GRUB.
The resolution may be specified as a sequence of one or more modes,
separated by commas (@samp{,}) or semicolons (@samp{;}); each will be tried
@@ -3680,6 +3722,8 @@ you forget a command, you can run the command @command{help}
* lsfonts:: List loaded fonts
* lsmod:: Show loaded modules
* md5sum:: Compute or check MD5 hash
* module:: Load module for multiboot kernel
* multiboot:: Load multiboot compliant kernel
* nativedisk:: Switch to native disk drivers
* normal:: Enter normal mode
* normal_exit:: Exit from normal mode
@@ -4369,7 +4413,6 @@ List loaded fonts.
Show list of loaded modules.
@end deffn
@node md5sum
@subsection md5sum
@@ -4378,6 +4421,34 @@ Alias for @code{hashsum --hash md5 arg @dots{}}. See command @command{hashsum}
(@pxref{hashsum}) for full description.
@end deffn
@node module
@subsection module
@deffn Command module [--nounzip] file [arguments]
Load a module for multiboot kernel image. The rest of the
line is passed verbatim as the module command line.
@end deffn
@node multiboot
@subsection multiboot
@deffn Command multiboot [--quirk-bad-kludge] [--quirk-modules-after-kernel] file @dots{}
Load a multiboot kernel image from @var{file}. The rest of the
line is passed verbatim as the @dfn{kernel command-line}. Any module must
be reloaded after using this command (@pxref{module}).
Some kernels have known problems. You need to specify --quirk-* for those.
--quirk-bad-kludge is a problem seen in several products that they include
loading kludge information with invalid data in ELF file. GRUB prior to 0.97
and some custom builds prefered ELF information while 0.97 and GRUB 2
use kludge. Use this option to ignore kludge.
Known affected systems: old Solaris, SkyOS.
--quirk-modules-after-kernel is needed for kernels which load at relatively
high address e.g. 16MiB mark and can't cope with modules stuffed between
1MiB mark and beginning of the kernel.
Known afftected systems: VMWare.
@end deffn
@node nativedisk
@subsection nativedisk
@@ -5340,9 +5411,8 @@ may halt or otherwise impact the boot process.
GRUB uses GPG-style detached signatures (meaning that a file
@file{foo.sig} will be produced when file @file{foo} is signed), and
currently supports the DSA signing algorithm. Both 2048-bit and
3072-bit keys are supported. A signing key can be generated as
follows:
currently supports the DSA and RSA signing algorithms. A signing key
can be generated as follows:
@example
gpg --gen-key
+325
View File
@@ -0,0 +1,325 @@
# Sample GRUB script to autodetect operating systems
#
# Copyright (C) 2010 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/>.
set saved_root=$root
function freebsd_ufs_variants {
set device=$1
set fstype=$2
set uuid=$3
menuentry "FreeBSD (on $fstype $device)" $device $uuid {
set root=$2
set uuid=$3
freebsd /boot/kernel/kernel
set FreeBSD.acpi_load=YES
set FreeBSD.hint.acpi.0.disabled=0
set FreeBSD.vfs.root.mountfrom=ufs:ufsid/$uuid
frebsd_loadenv /boot/device.hints
}
menuentry "FreeBSD (on $fstype $device) (single)" $device $uuid {
set root=$2
set uuid=$3
freebsd /boot/kernel/kernel --single
set FreeBSD.acpi_load=YES
set FreeBSD.hint.acpi.0.disabled=0
set FreeBSD.vfs.root.mountfrom=ufs:ufsid/$uuid
frebsd_loadenv /boot/device.hints
}
menuentry "FreeBSD (on $fstype $device) (verbose)" $device $uuid {
set root=$2
set uuid=$3
freebsd /boot/kernel/kernel --verbose
set FreeBSD.acpi_load=YES
set FreeBSD.hint.acpi.0.disabled=0
set FreeBSD.vfs.root.mountfrom=ufs:ufsid/$uuid
frebsd_loadenv /boot/device.hints
}
menuentry "FreeBSD (on $fstype $device) (without ACPI)" $device $uuid {
set root=$2
set uuid=$3
freebsd /boot/kernel/kernel --verbose
unset FreeBSD.acpi_load
set FreeBSD.hint.acpi.0.disabled=1
set FreeBSD.loader.acpi_disabled_by_user=1
set FreeBSD.vfs.root.mountfrom=ufs:ufsid/$uuid
frebsd_loadenv /boot/device.hints
}
menuentry "FreeBSD (on $fstype $device) (safe mode)" $device $uuid {
set root=$2
set uuid=$3
freebsd /boot/kernel/kernel --verbose
unset FreeBSD.acpi_load
set FreeBSD.hint.acpi.0.disabled=1
set FreeBSD.loader.acpi_disabled_by_user=1
set FreeBSD.hint.apic.0.disabled=1
set FreeBSD.hw.ata.ata_dma=0
set FreeBSD.hw.ata.atapi_dma=0
set FreeBSD.hw.ata.wc=0
set FreeBSD.hw.eisa_slots=0
set FreeBSD.hint.kbdmux.0.disabled=1
set FreeBSD.vfs.root.mountfrom=ufs:ufsid/$uuid
frebsd_loadenv /boot/device.hints
}
}
function freebsd_zfs_variants {
set device=$1
set fstype=zfs
menuentry "FreeBSD (on $fstype $device)" $device {
set root=$2
freebsd /@/boot/kernel/kernel
set FreeBSD.acpi_load=YES
set FreeBSD.hint.acpi.0.disabled=0
freebsd_module_elf /@/boot/kernel/opensolaris.ko
freebsd_module_elf /@/boot/kernel/zfs.ko
freebsd_module /@/boot/zfs/zpool.cache type=/boot/zfs/zpool.cache
probe -l -s name $root
set FreeBSD.vfs.root.mountfrom=zfs:$name
freebsd_loadenv /@/boot/device.hints
}
menuentry "FreeBSD (on $fstype $device) (single)" $device {
set root=$2
freebsd /@/boot/kernel/kernel --single
set FreeBSD.acpi_load=YES
set FreeBSD.hint.acpi.0.disabled=0
freebsd_module_elf /@/boot/kernel/opensolaris.ko
freebsd_module_elf /@/boot/kernel/zfs.ko
freebsd_module /@/boot/zfs/zpool.cache type=/boot/zfs/zpool.cache
probe -l -s name $root
set FreeBSD.vfs.root.mountfrom=zfs:$name
freebsd_loadenv /@/boot/device.hints
}
menuentry "FreeBSD (on $fstype $device) (verbose)" $device {
set root=$2
freebsd /@/boot/kernel/kernel --verbose
set FreeBSD.acpi_load=YES
set FreeBSD.hint.acpi.0.disabled=0
freebsd_module_elf /@/boot/kernel/opensolaris.ko
freebsd_module_elf /@/boot/kernel/zfs.ko
freebsd_module /@/boot/zfs/zpool.cache type=/boot/zfs/zpool.cache
probe -l -s name $root
set FreeBSD.vfs.root.mountfrom=zfs:$name
freebsd_loadenv /@/boot/device.hints
}
menuentry "FreeBSD (on $fstype $device) (without ACPI)" $device {
set root=$2
freebsd /@/boot/kernel/kernel --verbose
unset FreeBSD.acpi_load
set FreeBSD.hint.acpi.0.disabled=1
set FreeBSD.loader.acpi_disabled_by_user=1
freebsd_module_elf /@/boot/kernel/opensolaris.ko
freebsd_module_elf /@/boot/kernel/zfs.ko
freebsd_module /@/boot/zfs/zpool.cache type=/boot/zfs/zpool.cache
probe -l -s name $root
set FreeBSD.vfs.root.mountfrom=zfs:$name
freebsd_loadenv /@/boot/device.hints
}
menuentry "FreeBSD (on $fstype $device) (safe mode)" $device {
set root=$2
freebsd /@/boot/kernel/kernel --verbose
unset FreeBSD.acpi_load
set FreeBSD.hint.acpi.0.disabled=1
set FreeBSD.loader.acpi_disabled_by_user=1
set FreeBSD.hint.apic.0.disabled=1
set FreeBSD.hw.ata.ata_dma=0
set FreeBSD.hw.ata.atapi_dma=0
set FreeBSD.hw.ata.wc=0
set FreeBSD.hw.eisa_slots=0
set FreeBSD.hint.kbdmux.0.disabled=1
freebsd_module_elf /@/boot/kernel/opensolaris.ko
freebsd_module_elf /@/boot/kernel/zfs.ko
freebsd_module /@/boot/zfs/zpool.cache type=/boot/zfs/zpool.cache
probe -l -s name $root
set FreeBSD.vfs.root.mountfrom=zfs:$name
freebsd_loadenv /@/boot/device.hints
}
}
insmod regexp
for dev in (*); do
# $device: parenthesis removed from $dev
regexp -s device '\((.*)\)' $dev
# $fstype: filesystem type identified
probe -s fstype -f $dev
# uuid: filesystem UUID
probe -s uuid -u $dev
if test -f ($device)/bootmgr -a -f ($device)/boot/bcd; then
menuentry "Windows Vista bootmgr (on $device)" $device {
set root=$2
chainloader +1
}
elif test -f ($device)/ntldr -a \
-e ($device)/ntdetect.com -a -f ($device)/boot.ini; then
menuentry "Windows NT/2000/XP loader (on $device)" $device {
set root=$2
regexp -s devnum 'hd([0-9]+)' $root
if test "$devnum" != "0"; then
drivemap -s hd0 $root
fi
chainloader +1
}
elif test -f ($device)/windows/win.com; then
menuentry "Windows 98/ME (on $device)" $device {
set root=$2
regexp -s devnum 'hd([0-9]+)' $root
if test "$devnum" != "0"; then
drivemap -s hd0 $root
fi
chainloader +1
}
elif test -f ($device)/io.sys -a -f ($device)/command.com; then
menuentry "MS-DOS (on $device)" $device {
set root=$2
regexp -s devnum 'hd([0-9]+)' $root
if test "$devnum" != "0"; then
drivemap -s hd0 $root
fi
chainloader +1
}
elif test -f ($device)/kernel.sys; then
menuentry "FreeDOS (on $device)" $device {
set root=$2
regexp -s type '([fh])d[0-9]+' $root
regexp -s devnum '[fh]d([0-9]+)' $root
if test $type = 'h' -a "$devnum" != "0"; then
drivemap -s hd0 $root
fi
chainloader +1
}
elif test "$fstype" = ufs1 -o "$fstype" = ufs2 -a \
-e ($device)/boot/kernel/kernel -a \
-e ($device)/boot/device.hints; then
freebsd_ufs_variants $device $fstype $uuid
elif test "$fstype" = zfs -a \
-e ($device)/@/boot/kernel/kernel -a \
-e ($device)/@/boot/device.hints; then
freebsd_zfs_variants $device
elif test "$fstype" = hfsplus -a -f ($device)/mach_kernel; then
menuentry "Mac OS X/Darwin" $device $uuid {
set root=$2
set uuid=$3
insmod vbe
do_resume=0
if [ /var/vm/sleepimage -nt10 / ]; then
if xnu_resume /var/vm/sleepimage; then
do_resume=1
fi
fi
if [ $do_resume = 1 ]; then
xnu_uuid $uuid uuid
if [ -f /Extra/DSDT.aml ]; then
acpi -e /Extra/DSDT.aml
fi
xnu_kernel /mach_kernel boot-uuid=${uuid} rd=*uuid
if [ /System/Library/Extensions.mkext -nt /System/Library/Extensions ]; then
xnu_mkext /System/Library/Extensions.mkext
else
xnu_mkext /System/Library/Extensions
fi
if [ -f /Extra/Extensions.mkext ]; then
xnu_mkext /Extra/Extensions.mkext
fi
if [ -d /Extra/Extensions ]; then
xnu_kextdir /Extra/Extensions
fi
if [ -f /Extra/devtree.txt ]; then
xnu_devtree /Extra/devtree.txt
fi
if [ -f /Extra/splash.jpg ]; then
insmod jpeg
xnu_splash /Extra/splash.jpg
fi
if [ -f /Extra/splash.png ]; then
insmod png
xnu_splash /Extra/splash.png
fi
if [ -f /Extra/splash.tga ]; then
insmod tga
xnu_splash /Extra/splash.tga
fi
fi
}
else
set root=$device
for file in /boot/vmlinuz-* /boot/linux-*; do
if test -f $file; then
regexp -s version '/boot/vmlinuz-(.*)' $file
regexp -s version '/boot/linux-(.*)' $file
menuentry "Linux $file" $device $uuid $file $version {
set root=$2
set uuid=$3
set kernel=$4
set version=$5
linux $kernel root=UUID=$uuid ro
if test -f /boot/initrd-$version.img; then
initrd /boot/initrd-$version.img
elif test -f /boot/initrd.img-$version; then
initrd /boot/initrd.img-$version
elif test -f /boot/initrd-$version; then
initrd /boot/initrd-$version
fi
}
menuentry "Linux $file (single)" $device $uuid $file $version {
set root=$2
set uuid=$3
set kernel=$4
set version=$5
linux $kernel root=UUID=$uuid ro single
if test -f /boot/initrd-$version.img; then
initrd /boot/initrd-$version.img
elif test -f /boot/initrd.img-$version; then
initrd /boot/initrd.img-$version
elif test -f /boot/initrd-$version; then
initrd /boot/initrd-$version
fi
}
fi
done
fi
done
set root=$saved_root
+2
View File
@@ -82,7 +82,9 @@ KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/term.h
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/time.h
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/mm_private.h
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/net.h
if !COND_clang
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/libgcc.h
endif
KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/memory.h
if COND_i386_pc
+26 -8
View File
@@ -424,9 +424,9 @@ image = {
cppflags = '-I$(srcdir)/lib/posix_wrap -I$(srcdir)/lib/xzembed -DGRUB_EMBED_DECOMPRESSOR=1';
objcopyflags = '-O binary';
mips_ldflags = '-static-libgcc -Wl,-Ttext,$(TARGET_DECOMPRESSOR_LINK_ADDR)';
ldadd = '-lgcc';
cflags = '-Wno-unreachable-code -static-libgcc';
mips_ldflags = '$(TARGET_LDFLAGS_STATIC_LIBGCC) -Wl,-Ttext,$(TARGET_DECOMPRESSOR_LINK_ADDR)';
ldadd = '$(TARGET_LIBGCC)';
cflags = '-Wno-unreachable-code $(TARGET_LDFLAGS_STATIC_LIBGCC)';
enable = mips;
};
@@ -438,9 +438,9 @@ image = {
cppflags = '-DGRUB_EMBED_DECOMPRESSOR=1';
objcopyflags = '-O binary';
mips_ldflags = '-static-libgcc -Wl,-Ttext,$(TARGET_DECOMPRESSOR_LINK_ADDR)';
ldadd = '-lgcc';
cflags = '-static-libgcc';
mips_ldflags = '$(TARGET_LDFLAGS_STATIC_LIBGCC) -Wl,-Ttext,$(TARGET_DECOMPRESSOR_LINK_ADDR)';
ldadd = '$(TARGET_LIBGCC)';
cflags = '$(TARGET_LDFLAGS_STATIC_LIBGCC)';
enable = mips;
};
@@ -458,7 +458,7 @@ image = {
name = fwstart;
mips_loongson = boot/mips/loongson/fwstart.S;
objcopyflags = '-O binary';
ldflags = '-static-libgcc -lgcc -Wl,-N,-S,-Ttext,0xbfc00000,-Bstatic';
ldflags = '$(TARGET_LDFLAGS_STATIC_LIBGCC) $(TARGET_LIBGCC) -Wl,-N,-S,-Ttext,0xbfc00000,-Bstatic';
enable = mips_loongson;
};
@@ -466,10 +466,16 @@ image = {
name = fwstart_fuloong2f;
mips_loongson = boot/mips/loongson/fuloong2f.S;
objcopyflags = '-O binary';
ldflags = '-static-libgcc -lgcc -Wl,-N,-S,-Ttext,0xbfc00000,-Bstatic';
ldflags = '$(TARGET_LDFLAGS_STATIC_LIBGCC) $(TARGET_LIBGCC) -Wl,-N,-S,-Ttext,0xbfc00000,-Bstatic';
enable = mips_loongson;
};
module = {
name = disk;
common = lib/disk.c;
extra_dist = kern/disk_common.c;
};
module = {
name = trig;
common_nodist = trigtables.c;
@@ -506,6 +512,7 @@ module = {
module = {
name = emuusb;
common = bus/usb/usb.c;
enable = emu;
condition = COND_GRUB_EMU_USB;
};
@@ -575,6 +582,7 @@ module = {
common = bus/emu/pci.c;
common = commands/lspci.c;
enable = emu;
condition = COND_GRUB_EMU_PCI;
};
@@ -585,6 +593,11 @@ module = {
enable = mips_arc;
};
module = {
name = check_nt_hiberfil;
common = commands/i386/nthibr.c;
};
library = {
name = libgnulib.a;
common = gnulib/regex.c;
@@ -1861,6 +1874,11 @@ module = {
common = tests/setjmp_test.c;
};
module = {
name = div_test;
common = tests/div_test.c;
};
module = {
name = videotest_checksum;
common = tests/videotest_checksum.c;
+7 -8
View File
@@ -1677,7 +1677,7 @@ grub_ehci_hubports (grub_usb_controller_t dev)
return portinfo;
}
static grub_err_t
static grub_usb_err_t
grub_ehci_portstatus (grub_usb_controller_t dev,
unsigned int port, unsigned int enable)
{
@@ -1699,14 +1699,14 @@ grub_ehci_portstatus (grub_usb_controller_t dev,
endtime = grub_get_time_ms () + 1000;
while (grub_ehci_port_read (e, port) & GRUB_EHCI_PORT_ENABLED)
if (grub_get_time_ms () > endtime)
return grub_error (GRUB_ERR_IO, "portstatus: EHCI Timed out - disable");
return GRUB_USB_ERR_TIMEOUT;
if (!enable) /* We don't need reset port */
{
grub_dprintf ("ehci", "portstatus: Disabled.\n");
grub_dprintf ("ehci", "portstatus: end, status=0x%02x\n",
grub_ehci_port_read (e, port));
return GRUB_ERR_NONE;
return GRUB_USB_ERR_NONE;
}
grub_dprintf ("ehci", "portstatus: enable\n");
@@ -1724,8 +1724,7 @@ grub_ehci_portstatus (grub_usb_controller_t dev,
endtime = grub_get_time_ms () + 1000;
while (grub_ehci_port_read (e, port) & GRUB_EHCI_PORT_RESET)
if (grub_get_time_ms () > endtime)
return grub_error (GRUB_ERR_IO,
"portstatus: EHCI Timed out - reset port");
return GRUB_USB_ERR_TIMEOUT;
grub_boot_time ("Port %d reset", port);
/* Remember "we did the reset" - needed by detect_dev */
e->reset |= (1 << port);
@@ -1753,7 +1752,7 @@ grub_ehci_portstatus (grub_usb_controller_t dev,
grub_dprintf ("ehci", "portstatus: end, status=0x%02x\n",
grub_ehci_port_read (e, port));
return GRUB_ERR_NONE;
return GRUB_USB_ERR_NONE;
}
static grub_usb_speed_t
@@ -1888,7 +1887,7 @@ grub_ehci_restore_hw (void)
}
}
return GRUB_USB_ERR_NONE;
return GRUB_ERR_NONE;
}
static grub_err_t
@@ -1911,7 +1910,7 @@ grub_ehci_fini_hw (int noreturn __attribute__ ((unused)))
grub_ehci_reset (e);
}
return GRUB_USB_ERR_NONE;
return GRUB_ERR_NONE;
}
static struct grub_usb_controller_dev usb_controller = {
+6 -6
View File
@@ -1216,7 +1216,7 @@ grub_ohci_cancel_transfer (grub_usb_controller_t dev,
return GRUB_USB_ERR_NONE;
}
static grub_err_t
static grub_usb_err_t
grub_ohci_portstatus (grub_usb_controller_t dev,
unsigned int port, unsigned int enable)
{
@@ -1236,11 +1236,11 @@ grub_ohci_portstatus (grub_usb_controller_t dev,
while ((grub_ohci_readreg32 (o, GRUB_OHCI_REG_RHUBPORT + port)
& (1 << 1)))
if (grub_get_time_ms () > endtime)
return grub_error (GRUB_ERR_IO, "OHCI Timed out - disable");
return GRUB_USB_ERR_TIMEOUT;
grub_dprintf ("ohci", "end of portstatus=0x%02x\n",
grub_ohci_readreg32 (o, GRUB_OHCI_REG_RHUBPORT + port));
return GRUB_ERR_NONE;
return GRUB_USB_ERR_NONE;
}
/* OHCI does one reset signal 10ms long but USB spec.
@@ -1257,7 +1257,7 @@ grub_ohci_portstatus (grub_usb_controller_t dev,
while (! (grub_ohci_readreg32 (o, GRUB_OHCI_REG_RHUBPORT + port)
& GRUB_OHCI_SET_PORT_RESET_STATUS_CHANGE))
if (grub_get_time_ms () > endtime)
return grub_error (GRUB_ERR_IO, "OHCI Timed out - reset");
return GRUB_USB_ERR_TIMEOUT;
/* End the reset signaling - reset the reset status change */
grub_ohci_writereg32 (o, GRUB_OHCI_REG_RHUBPORT + port,
@@ -1275,7 +1275,7 @@ grub_ohci_portstatus (grub_usb_controller_t dev,
while (! (grub_ohci_readreg32 (o, GRUB_OHCI_REG_RHUBPORT + port)
& (1 << 1)))
if (grub_get_time_ms () > endtime)
return grub_error (GRUB_ERR_IO, "OHCI Timed out - enable");
return GRUB_USB_ERR_TIMEOUT;
/* Reset bit Connect Status Change */
grub_ohci_writereg32 (o, GRUB_OHCI_REG_RHUBPORT + port,
@@ -1287,7 +1287,7 @@ grub_ohci_portstatus (grub_usb_controller_t dev,
grub_dprintf ("ohci", "end of portstatus=0x%02x\n",
grub_ohci_readreg32 (o, GRUB_OHCI_REG_RHUBPORT + port));
return GRUB_ERR_NONE;
return GRUB_USB_ERR_NONE;
}
static grub_usb_speed_t
+4 -2
View File
@@ -91,11 +91,13 @@ real_config (struct grub_serial_port *port)
grub_usb_control_msg (port->usbdev, GRUB_USB_REQTYPE_VENDOR_OUT,
GRUB_FTDI_MODEM_CTRL,
GRUB_FTDI_MODEM_CTRL_DTRRTS, 0, 0, 0);
port->config.rtscts ? GRUB_FTDI_MODEM_CTRL_DTRRTS : 0,
0, 0, 0);
grub_usb_control_msg (port->usbdev, GRUB_USB_REQTYPE_VENDOR_OUT,
GRUB_FTDI_FLOW_CTRL,
GRUB_FTDI_FLOW_CTRL_DTRRTS, 0, 0, 0);
port->config.rtscts ? GRUB_FTDI_FLOW_CTRL_DTRRTS : 0,
0, 0, 0);
divisor = get_divisor (port->config.speed);
grub_usb_control_msg (port->usbdev, GRUB_USB_REQTYPE_VENDOR_OUT,
+1 -1
View File
@@ -125,7 +125,7 @@ real_config (struct grub_serial_port *port)
0x22, 3, 0, 0, 0);
grub_usb_control_msg (port->usbdev, GRUB_USB_REQTYPE_VENDOR_OUT,
1, 0, 0x61, 0, 0);
1, 0, port->config.rtscts ? 0x61 : 0, 0, 0);
port->configured = 1;
}
+6 -12
View File
@@ -189,11 +189,6 @@ grub_uhci_writereg32 (struct grub_uhci *u,
grub_outl (val, u->iobase + reg);
}
static grub_err_t
grub_uhci_portstatus (grub_usb_controller_t dev,
unsigned int port, unsigned int enable);
/* Iterate over all PCI devices. Determine if a device is an UHCI
controller. If this is the case, initialize it. */
static int
@@ -715,7 +710,7 @@ grub_uhci_iterate (grub_usb_controller_iterate_hook_t hook, void *hook_data)
return 0;
}
static grub_err_t
static grub_usb_err_t
grub_uhci_portstatus (grub_usb_controller_t dev,
unsigned int port, unsigned int enable)
{
@@ -733,8 +728,7 @@ grub_uhci_portstatus (grub_usb_controller_t dev,
else if (port == 1)
reg = GRUB_UHCI_REG_PORTSC2;
else
return grub_error (GRUB_ERR_OUT_OF_RANGE,
"UHCI Root Hub port does not exist");
return GRUB_USB_ERR_INTERNAL;
status = grub_uhci_readreg16 (u, reg);
grub_dprintf ("uhci", "detect=0x%02x\n", status);
@@ -747,11 +741,11 @@ grub_uhci_portstatus (grub_usb_controller_t dev,
endtime = grub_get_time_ms () + 1000;
while ((grub_uhci_readreg16 (u, reg) & (1 << 2)))
if (grub_get_time_ms () > endtime)
return grub_error (GRUB_ERR_IO, "UHCI Timed out - disable");
return GRUB_USB_ERR_TIMEOUT;
status = grub_uhci_readreg16 (u, reg);
grub_dprintf ("uhci", ">3detect=0x%02x\n", status);
return GRUB_ERR_NONE;
return GRUB_USB_ERR_NONE;
}
/* Reset the port. */
@@ -782,7 +776,7 @@ grub_uhci_portstatus (grub_usb_controller_t dev,
endtime = grub_get_time_ms () + 1000;
while (! ((status = grub_uhci_readreg16 (u, reg)) & (1 << 2)))
if (grub_get_time_ms () > endtime)
return grub_error (GRUB_ERR_IO, "UHCI Timed out - enable");
return GRUB_USB_ERR_TIMEOUT;
/* Reset recovery time */
grub_millisleep (10);
@@ -792,7 +786,7 @@ grub_uhci_portstatus (grub_usb_controller_t dev,
grub_dprintf ("uhci", ">3detect=0x%02x\n", status);
return GRUB_ERR_NONE;
return GRUB_USB_ERR_NONE;
}
static grub_usb_speed_t
+2 -2
View File
@@ -195,7 +195,7 @@ grub_usb_add_hub (grub_usb_device_t dev)
rescan = 1;
return GRUB_ERR_NONE;
return GRUB_USB_ERR_NONE;
}
static void
@@ -203,7 +203,7 @@ attach_root_port (struct grub_usb_hub *hub, int portno,
grub_usb_speed_t speed)
{
grub_usb_device_t dev;
grub_err_t err;
grub_usb_err_t err;
grub_boot_time ("After detect_dev");
+31 -7
View File
@@ -62,23 +62,47 @@ read_blocklist (grub_disk_addr_t sector, unsigned offset, unsigned length,
if (ctx->num_sectors > 0)
{
if (ctx->start_sector + ctx->num_sectors == sector
&& offset == 0 && length == GRUB_DISK_SECTOR_SIZE)
&& offset == 0 && length >= GRUB_DISK_SECTOR_SIZE)
{
ctx->num_sectors++;
return;
ctx->num_sectors += length >> GRUB_DISK_SECTOR_BITS;
sector += length >> GRUB_DISK_SECTOR_BITS;
length &= (GRUB_DISK_SECTOR_SIZE - 1);
}
if (!length)
return;
print_blocklist (ctx->start_sector, ctx->num_sectors, 0, 0, ctx);
ctx->num_sectors = 0;
}
if (offset == 0 && length == GRUB_DISK_SECTOR_SIZE)
if (offset)
{
ctx->start_sector = sector;
ctx->num_sectors++;
unsigned l = length + offset;
l &= (GRUB_DISK_SECTOR_SIZE - 1);
l -= offset;
print_blocklist (sector, 0, offset, l, ctx);
length -= l;
sector++;
offset = 0;
}
if (!length)
return;
if (length & (GRUB_DISK_SECTOR_SIZE - 1))
{
if (length >> GRUB_DISK_SECTOR_BITS)
{
print_blocklist (sector, length >> GRUB_DISK_SECTOR_BITS, 0, 0, ctx);
sector += length >> GRUB_DISK_SECTOR_BITS;
}
print_blocklist (sector, 0, 0, length & (GRUB_DISK_SECTOR_SIZE - 1), ctx);
}
else
print_blocklist (sector, 0, offset, length, ctx);
{
ctx->start_sector = sector;
ctx->num_sectors = length >> GRUB_DISK_SECTOR_BITS;
}
}
static grub_err_t
+3 -8
View File
@@ -29,11 +29,6 @@
GRUB_MOD_LICENSE ("GPLv3+");
#define cpuid(num,a,b,c,d) \
asm volatile ("xchgl %%ebx, %1; cpuid; xchgl %%ebx, %1" \
: "=a" (a), "=r" (b), "=c" (c), "=d" (d) \
: "0" (num))
static const struct grub_arg_option options[] =
{
/* TRANSLATORS: "(default)" at the end means that this option is used if
@@ -78,18 +73,18 @@ GRUB_MOD_INIT(cpuid)
goto done;
/* Check the highest input value for eax. */
cpuid (0, eax, ebx, ecx, edx);
grub_cpuid (0, eax, ebx, ecx, edx);
/* We only look at the first four characters. */
max_level = eax;
if (max_level == 0)
goto done;
cpuid (0x80000000, eax, ebx, ecx, edx);
grub_cpuid (0x80000000, eax, ebx, ecx, edx);
ext_level = eax;
if (ext_level < 0x80000000)
goto done;
cpuid (0x80000001, eax, ebx, ecx, edx);
grub_cpuid (0x80000001, eax, ebx, ecx, edx);
grub_cpuid_has_longmode = !!(edx & bit_LM);
done:
#endif
+79
View File
@@ -0,0 +1,79 @@
/* nthibr.c - tests whether an MS Windows system partition is hibernated */
/*
* GRUB -- GRand Unified Bootloader
* Copyright (C) 2013 Peter Lustig
* Copyright (C) 2013 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/types.h>
#include <grub/mm.h>
#include <grub/file.h>
#include <grub/misc.h>
#include <grub/dl.h>
#include <grub/command.h>
#include <grub/err.h>
#include <grub/i18n.h>
GRUB_MOD_LICENSE ("GPLv3+");
static grub_err_t
grub_cmd_nthibr (grub_command_t cmd __attribute__ ((unused)),
int argc, char **args)
{
grub_uint8_t hibr_file_magic[4];
grub_file_t hibr_file = 0;
if (argc != 1)
return grub_error (GRUB_ERR_BAD_ARGUMENT, N_("one argument expected"));
hibr_file = grub_file_open (args[0]);
if (!hibr_file)
return grub_errno;
/* Try to read magic number of 'hiberfil.sys' */
if (grub_file_read (hibr_file, hibr_file_magic,
sizeof (hibr_file_magic))
!= (grub_ssize_t) sizeof (hibr_file_magic))
{
if (!grub_errno)
grub_error (GRUB_ERR_TEST_FAILURE, "false");
goto exit;
}
if (!(grub_memcmp ("hibr", hibr_file_magic, sizeof (hibr_file_magic)) == 0
|| grub_memcmp ("HIBR", hibr_file_magic, sizeof (hibr_file_magic)) == 0))
grub_error (GRUB_ERR_TEST_FAILURE, "false");
exit:
grub_file_close (hibr_file);
return grub_errno;
}
static grub_command_t cmd;
GRUB_MOD_INIT (check_nt_hiberfil)
{
cmd = grub_register_command ("check_nt_hiberfil", grub_cmd_nthibr,
N_("FILE"),
N_("Test whether a hiberfil.sys is "
"in hibernated state."));
}
GRUB_MOD_FINI (check_nt_hiberfil)
{
grub_unregister_command (cmd);
}
+1 -3
View File
@@ -358,7 +358,7 @@ grub_cmd_legacy_kernel (struct grub_command *mycmd __attribute__ ((unused)),
dev = grub_device_open (0);
if (dev && dev->disk
&& dev->disk->dev->id == GRUB_DISK_DEVICE_BIOSDISK_ID
&& dev->disk->dev->id >= 0x80 && dev->disk->dev->id <= 0x90)
&& dev->disk->id >= 0x80 && dev->disk->id <= 0x90)
{
struct grub_partition *part = dev->disk->partition;
bsd_device = dev->disk->id - 0x80 - hdbias;
@@ -546,8 +546,6 @@ struct legacy_md5_password
grub_uint8_t hash[MD5_HASHLEN];
};
#pragma GCC diagnostic ignored "-Wunsafe-loop-optimizations"
static int
check_password_md5_real (const char *entered,
struct legacy_md5_password *pw)
+32 -7
View File
@@ -259,10 +259,28 @@ check_blocklists (grub_envblk_t envblk, struct blocklist *blocklists,
for (p = blocklists; p; p = p->next)
{
struct blocklist *q;
/* Check if any pair of blocks overlap. */
for (q = p->next; q; q = q->next)
{
/* Check if any pair of blocks overlap. */
if (p->sector == q->sector)
grub_disk_addr_t s1, s2;
grub_disk_addr_t e1, e2, t;
s1 = p->sector;
e1 = s1 + ((p->length + GRUB_DISK_SECTOR_SIZE - 1) >> GRUB_DISK_SECTOR_BITS);
s2 = q->sector;
e2 = s2 + ((q->length + GRUB_DISK_SECTOR_SIZE - 1) >> GRUB_DISK_SECTOR_BITS);
if (s2 > s1)
{
t = s2;
s2 = s1;
s1 = t;
t = e2;
e2 = e1;
e1 = t;
}
if (e1 > s2)
{
/* This might be actually valid, but it is unbelievable that
any filesystem makes such a silly allocation. */
@@ -286,9 +304,18 @@ check_blocklists (grub_envblk_t envblk, struct blocklist *blocklists,
part_start = grub_partition_get_start (disk->partition);
buf = grub_envblk_buffer (envblk);
char *blockbuf = NULL;
grub_size_t blockbuf_len = 0;
for (p = blocklists, index = 0; p; index += p->length, p = p->next)
{
char blockbuf[GRUB_DISK_SECTOR_SIZE];
if (p->length > blockbuf_len)
{
grub_free (blockbuf);
blockbuf_len = 2 * p->length;
blockbuf = grub_malloc (blockbuf_len);
if (!blockbuf)
return grub_errno;
}
if (grub_disk_read (disk, p->sector - part_start,
p->offset, p->length, blockbuf))
@@ -340,10 +367,6 @@ save_env_read_hook (grub_disk_addr_t sector, unsigned offset, unsigned length,
struct grub_cmd_save_env_ctx *ctx = data;
struct blocklist *block;
if (offset + length > GRUB_DISK_SECTOR_SIZE)
/* Seemingly a bug. */
return;
block = grub_malloc (sizeof (*block));
if (! block)
return;
@@ -409,6 +432,8 @@ grub_cmd_save_env (grub_extcmd_context_t ctxt, int argc, char **args)
goto fail;
}
}
else
grub_envblk_delete (envblk, args[0]);
argc--;
args++;
+5 -2
View File
@@ -35,10 +35,13 @@ GRUB_MOD_LICENSE ("GPLv3+");
static void
read_progress (grub_disk_addr_t sector __attribute__ ((unused)),
unsigned offset __attribute__ ((unused)),
unsigned len __attribute__ ((unused)),
unsigned len,
void *data __attribute__ ((unused)))
{
grub_xputs (".");
for (; len >= GRUB_DISK_SECTOR_SIZE; len -= GRUB_DISK_SECTOR_SIZE)
grub_xputs (".");
if (len)
grub_xputs (".");
grub_refresh ();
}
+67 -16
View File
@@ -145,16 +145,31 @@ const char *hashes[] = {
[0x0b] = "sha224"
};
struct gcry_pk_spec *grub_crypto_pk_dsa;
struct gcry_pk_spec *grub_crypto_pk_ecdsa;
struct gcry_pk_spec *grub_crypto_pk_rsa;
static int
dsa_pad (gcry_mpi_t *hmpi, grub_uint8_t *hval,
const gcry_md_spec_t *hash, struct grub_public_subkey *sk);
static int
rsa_pad (gcry_mpi_t *hmpi, grub_uint8_t *hval,
const gcry_md_spec_t *hash, struct grub_public_subkey *sk);
struct
{
const char *name;
grub_size_t nmpisig;
grub_size_t nmpipub;
struct gcry_pk_spec **algo;
int (*pad) (gcry_mpi_t *hmpi, grub_uint8_t *hval,
const gcry_md_spec_t *hash, struct grub_public_subkey *sk);
const char *module;
} pkalgos[] =
{
[1] = { "rsa", 1, 2 },
[3] = { "rsa", 1, 2 },
[17] = { "dsa", 2, 4 },
[1] = { "rsa", 1, 2, &grub_crypto_pk_rsa, rsa_pad, "gcry_rsa" },
[3] = { "rsa", 1, 2, &grub_crypto_pk_rsa, rsa_pad, "gcry_rsa" },
[17] = { "dsa", 2, 4, &grub_crypto_pk_dsa, dsa_pad, "gcry_dsa" },
};
struct grub_public_key
@@ -351,6 +366,51 @@ grub_crypto_pk_locate_subkey_in_trustdb (grub_uint64_t keyid)
return 0;
}
static int
dsa_pad (gcry_mpi_t *hmpi, grub_uint8_t *hval,
const gcry_md_spec_t *hash, struct grub_public_subkey *sk)
{
unsigned nbits = gcry_mpi_get_nbits (sk->mpis[1]);
grub_dprintf ("crypt", "must be %u bits got %d bits\n", nbits,
(int)(8 * hash->mdlen));
return gcry_mpi_scan (hmpi, GCRYMPI_FMT_USG, hval,
nbits / 8 < (unsigned) hash->mdlen ? nbits / 8
: (unsigned) hash->mdlen, 0);
}
static int
rsa_pad (gcry_mpi_t *hmpi, grub_uint8_t *hval,
const gcry_md_spec_t *hash, struct grub_public_subkey *sk)
{
grub_size_t tlen, emlen, fflen;
grub_uint8_t *em, *emptr;
unsigned nbits = gcry_mpi_get_nbits (sk->mpis[0]);
int ret;
tlen = hash->mdlen + hash->asnlen;
emlen = (nbits + 7) / 8;
if (emlen < tlen + 11)
return 1;
em = grub_malloc (emlen);
if (!em)
return 1;
em[0] = 0x00;
em[1] = 0x01;
fflen = emlen - tlen - 3;
for (emptr = em + 2; emptr < em + 2 + fflen; emptr++)
*emptr = 0xff;
*emptr++ = 0x00;
grub_memcpy (emptr, hash->asnoid, hash->asnlen);
emptr += hash->asnlen;
grub_memcpy (emptr, hval, hash->mdlen);
ret = gcry_mpi_scan (hmpi, GCRYMPI_FMT_USG, em, emlen, 0);
grub_free (em);
return ret;
}
static grub_err_t
grub_verify_signature_real (char *buf, grub_size_t size,
grub_file_t f, grub_file_t sig,
@@ -532,17 +592,11 @@ grub_verify_signature_real (char *buf, grub_size_t size,
/* TRANSLATORS: %08x is 32-bit key id. */
return grub_error (GRUB_ERR_BAD_SIGNATURE, N_("public key %08x not found"), keyid);
unsigned nbits = gcry_mpi_get_nbits (sk->mpis[1]);
grub_dprintf ("crypt", "must be %u bits got %d bits\n", nbits,
(int)(8 * hash->mdlen));
if (gcry_mpi_scan (&hmpi, GCRYMPI_FMT_USG, hval,
nbits / 8 < (unsigned) hash->mdlen ? nbits / 8
: (unsigned) hash->mdlen, 0))
if (pkalgos[pk].pad (&hmpi, hval, hash, sk))
return grub_error (GRUB_ERR_BAD_SIGNATURE, N_("bad signature"));
if (!grub_crypto_pk_dsa)
return grub_error (GRUB_ERR_BAD_SIGNATURE, N_("module `%s' isn't loaded"), "gcry_dsa");
if (grub_crypto_pk_dsa->verify (0, hmpi, mpis, sk->mpis, 0, 0))
if (!*pkalgos[pk].algo)
return grub_error (GRUB_ERR_BAD_SIGNATURE, N_("module `%s' isn't loaded"), pkalgos[pk].module);
if ((*pkalgos[pk].algo)->verify (0, hmpi, mpis, sk->mpis, 0, 0))
return grub_error (GRUB_ERR_BAD_SIGNATURE, N_("bad signature"));
}
@@ -803,9 +857,6 @@ struct grub_fs pseudo_fs =
.read = pseudo_read
};
struct gcry_pk_spec *grub_crypto_pk_dsa;
struct gcry_pk_spec *grub_crypto_pk_ecdsa;
struct gcry_pk_spec *grub_crypto_pk_rsa;
static grub_extcmd_t cmd, cmd_trust;
static grub_command_t cmd_distrust, cmd_list;
+6
View File
@@ -133,6 +133,7 @@ struct grub_ahci_device
volatile struct grub_ahci_cmd_table *command_table;
struct grub_pci_dma_chunk *rfis;
int present;
int atapi;
};
static grub_err_t
@@ -616,6 +617,10 @@ grub_ahci_pciinit (grub_pci_device_t dev,
grub_dma_free (failed_adevs[i]->rfis);
}
for (i = 0; i < nports; i++)
if (adevs[i] && (adevs[i]->hba->ports[adevs[i]->port].sig >> 16) == 0xeb14)
adevs[i]->atapi = 1;
for (i = 0; i < nports; i++)
if (adevs[i])
{
@@ -1075,6 +1080,7 @@ grub_ahci_open (int id, int devnum, struct grub_ata *ata)
ata->data = dev;
ata->dma = 1;
ata->atapi = dev->atapi;
ata->maxbuffer = GRUB_AHCI_PRDT_MAX_CHUNK_LENGTH;
ata->present = &dev->present;
+13 -9
View File
@@ -108,6 +108,9 @@ grub_ata_identify (struct grub_ata *dev)
grub_uint16_t *info16;
grub_err_t err;
if (dev->atapi)
return grub_atapi_identify (dev);
info64 = grub_malloc (GRUB_DISK_SECTOR_SIZE);
info32 = (grub_uint32_t *) info64;
info16 = (grub_uint16_t *) info64;
@@ -129,7 +132,7 @@ grub_ata_identify (struct grub_ata *dev)
grub_free (info16);
grub_errno = GRUB_ERR_NONE;
if ((sts & (GRUB_ATA_STATUS_BUSY | GRUB_ATA_STATUS_DRQ
| GRUB_ATA_STATUS_ERR)) == GRUB_ATA_STATUS_ERR
| GRUB_ATA_STATUS_ERR)) == GRUB_ATA_STATUS_ERR
&& (parms.taskfile.error & 0x04 /* ABRT */))
/* Device without ATA IDENTIFY, try ATAPI. */
return grub_atapi_identify (dev);
@@ -285,7 +288,6 @@ grub_ata_readwrite (grub_disk_t disk, grub_disk_addr_t sector,
if (addressing == GRUB_ATA_LBA48 && ((sector + size) >> 28) != 0)
{
batch = 65536;
if (ata->dma)
{
cmd = GRUB_ATA_CMD_READ_SECTORS_DMA_EXT;
@@ -301,10 +303,6 @@ grub_ata_readwrite (grub_disk_t disk, grub_disk_addr_t sector,
{
if (addressing == GRUB_ATA_LBA48)
addressing = GRUB_ATA_LBA;
if (addressing != GRUB_ATA_CHS)
batch = 256;
else
batch = 1;
if (ata->dma)
{
cmd = GRUB_ATA_CMD_READ_SECTORS_DMA;
@@ -317,8 +315,10 @@ grub_ata_readwrite (grub_disk_t disk, grub_disk_addr_t sector,
}
}
if (batch > (ata->maxbuffer >> ata->log_sector_size))
batch = (ata->maxbuffer >> ata->log_sector_size);
if (addressing != GRUB_ATA_CHS)
batch = 256;
else
batch = 1;
while (nsectors < size)
{
@@ -366,7 +366,7 @@ grub_ata_real_open (int id, int bus)
struct grub_ata *ata;
grub_ata_dev_t p;
ata = grub_malloc (sizeof (*ata));
ata = grub_zalloc (sizeof (*ata));
if (!ata)
return NULL;
for (p = grub_ata_dev_list; p; p = p->next)
@@ -464,6 +464,10 @@ grub_ata_open (const char *name, grub_disk_t disk)
return grub_error (GRUB_ERR_UNKNOWN_DEVICE, "not an ATA harddisk");
disk->total_sectors = ata->size;
disk->max_agglomerate = (ata->maxbuffer >> (GRUB_DISK_CACHE_BITS + GRUB_DISK_SECTOR_BITS));
if (disk->max_agglomerate > (256U >> (GRUB_DISK_CACHE_BITS + GRUB_DISK_SECTOR_BITS - ata->log_sector_size)))
disk->max_agglomerate = (256U >> (GRUB_DISK_CACHE_BITS + GRUB_DISK_SECTOR_BITS - ata->log_sector_size));
disk->log_sector_size = ata->log_sector_size;
disk->id = grub_make_scsi_id (id, bus, 0);
+11 -4
View File
@@ -517,6 +517,7 @@ grub_cryptodisk_open (const char *name, grub_disk_t disk)
disk->data = dev;
disk->total_sectors = dev->total_length;
disk->max_agglomerate = GRUB_DISK_MAX_MAX_AGGLOMERATE;
disk->id = dev->id;
dev->ref++;
return GRUB_ERR_NONE;
@@ -631,10 +632,16 @@ grub_cryptodisk_write (grub_disk_t disk, grub_disk_addr_t sector,
return grub_crypto_gcry_error (gcry_err);
}
err = grub_disk_write (dev->source_disk,
(sector << (disk->log_sector_size
- GRUB_DISK_SECTOR_BITS)) + dev->offset,
0, size << disk->log_sector_size, tmp);
/* Since ->write was called so disk.mod is loaded but be paranoid */
if (grub_disk_write_weak)
err = grub_disk_write_weak (dev->source_disk,
(sector << (disk->log_sector_size
- GRUB_DISK_SECTOR_BITS))
+ dev->offset,
0, size << disk->log_sector_size, tmp);
else
err = grub_error (GRUB_ERR_BUG, "disk.mod not loaded");
grub_free (tmp);
return err;
}
+1
View File
@@ -445,6 +445,7 @@ grub_diskfilter_open (const char *name, grub_disk_t disk)
disk->data = lv;
disk->total_sectors = lv->size;
disk->max_agglomerate = GRUB_DISK_MAX_MAX_AGGLOMERATE;
return 0;
}
+7 -20
View File
@@ -518,6 +518,8 @@ grub_efidisk_open (const char *name, struct grub_disk *disk)
grub_dprintf ("efidisk", "m = %p, last block = %llx, block size = %x\n",
m, (unsigned long long) m->last_block, m->block_size);
disk->total_sectors = m->last_block + 1;
/* Don't increase this value due to bug in some EFI. */
disk->max_agglomerate = 0xa0000 >> (GRUB_DISK_CACHE_BITS + GRUB_DISK_SECTOR_BITS);
if (m->block_size & (m->block_size - 1) || !m->block_size)
return grub_error (GRUB_ERR_IO, "invalid sector size %d",
m->block_size);
@@ -542,32 +544,17 @@ static grub_efi_status_t
grub_efidisk_readwrite (struct grub_disk *disk, grub_disk_addr_t sector,
grub_size_t size, char *buf, int wr)
{
/* For now, use the disk io interface rather than the block io's. */
struct grub_efidisk_data *d;
grub_efi_block_io_t *bio;
grub_efi_status_t status;
d = disk->data;
bio = d->block_io;
while (size > 0)
{
grub_size_t len;
len = 0x500;
if (len > size)
len = size;
status = efi_call_5 ((wr ? bio->write_blocks : bio->read_blocks), bio,
bio->media->media_id,
(grub_efi_uint64_t) sector,
(grub_efi_uintn_t) len << disk->log_sector_size,
buf);
size -= len;
buf += len << disk->log_sector_size;
sector += len;
if (status != GRUB_EFI_SUCCESS)
return status;
}
return GRUB_EFI_SUCCESS;
return efi_call_5 ((wr ? bio->write_blocks : bio->read_blocks), bio,
bio->media->media_id,
(grub_efi_uint64_t) sector,
(grub_efi_uintn_t) size << disk->log_sector_size,
buf);
}
static grub_err_t
+1 -13
View File
@@ -153,24 +153,12 @@ geli_rekey (struct grub_cryptodisk *dev, grub_uint64_t zoneno)
gcry_err = grub_crypto_hmac_buffer (dev->hash, dev->rekey_key, 64,
&tohash, sizeof (tohash), key);
if (gcry_err)
return grub_crypto_gcry_error (gcry_err);
return gcry_err;
return grub_cryptodisk_setkey (dev, (grub_uint8_t *) key,
dev->rekey_derived_size);
}
static inline int
ascii2hex (char c)
{
if (c >= '0' && c <= '9')
return c - '0';
if (c >= 'a' && c <= 'f')
return c - 'a' + 10;
if (c >= 'A' && c <= 'F')
return c - 'A' + 10;
return 0;
}
static inline gcry_err_code_t
make_uuid (const struct grub_geli_phdr *header,
char *uuid)
+4
View File
@@ -20,9 +20,13 @@
/* When using the disk, make a reference to this module. Otherwise
the user will end up with a useless module :-). */
#include <config.h>
#include <config-util.h>
#include <grub/dl.h>
#include <grub/disk.h>
#include <grub/misc.h>
#include <grub/emu/hostdisk.h>
int grub_disk_host_i_want_a_reference;
+3 -4
View File
@@ -424,6 +424,9 @@ grub_biosdisk_open (const char *name, grub_disk_t disk)
}
disk->total_sectors = total_sectors;
/* Limit the max to 0x7f because of Phoenix EDD. */
disk->max_agglomerate = 0x7f >> GRUB_DISK_CACHE_BITS;
disk->data = data;
return GRUB_ERR_NONE;
@@ -548,10 +551,6 @@ get_safe_sectors (grub_disk_t disk, grub_disk_addr_t sector)
size = sectors - offset;
/* Limit the max to 0x7f because of Phoenix EDD. */
if (size > ((0x7fU << GRUB_DISK_SECTOR_BITS) >> disk->log_sector_size))
size = ((0x7fU << GRUB_DISK_SECTOR_BITS) >> disk->log_sector_size);
return size;
}
+4
View File
@@ -167,6 +167,10 @@ grub_loopback_open (const char *name, grub_disk_t disk)
/ GRUB_DISK_SECTOR_SIZE);
else
disk->total_sectors = GRUB_DISK_SIZE_UNKNOWN;
/* Avoid reading more than 512M. */
disk->max_agglomerate = 1 << (29 - GRUB_DISK_SECTOR_BITS
- GRUB_DISK_CACHE_BITS);
disk->id = (unsigned long) dev;
disk->data = dev;
+1
View File
@@ -46,6 +46,7 @@ grub_memdisk_open (const char *name, grub_disk_t disk)
return grub_error (GRUB_ERR_UNKNOWN_DEVICE, "not a memdisk");
disk->total_sectors = memdisk_size / GRUB_DISK_SECTOR_SIZE;
disk->max_agglomerate = GRUB_DISK_MAX_MAX_AGGLOMERATE;
disk->id = (unsigned long) "mdsk";
return GRUB_ERR_NONE;
+41 -60
View File
@@ -606,6 +606,13 @@ grub_scsi_open (const char *name, grub_disk_t disk)
}
disk->total_sectors = scsi->last_block + 1;
/* PATA doesn't support more than 32K reads.
Not sure about AHCI and USB. If it's confirmed that either of
them can do bigger reads reliably this value can be moved to 'scsi'
structure. */
disk->max_agglomerate = 32768 >> (GRUB_DISK_SECTOR_BITS
+ GRUB_DISK_CACHE_BITS);
if (scsi->blocksize & (scsi->blocksize - 1) || !scsi->blocksize)
{
grub_free (scsi);
@@ -647,40 +654,27 @@ grub_scsi_read (grub_disk_t disk, grub_disk_addr_t sector,
scsi = disk->data;
while (size)
grub_err_t err;
/* Depending on the type, select a read function. */
switch (scsi->devtype)
{
/* PATA doesn't support more than 32K reads.
Not sure about AHCI and USB. If it's confirmed that either of
them can do bigger reads reliably this value can be moved to 'scsi'
structure. */
grub_size_t len = 32768 >> disk->log_sector_size;
grub_err_t err;
if (len > size)
len = size;
/* Depending on the type, select a read function. */
switch (scsi->devtype)
{
case grub_scsi_devtype_direct:
if (sector >> 32)
err = grub_scsi_read16 (disk, sector, len, buf);
else
err = grub_scsi_read10 (disk, sector, len, buf);
if (err)
return err;
break;
case grub_scsi_devtype_direct:
if (sector >> 32)
err = grub_scsi_read16 (disk, sector, size, buf);
else
err = grub_scsi_read10 (disk, sector, size, buf);
if (err)
return err;
break;
case grub_scsi_devtype_cdrom:
if (sector >> 32)
err = grub_scsi_read16 (disk, sector, len, buf);
else
err = grub_scsi_read12 (disk, sector, len, buf);
if (err)
return err;
break;
}
size -= len;
sector += len;
buf += len << disk->log_sector_size;
case grub_scsi_devtype_cdrom:
if (sector >> 32)
err = grub_scsi_read16 (disk, sector, size, buf);
else
err = grub_scsi_read12 (disk, sector, size, buf);
if (err)
return err;
break;
}
return GRUB_ERR_NONE;
@@ -718,10 +712,10 @@ grub_scsi_read (grub_disk_t disk, grub_disk_addr_t sector,
}
static grub_err_t
grub_scsi_write (grub_disk_t disk __attribute((unused)),
grub_disk_addr_t sector __attribute((unused)),
grub_size_t size __attribute((unused)),
const char *buf __attribute((unused)))
grub_scsi_write (grub_disk_t disk,
grub_disk_addr_t sector,
grub_size_t size,
const char *buf)
{
grub_scsi_t scsi;
@@ -730,31 +724,18 @@ grub_scsi_write (grub_disk_t disk __attribute((unused)),
if (scsi->devtype == grub_scsi_devtype_cdrom)
return grub_error (GRUB_ERR_IO, N_("cannot write to CD-ROM"));
while (size)
grub_err_t err;
/* Depending on the type, select a read function. */
switch (scsi->devtype)
{
/* PATA doesn't support more than 32K reads.
Not sure about AHCI and USB. If it's confirmed that either of
them can do bigger reads reliably this value can be moved to 'scsi'
structure. */
grub_size_t len = 32768 >> disk->log_sector_size;
grub_err_t err;
if (len > size)
len = size;
/* Depending on the type, select a read function. */
switch (scsi->devtype)
{
case grub_scsi_devtype_direct:
if (sector >> 32)
err = grub_scsi_write16 (disk, sector, len, buf);
else
err = grub_scsi_write10 (disk, sector, len, buf);
if (err)
return err;
break;
}
size -= len;
sector += len;
buf += len << disk->log_sector_size;
case grub_scsi_devtype_direct:
if (sector >> 32)
err = grub_scsi_write16 (disk, sector, size, buf);
else
err = grub_scsi_write10 (disk, sector, size, buf);
if (err)
return err;
break;
}
return GRUB_ERR_NONE;
+10 -11
View File
@@ -76,7 +76,7 @@ typedef struct grub_usbms_dev *grub_usbms_dev_t;
static grub_usbms_dev_t grub_usbms_devices[MAX_USBMS_DEVICES];
static int first_available_slot = 0;
static grub_err_t
static grub_usb_err_t
grub_usbms_cbi_cmd (grub_usb_device_t dev, int interface,
grub_uint8_t *cbicb)
{
@@ -86,7 +86,7 @@ grub_usbms_cbi_cmd (grub_usb_device_t dev, int interface,
GRUB_USBMS_CBI_CMD_SIZE, (char*)cbicb);
}
static grub_err_t
static grub_usb_err_t
grub_usbms_cbi_reset (grub_usb_device_t dev, int interface)
{
/* Prepare array with Command Block Reset (=CBR) */
@@ -108,17 +108,13 @@ grub_usbms_cbi_reset (grub_usb_device_t dev, int interface)
return grub_usbms_cbi_cmd (dev, interface, (grub_uint8_t *)&cbicb);
}
static grub_err_t
static grub_usb_err_t
grub_usbms_bo_reset (grub_usb_device_t dev, int interface)
{
grub_usb_err_t u;
u = grub_usb_control_msg (dev, 0x21, 255, 0, interface, 0, 0);
if (u)
return grub_error (GRUB_ERR_IO, "USB error %d", u);
return GRUB_ERR_NONE;
return grub_usb_control_msg (dev, 0x21, 255, 0, interface, 0, 0);
}
static grub_err_t
static grub_usb_err_t
grub_usbms_reset (grub_usbms_dev_t dev)
{
if (dev->protocol == GRUB_USBMS_PROTOCOL_BULK)
@@ -149,7 +145,7 @@ grub_usbms_attach (grub_usb_device_t usbdev, int configno, int interfno)
int j;
grub_uint8_t luns = 0;
unsigned curnum;
grub_usb_err_t err = GRUB_ERR_NONE;
grub_usb_err_t err = GRUB_USB_ERR_NONE;
grub_boot_time ("Attaching USB mass storage");
@@ -572,7 +568,10 @@ grub_usbms_transfer_cbi (struct grub_scsi *scsi, grub_size_t cmdsize, char *cmd,
}
}
return err;
if (err)
return grub_error (GRUB_ERR_IO, "USB error %d", err);
return GRUB_ERR_NONE;
}
+2 -34
View File
@@ -18,42 +18,10 @@
#include <grub/efiemu/efiemu.h>
#include <grub/command.h>
#define cpuid(num,a,b,c,d) \
asm volatile ("xchgl %%ebx, %1; cpuid; xchgl %%ebx, %1" \
: "=a" (a), "=r" (b), "=c" (c), "=d" (d) \
: "0" (num))
#define bit_LM (1 << 29)
#include <grub/i386/cpuid.h>
const char *
grub_efiemu_get_default_core_name (void)
{
unsigned int eax, ebx, ecx, edx;
unsigned int max_level;
unsigned int ext_level;
/* See if we can use cpuid. */
asm volatile ("pushfl; pushfl; popl %0; movl %0,%1; xorl %2,%0;"
"pushl %0; popfl; pushfl; popl %0; popfl"
: "=&r" (eax), "=&r" (ebx)
: "i" (0x00200000));
if (((eax ^ ebx) & 0x00200000) == 0)
return "efiemu32.o";
/* Check the highest input value for eax. */
cpuid (0, eax, ebx, ecx, edx);
/* We only look at the first four characters. */
max_level = eax;
if (max_level == 0)
return "efiemu32.o";
cpuid (0x80000000, eax, ebx, ecx, edx);
ext_level = eax;
if (ext_level < 0x80000000)
return "efiemu32.o";
cpuid (0x80000001, eax, ebx, ecx, edx);
return (edx & bit_LM) ? "efiemu64.o" : "efiemu32.o";
return grub_cpuid_has_longmode ? "efiemu64.o" : "efiemu32.o";
}
+4 -2
View File
@@ -67,6 +67,7 @@ handle_symlink (struct grub_archelp_data *data,
grub_size_t prefixlen;
char *rest;
char *linktarget;
grub_size_t linktarget_len;
*restart = 0;
@@ -96,7 +97,8 @@ handle_symlink (struct grub_archelp_data *data,
return grub_errno;
if (linktarget[0] == '\0')
return GRUB_ERR_NONE;
target = grub_malloc (grub_strlen (linktarget) + grub_strlen (*name) + 2);
linktarget_len = grub_strlen (linktarget);
target = grub_malloc (linktarget_len + grub_strlen (*name) + 2);
if (!target)
return grub_errno;
@@ -121,7 +123,7 @@ handle_symlink (struct grub_archelp_data *data,
grub_memcpy (target, *name, prefixlen);
target[prefixlen-1] = '/';
}
grub_strcat (target, rest);
grub_strcpy (target + prefixlen + linktarget_len, rest);
grub_dprintf ("archelp", "symlink redirected %s to %s\n",
*name, target);
grub_free (*name);
+56 -66
View File
@@ -1,7 +1,7 @@
/* btrfs.c - B-tree file system. */
/*
* GRUB -- GRand Unified Bootloader
* Copyright (C) 2010 Free Software Foundation, Inc.
* Copyright (C) 2010,2011,2012,2013 Free Software Foundation, Inc.
*
* GRUB is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -28,6 +28,7 @@
#include <grub/deflate.h>
#include <minilzo.h>
#include <grub/i18n.h>
#include <grub/btrfs.h>
GRUB_MOD_LICENSE ("GPLv3+");
@@ -106,24 +107,6 @@ struct grub_btrfs_data
struct grub_btrfs_extent_data *extent;
};
enum
{
GRUB_BTRFS_ITEM_TYPE_INODE_ITEM = 0x01,
GRUB_BTRFS_ITEM_TYPE_INODE_REF = 0x0c,
GRUB_BTRFS_ITEM_TYPE_DIR_ITEM = 0x54,
GRUB_BTRFS_ITEM_TYPE_EXTENT_ITEM = 0x6c,
GRUB_BTRFS_ITEM_TYPE_ROOT_ITEM = 0x84,
GRUB_BTRFS_ITEM_TYPE_DEVICE = 0xd8,
GRUB_BTRFS_ITEM_TYPE_CHUNK = 0xe4
};
struct grub_btrfs_key
{
grub_uint64_t object_id;
grub_uint8_t type;
grub_uint64_t offset;
} __attribute__ ((packed));
struct grub_btrfs_chunk_item
{
grub_uint64_t size;
@@ -188,13 +171,6 @@ struct grub_btrfs_leaf_descriptor
} *data;
};
struct grub_btrfs_root_item
{
grub_uint8_t dummy[0xb0];
grub_uint64_t tree;
grub_uint64_t inode;
};
struct grub_btrfs_time
{
grub_int64_t sec;
@@ -1196,6 +1172,40 @@ grub_btrfs_extent_read (struct grub_btrfs_data *data,
return pos - pos0;
}
static grub_err_t
get_root (struct grub_btrfs_data *data, struct grub_btrfs_key *key,
grub_uint64_t *tree, grub_uint8_t *type)
{
grub_err_t err;
grub_disk_addr_t elemaddr;
grub_size_t elemsize;
struct grub_btrfs_key key_out, key_in;
struct grub_btrfs_root_item ri;
key_in.object_id = GRUB_BTRFS_ROOT_VOL_OBJECTID;
key_in.offset = 0;
key_in.type = GRUB_BTRFS_ITEM_TYPE_ROOT_ITEM;
err = lower_bound (data, &key_in, &key_out,
data->sblock.root_tree,
&elemaddr, &elemsize, NULL, 0);
if (err)
return err;
if (key_in.object_id != key_out.object_id
|| key_in.type != key_out.type
|| key_in.offset != key_out.offset)
return grub_error (GRUB_ERR_BAD_FS, "no root");
err = grub_btrfs_read_logical (data, elemaddr, &ri,
sizeof (ri), 0);
if (err)
return err;
key->type = GRUB_BTRFS_ITEM_TYPE_DIR_ITEM;
key->offset = 0;
key->object_id = grub_cpu_to_le64_compile_time (GRUB_BTRFS_OBJECT_ID_CHUNK);
*tree = ri.tree;
*type = GRUB_BTRFS_DIR_ITEM_TYPE_DIRECTORY;
return GRUB_ERR_NONE;
}
static grub_err_t
find_path (struct grub_btrfs_data *data,
const char *path, struct grub_btrfs_key *key,
@@ -1208,42 +1218,31 @@ find_path (struct grub_btrfs_data *data,
grub_size_t allocated = 0;
struct grub_btrfs_dir_item *direl = NULL;
struct grub_btrfs_key key_out;
int skip_default;
const char *ctoken;
grub_size_t ctokenlen;
char *path_alloc = NULL;
char *origpath = NULL;
unsigned symlinks_max = 32;
*type = GRUB_BTRFS_DIR_ITEM_TYPE_DIRECTORY;
*tree = data->sblock.root_tree;
key->object_id = data->sblock.root_dir_objectid;
key->type = GRUB_BTRFS_ITEM_TYPE_DIR_ITEM;
key->offset = 0;
skip_default = 1;
err = get_root (data, key, tree, type);
if (err)
return err;
origpath = grub_strdup (path);
if (!origpath)
return grub_errno;
while (1)
{
if (!skip_default)
{
while (path[0] == '/')
path++;
if (!path[0])
break;
slash = grub_strchr (path, '/');
if (!slash)
slash = path + grub_strlen (path);
ctoken = path;
ctokenlen = slash - path;
}
else
{
ctoken = "default";
ctokenlen = sizeof ("default") - 1;
}
while (path[0] == '/')
path++;
if (!path[0])
break;
slash = grub_strchr (path, '/');
if (!slash)
slash = path + grub_strlen (path);
ctoken = path;
ctokenlen = slash - path;
if (*type != GRUB_BTRFS_DIR_ITEM_TYPE_DIRECTORY)
{
@@ -1254,10 +1253,8 @@ find_path (struct grub_btrfs_data *data,
if (ctokenlen == 1 && ctoken[0] == '.')
{
if (!skip_default)
path = slash;
skip_default = 0;
continue;
path = slash;
continue;
}
if (ctokenlen == 2 && ctoken[0] == '.' && ctoken[1] == '.')
{
@@ -1287,9 +1284,7 @@ find_path (struct grub_btrfs_data *data,
*type = GRUB_BTRFS_DIR_ITEM_TYPE_DIRECTORY;
key->object_id = key_out.offset;
if (!skip_default)
path = slash;
skip_default = 0;
path = slash;
continue;
}
@@ -1359,9 +1354,7 @@ find_path (struct grub_btrfs_data *data,
return err;
}
if (!skip_default)
path = slash;
skip_default = 0;
path = slash;
if (cdirel->type == GRUB_BTRFS_DIR_ITEM_TYPE_SYMLINK)
{
struct grub_btrfs_inode inode;
@@ -1411,12 +1404,9 @@ find_path (struct grub_btrfs_data *data,
path = path_alloc = tmp;
if (path[0] == '/')
{
*type = GRUB_BTRFS_DIR_ITEM_TYPE_DIRECTORY;
*tree = data->sblock.root_tree;
key->object_id = data->sblock.root_dir_objectid;
key->type = GRUB_BTRFS_ITEM_TYPE_DIR_ITEM;
key->offset = 0;
skip_default = 1;
err = get_root (data, key, tree, type);
if (err)
return err;
}
continue;
}
+1
View File
@@ -289,6 +289,7 @@ grub_cbfsdisk_open (const char *name, grub_disk_t disk)
return grub_error (GRUB_ERR_UNKNOWN_DEVICE, "not a cbfsdisk");
disk->total_sectors = cbfsdisk_size / GRUB_DISK_SECTOR_SIZE;
disk->max_agglomerate = GRUB_DISK_MAX_MAX_AGGLOMERATE;
disk->id = (unsigned long) "cbfs";
return GRUB_ERR_NONE;
+4 -4
View File
@@ -670,10 +670,10 @@ grub_ext2_read_symlink (grub_fshelp_node_t node)
/* If the filesize of the symlink is bigger than
60 the symlink is stored in a separate block,
otherwise it is stored in the inode. */
if (grub_le_to_cpu32 (diro->inode.size) <= 60)
grub_strncpy (symlink,
diro->inode.symlink,
grub_le_to_cpu32 (diro->inode.size));
if (grub_le_to_cpu32 (diro->inode.size) <= sizeof (diro->inode.symlink))
grub_memcpy (symlink,
diro->inode.symlink,
grub_le_to_cpu32 (diro->inode.size));
else
{
grub_ext2_read_file (diro, 0, 0, 0,
+3
View File
@@ -133,6 +133,7 @@ find_file (const char *currpath, grub_fshelp_node_t currroot,
if (ctx->type == GRUB_FSHELP_SYMLINK)
{
char *symlink;
const char *next;
/* Test if the symlink does not loop. */
if (++ctx->symlinknest == 8)
@@ -164,8 +165,10 @@ find_file (const char *currpath, grub_fshelp_node_t currroot,
}
/* Lookup the node the symlink points to. */
next = ctx->next;
find_file (symlink, ctx->oldnode, &ctx->currnode,
iterate_dir, read_symlink, ctx);
ctx->next = next;
ctx->type = ctx->foundtype;
grub_free (symlink);
+2
View File
@@ -888,6 +888,8 @@ grub_hfsplus_read (grub_file_t file, char *buf, grub_size_t len)
struct grub_hfsplus_data *data =
(struct grub_hfsplus_data *) file->data;
data->opened_file.file = file;
if (grub_hfsplus_read_compressed && data->opened_file.compressed)
return grub_hfsplus_read_compressed (&data->opened_file,
file->offset, len, buf);
+5
View File
@@ -23,6 +23,7 @@
#include <grub/misc.h>
#include <grub/mm.h>
#include <grub/deflate.h>
#include <grub/file.h>
GRUB_MOD_LICENSE ("GPLv3+");
@@ -121,6 +122,8 @@ hfsplus_read_compressed_real (struct grub_hfsplus_file *node,
if (node->compressed == 1)
{
grub_memcpy (buf, node->cbuf + pos, len);
if (grub_file_progress_hook && node->file)
grub_file_progress_hook (0, 0, len, node->file);
return len;
}
@@ -162,6 +165,8 @@ hfsplus_read_compressed_real (struct grub_hfsplus_file *node,
}
grub_memcpy (buf, node->cbuf + (pos % HFSPLUS_COMPRESS_BLOCK_SIZE),
curlen);
if (grub_file_progress_hook && node->file)
grub_file_progress_hook (0, 0, curlen, node->file);
buf += curlen;
pos += curlen;
len -= curlen;
+10 -11
View File
@@ -536,8 +536,8 @@ add_part (struct iterate_dir_ctx *ctx,
if (! ctx->symlink)
return;
ctx->symlink[size] = 0;
grub_strncat (ctx->symlink, part, len2);
grub_memcpy (ctx->symlink + size, part, len2);
ctx->symlink[size + len2] = 0;
}
static grub_err_t
@@ -558,20 +558,19 @@ susp_iterate_dir (struct grub_iso9660_susp_entry *entry,
ctx->filename = (char *) "..";
else if (entry->len >= 5)
{
grub_size_t size = 1, csize = 1;
grub_size_t off = 0, csize = 1;
char *old;
csize = size = entry->len - 5;
csize = entry->len - 5;
old = ctx->filename;
if (ctx->filename_alloc)
{
size += grub_strlen (ctx->filename);
ctx->filename = grub_realloc (ctx->filename, size + 1);
off = grub_strlen (ctx->filename);
ctx->filename = grub_realloc (ctx->filename, csize + off + 1);
}
else
{
ctx->filename_alloc = 1;
ctx->filename = grub_zalloc (size + 1);
ctx->filename[0] = 0;
off = 0;
ctx->filename = grub_zalloc (csize + 1);
}
if (!ctx->filename)
{
@@ -579,8 +578,8 @@ susp_iterate_dir (struct grub_iso9660_susp_entry *entry,
return grub_errno;
}
ctx->filename_alloc = 1;
grub_strncat (ctx->filename, (char *) &entry->data[1], csize);
ctx->filename[size] = '\0';
grub_memcpy (ctx->filename + off, (char *) &entry->data[1], csize);
ctx->filename[off + csize] = '\0';
}
}
/* The mode information (st_mode). */
+1 -1
View File
@@ -723,7 +723,7 @@ grub_jfs_lookup_symlink (struct grub_jfs_data *data, grub_uint32_t ino)
if (!symlink)
return grub_errno;
if (size <= sizeof (data->currinode.symlink.path))
grub_strncpy (symlink, (char *) (data->currinode.symlink.path), size);
grub_memcpy (symlink, (char *) (data->currinode.symlink.path), size);
else if (grub_jfs_read_file (data, 0, 0, 0, size, symlink) < 0)
{
grub_free (symlink);
+3
View File
@@ -378,6 +378,9 @@ read_data (struct grub_ntfs_attr *at, grub_uint8_t *pa, grub_uint8_t *dest,
ctx->comp.log_spc = at->mft->data->log_spc;
ctx->comp.disk = at->mft->data->disk;
if (read_hook == grub_file_progress_hook)
ctx->file = read_hook_data;
if (pa[8] == 0)
{
if (ofs + len > u32at (pa, 0x10))
+29
View File
@@ -226,6 +226,9 @@ read_block (struct grub_ntfs_rlst *ctx, grub_uint8_t *buf, grub_size_t num)
{
grub_memset (buf, 0, nn * GRUB_NTFS_COM_LEN);
buf += nn * GRUB_NTFS_COM_LEN;
if (grub_file_progress_hook && ctx->file)
grub_file_progress_hook (0, 0, nn * GRUB_NTFS_COM_LEN,
ctx->file);
}
}
else
@@ -236,6 +239,9 @@ read_block (struct grub_ntfs_rlst *ctx, grub_uint8_t *buf, grub_size_t num)
return grub_errno;
if (buf)
buf += GRUB_NTFS_COM_LEN;
if (grub_file_progress_hook && ctx->file)
grub_file_progress_hook (0, 0, GRUB_NTFS_COM_LEN,
ctx->file);
nn--;
}
}
@@ -262,6 +268,11 @@ read_block (struct grub_ntfs_rlst *ctx, grub_uint8_t *buf, grub_size_t num)
ctx->target_vcn)) << ctx->comp.log_spc, 0,
tt << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR), buf))
return grub_errno;
if (grub_file_progress_hook && ctx->file)
grub_file_progress_hook (0, 0,
tt << (ctx->comp.log_spc
+ GRUB_NTFS_BLK_SHR),
ctx->file);
buf += tt << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR);
}
nn -= tt;
@@ -280,6 +291,11 @@ read_block (struct grub_ntfs_rlst *ctx, grub_uint8_t *buf, grub_size_t num)
nn << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR), buf))
return grub_errno;
buf += nn << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR);
if (grub_file_progress_hook && ctx->file)
grub_file_progress_hook (0, 0,
nn << (ctx->comp.log_spc
+ GRUB_NTFS_BLK_SHR),
ctx->file);
}
ctx->target_vcn += nn;
}
@@ -306,6 +322,8 @@ ntfscomp (grub_uint8_t *dest, grub_disk_addr_t ofs,
n = len;
grub_memcpy (dest, ctx->attr->sbuf + ofs - ctx->attr->save_pos, n);
if (grub_file_progress_hook && ctx->file)
grub_file_progress_hook (0, 0, n, ctx->file);
if (n == len)
return 0;
@@ -351,6 +369,9 @@ ntfscomp (grub_uint8_t *dest, grub_disk_addr_t ofs,
if (ofs % GRUB_NTFS_COM_LEN)
{
grub_uint32_t t, n, o;
void *file = ctx->file;
ctx->file = 0;
t = ctx->target_vcn << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR);
if (read_block (ctx, ctx->attr->sbuf, 1))
@@ -359,6 +380,8 @@ ntfscomp (grub_uint8_t *dest, grub_disk_addr_t ofs,
goto quit;
}
ctx->file = file;
ctx->attr->save_pos = t;
o = ofs % GRUB_NTFS_COM_LEN;
@@ -366,6 +389,8 @@ ntfscomp (grub_uint8_t *dest, grub_disk_addr_t ofs,
if (n > len)
n = len;
grub_memcpy (dest, &ctx->attr->sbuf[o], n);
if (grub_file_progress_hook && ctx->file)
grub_file_progress_hook (0, 0, n, ctx->file);
if (n == len)
goto quit;
dest += n;
@@ -383,7 +408,9 @@ ntfscomp (grub_uint8_t *dest, grub_disk_addr_t ofs,
if (len)
{
grub_uint32_t t;
void *file = ctx->file;
ctx->file = 0;
t = ctx->target_vcn << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR);
if (read_block (ctx, ctx->attr->sbuf, 1))
{
@@ -394,6 +421,8 @@ ntfscomp (grub_uint8_t *dest, grub_disk_addr_t ofs,
ctx->attr->save_pos = t;
grub_memcpy (dest, ctx->attr->sbuf, len);
if (grub_file_progress_hook && file)
grub_file_progress_hook (0, 0, len, file);
}
quit:
+1 -1
View File
@@ -781,7 +781,7 @@ grub_reiserfs_iterate_dir (grub_fshelp_node_t item,
= grub_le_to_cpu16 (directory_header->state);
grub_fshelp_node_t entry_item;
struct grub_reiserfs_key entry_key;
enum grub_reiserfs_item_type entry_type;
enum grub_fshelp_filetype entry_type;
char *entry_name;
if (!(entry_state & GRUB_REISERFS_VISIBLE_MASK))
+9 -2
View File
@@ -297,10 +297,17 @@ static grub_ssize_t
grub_cpio_read (grub_file_t file, char *buf, grub_size_t len)
{
struct grub_archelp_data *data;
grub_ssize_t ret;
data = file->data;
return (grub_disk_read (data->disk, 0, data->dofs + file->offset,
len, buf)) ? -1 : (grub_ssize_t) len;
data->disk->read_hook = file->read_hook;
data->disk->read_hook_data = file->read_hook_data;
ret = (grub_disk_read (data->disk, 0, data->dofs + file->offset,
len, buf)) ? -1 : (grub_ssize_t) len;
data->disk->read_hook = 0;
return ret;
}
static grub_err_t
+15 -16
View File
@@ -877,18 +877,13 @@ nvlist_next_nvpair (const char *nvl, const char *nvpair)
* containing the name of nvpair is saved in buf.
*/
static int
nvpair_name (const char *nvp, char **buf, int *buflen)
nvpair_name (const char *nvp, char **buf, grub_size_t *buflen)
{
int len;
/* skip over encode/decode size */
nvp += 4 * 2;
len = grub_be_to_cpu32 (grub_get_unaligned32 (nvp));
nvp=nvp+4;
*buf=(char*)nvp;
*buflen=len;
*buf = (char *) (nvp + 4);
*buflen = grub_be_to_cpu32 (grub_get_unaligned32 (nvp));
return 0;
}
@@ -1113,15 +1108,15 @@ check_pool_label (struct grub_zfs_data *data,
const char *nvp=NULL;
char name[MAX_SUPPORTED_FEATURE_STRLEN + 1];
char *nameptr;
int namelen;
grub_size_t namelen;
while ((nvp = nvlist_next_nvpair(features, nvp)) != NULL)
{
nvpair_name(nvp, &nameptr,&namelen);
nvpair_name (nvp, &nameptr, &namelen);
if(namelen > MAX_SUPPORTED_FEATURE_STRLEN)
namelen = MAX_SUPPORTED_FEATURE_STRLEN;
grub_strncpy(name,nameptr,namelen);
name[namelen]=0;
grub_dprintf("zfs","namelen=%u str=%s\n",namelen,name);
grub_memcpy (name, nameptr, namelen);
name[namelen] = '\0';
grub_dprintf("zfs","str=%s\n",name);
if (check_feature(name,1, NULL) != 0)
{
grub_dprintf("zfs","feature missing in check_pool_label:%s\n",name);
@@ -3308,7 +3303,8 @@ nvlist_find_value (const char *nvlist_in, const char *name,
int valtype, char **val,
grub_size_t *size_out, grub_size_t *nelm_out)
{
int name_len, type ;
grub_size_t nvp_name_len, name_len = grub_strlen(name);
int type;
const char *nvpair=NULL,*nvlist=nvlist_in;
char *nvp_name;
@@ -3329,9 +3325,12 @@ nvlist_find_value (const char *nvlist_in, const char *name,
*/
while ((nvpair=nvlist_next_nvpair(nvlist,nvpair)))
{
nvpair_name(nvpair,&nvp_name,&name_len);
nvpair_name(nvpair,&nvp_name, &nvp_name_len);
type = nvpair_type(nvpair);
if ((grub_strncmp (nvp_name, name, grub_strlen(name)) == 0) && type == valtype)
if (type == valtype
&& (nvp_name_len == name_len
|| (nvp_name_len > name_len && nvp_name[name_len] == '\0'))
&& grub_memcmp (nvp_name, name, name_len) == 0)
{
return nvpair_value(nvpair,val,size_out,nelm_out);
}
+9 -8
View File
@@ -143,7 +143,7 @@ grub_ccm_decrypt (grub_crypto_cipher_handle_t cipher,
return err;
if (mac_out)
grub_crypto_xor (mac_out, mac, mul, m);
return GRUB_ERR_NONE;
return GPG_ERR_NO_ERROR;
}
static void
@@ -244,7 +244,7 @@ grub_gcm_decrypt (grub_crypto_cipher_handle_t cipher,
if (mac_out)
grub_crypto_xor (mac_out, mac, mac_xor, m);
return GRUB_ERR_NONE;
return GPG_ERR_NO_ERROR;
}
@@ -258,13 +258,14 @@ algo_decrypt (grub_crypto_cipher_handle_t cipher, grub_uint64_t algo,
switch (algo)
{
case 0:
return grub_ccm_decrypt (cipher, out, in, psize, mac_out, nonce, l, m);
return grub_ccm_decrypt (cipher, out, in, psize,
mac_out, nonce, l, m);
case 1:
return grub_gcm_decrypt (cipher, out, in, psize, mac_out, nonce,
return grub_gcm_decrypt (cipher, out, in, psize,
mac_out, nonce,
15 - l, m);
default:
return grub_error (GRUB_ERR_NOT_IMPLEMENTED_YET, "algorithm %lld is not supported yet",
(long long) algo);
return GPG_ERR_CIPHER_ALGO;
}
}
@@ -279,7 +280,7 @@ grub_zfs_decrypt_real (grub_crypto_cipher_handle_t cipher,
grub_uint32_t mac[4];
unsigned i;
grub_uint32_t sw[4];
grub_err_t err;
gcry_err_code_t err;
grub_memcpy (sw, nonce, 16);
if (endian != GRUB_ZFS_BIG_ENDIAN)
@@ -295,7 +296,7 @@ grub_zfs_decrypt_real (grub_crypto_cipher_handle_t cipher,
size, mac,
sw + 1, 3, 12);
if (err)
return err;
return grub_crypto_gcry_error (err);
for (i = 0; i < 3; i++)
if (grub_zfs_to_cpu32 (expected_mac[i], endian)
+2 -2
View File
@@ -201,7 +201,7 @@ grub_gdb_hex2int (char **ptr, grub_uint64_t *int_value)
}
/* This function does all command procesing for interfacing to gdb. */
void
void __attribute__ ((regparm(3)))
grub_gdb_trap (int trap_no)
{
unsigned int sig_no;
@@ -216,7 +216,7 @@ grub_gdb_trap (int trap_no)
grub_backtrace_print_address ((void *) grub_gdb_regs[PC]);
grub_printf ("\n");
grub_backtrace_pointer ((void *) grub_gdb_regs[EBP]);
grub_abort ();
grub_fatal ("Unhandled exception");
}
sig_no = grub_gdb_trap2sig (trap_no);
+6 -2
View File
@@ -34,8 +34,6 @@ GRUB_MOD_LICENSE ("GPLv3+");
http://www.gnu.org/software/autoconf/manual/gettext/MO-Files.html .
*/
static struct grub_gettext_context main_context, secondary_context;
static const char *(*grub_gettext_original) (const char *s);
struct grub_gettext_msg
@@ -69,6 +67,8 @@ struct grub_gettext_context
struct grub_gettext_msg *grub_gettext_msg_list;
};
static struct grub_gettext_context main_context, secondary_context;
#define MO_MAGIC_NUMBER 0x950412de
static grub_err_t
@@ -423,6 +423,10 @@ grub_gettext_init_ext (struct grub_gettext_context *ctx,
grub_free (lang);
}
if (locale[0] == 'e' && locale[1] == 'n'
&& (locale[2] == '\0' || locale[2] == '_'))
grub_errno = err = GRUB_ERR_NONE;
return err;
}
+16
View File
@@ -234,14 +234,30 @@ static void
box_paint (void *vself, const grub_video_rect_t *region)
{
grub_gui_box_t self = vself;
struct component_node *cur;
grub_video_rect_t vpsave;
grub_video_area_status_t box_area_status;
grub_video_get_area_status (&box_area_status);
grub_gui_set_viewport (&self->bounds, &vpsave);
for (cur = self->chead.next; cur != &self->ctail; cur = cur->next)
{
grub_gui_component_t comp = cur->component;
grub_video_rect_t r;
comp->ops->get_bounds(comp, &r);
if (!grub_video_have_common_points (region, &r))
continue;
/* Paint the child. */
if (box_area_status == GRUB_VIDEO_AREA_ENABLED
&& grub_video_bounds_inside_region (&r, region))
grub_video_set_area_status (GRUB_VIDEO_AREA_DISABLED);
comp->ops->paint (comp, region);
if (box_area_status == GRUB_VIDEO_AREA_ENABLED)
grub_video_set_area_status (GRUB_VIDEO_AREA_ENABLED);
}
grub_gui_restore_viewport (&vpsave);
}
+13 -2
View File
@@ -80,9 +80,13 @@ static void
canvas_paint (void *vself, const grub_video_rect_t *region)
{
grub_gui_canvas_t self = vself;
struct component_node *cur;
grub_video_rect_t vpsave;
grub_video_area_status_t canvas_area_status;
grub_video_get_area_status (&canvas_area_status);
grub_gui_set_viewport (&self->bounds, &vpsave);
for (cur = self->components.next; cur; cur = cur->next)
{
@@ -135,9 +139,16 @@ canvas_paint (void *vself, const grub_video_rect_t *region)
r.height = h;
comp->ops->set_bounds (comp, &r);
if (!grub_video_have_common_points (region, &r))
continue;
/* Paint the child. */
if (grub_video_have_common_points (region, &r))
comp->ops->paint (comp, region);
if (canvas_area_status == GRUB_VIDEO_AREA_ENABLED
&& grub_video_bounds_inside_region (&r, region))
grub_video_set_area_status (GRUB_VIDEO_AREA_DISABLED);
comp->ops->paint (comp, region);
if (canvas_area_status == GRUB_VIDEO_AREA_ENABLED)
grub_video_set_area_status (GRUB_VIDEO_AREA_ENABLED);
}
grub_gui_restore_viewport (&vpsave);
}
+13 -11
View File
@@ -36,7 +36,7 @@ struct grub_gui_circular_progress
int visible;
int start;
int end;
unsigned value;
int value;
unsigned num_ticks;
int start_angle;
int ticks_disappear;
@@ -139,15 +139,16 @@ circprog_paint (void *vself, const grub_video_rect_t *region)
center_width, center_height);
int radius = grub_min (height, width) / 2 - grub_max (tick_height, tick_width) / 2 - 1;
int nticks;
int tick_begin;
int tick_end;
if (self->end == self->start)
unsigned nticks;
unsigned tick_begin;
unsigned tick_end;
if (self->end <= self->start
|| self->value <= self->start)
nticks = 0;
else
nticks = (self->num_ticks
* (self->value - self->start)
/ (self->end - self->start));
nticks = ((unsigned) (self->num_ticks
* (self->value - self->start)))
/ ((unsigned) (self->end - self->start));
/* Do ticks appear or disappear as the value approached the end? */
if (self->ticks_disappear)
{
@@ -160,7 +161,7 @@ circprog_paint (void *vself, const grub_video_rect_t *region)
tick_end = nticks;
}
int i;
unsigned i;
for (i = tick_begin; i < tick_end; i++)
{
int x;
@@ -168,7 +169,8 @@ circprog_paint (void *vself, const grub_video_rect_t *region)
int angle;
/* Calculate the location of the tick. */
angle = self->start_angle + i * GRUB_TRIG_ANGLE_MAX / self->num_ticks;
angle = self->start_angle
+ i * GRUB_TRIG_ANGLE_MAX / self->num_ticks;
x = width / 2 + (grub_cos (angle) * radius / GRUB_TRIG_FRACTION_SCALE);
y = height / 2 + (grub_sin (angle) * radius / GRUB_TRIG_FRACTION_SCALE);
@@ -253,7 +255,7 @@ circprog_set_property (void *vself, const char *name, const char *value)
circular_progress_t self = vself;
if (grub_strcmp (name, "num_ticks") == 0)
{
self->num_ticks = grub_strtol (value, 0, 10);
self->num_ticks = grub_strtoul (value, 0, 10);
}
else if (grub_strcmp (name, "start_angle") == 0)
{
+26 -7
View File
@@ -251,18 +251,24 @@ draw_scrollbar (list_impl_t self,
int value, int extent, int min, int max,
int scrollbar_width, int scrollbar_height)
{
unsigned thumby, thumbheight;
grub_gfxmenu_box_t frame = self->scrollbar_frame;
grub_gfxmenu_box_t thumb = self->scrollbar_thumb;
int frame_vertical_pad = (frame->get_top_pad (frame)
+ frame->get_bottom_pad (frame));
int frame_horizontal_pad = (frame->get_left_pad (frame)
+ frame->get_right_pad (frame));
int thumb_vertical_pad = (thumb->get_top_pad (thumb)
+ thumb->get_bottom_pad (thumb));
unsigned thumb_vertical_pad = (thumb->get_top_pad (thumb)
+ thumb->get_bottom_pad (thumb));
int thumb_horizontal_pad = (thumb->get_left_pad (thumb)
+ thumb->get_right_pad (thumb));
int tracktop = frame->get_top_pad (frame);
int tracklen = scrollbar_height - frame_vertical_pad;
unsigned tracklen;
if (scrollbar_height <= frame_vertical_pad)
tracklen = 0;
else
tracklen = scrollbar_height - frame_vertical_pad;
frame->set_content_size (frame,
scrollbar_width - frame_horizontal_pad,
tracklen);
@@ -271,15 +277,28 @@ draw_scrollbar (list_impl_t self,
tracklen += thumb_vertical_pad;
tracktop -= thumb->get_top_pad (thumb);
}
int thumby = tracktop + tracklen * (value - min) / (unsigned) (max - min);
int thumbheight = tracklen * extent / (unsigned) (max - min) + 1;
if (value <= min || max <= min)
thumby = 0;
else
thumby = ((unsigned) tracklen * (value - min))
/ ((unsigned) (max - min));
if (max <= min)
thumbheight = 1;
else
thumbheight = ((unsigned) (tracklen * extent)
/ ((unsigned) (max - min))) + 1;
/* Rare occasion: too many entries or too low height. */
if (thumbheight < thumb_vertical_pad)
{
thumbheight = thumb_vertical_pad;
thumby = tracktop + ((tracklen - thumb_vertical_pad) * (value - min)
/ (unsigned)(max - extent));
if (value <= min || max <= extent
|| tracklen <= thumb_vertical_pad)
thumby = 0;
else
thumby = ((unsigned) ((tracklen - thumb_vertical_pad) * (value - min))
/ ((unsigned)(max - extent)));
}
thumby += tracktop;
int thumbx = frame->get_left_pad (frame);
int thumbwidth = scrollbar_width - frame_horizontal_pad;
if (!self->scrollbar_thumb_overlay)
+6 -2
View File
@@ -169,8 +169,12 @@ draw_pixmap_bar (grub_gui_progress_bar_t self)
else
hlheight -= hl_v_pad;
barwidth = (tracklen * (self->value - self->start)
/ (unsigned) (self->end - self->start));
if (self->value <= self->start
|| self->end <= self->start)
barwidth = 0;
else
barwidth = ((unsigned) (tracklen * (self->value - self->start))
/ ((unsigned) (self->end - self->start)));
if (barwidth >= hl_h_pad)
{
+7 -11
View File
@@ -137,23 +137,19 @@ static struct grub_video_bitmap *
try_loading_icon (grub_gfxmenu_icon_manager_t mgr,
const char *dir, const char *class_name)
{
char *path;
int l;
char *path, *ptr;
path = grub_malloc (grub_strlen (dir) + grub_strlen (class_name)
+ grub_strlen (icon_extension) + 3);
if (! path)
return 0;
grub_strcpy (path, dir);
l = grub_strlen (path);
if (path[l-1] != '/')
{
path[l] = '/';
path[l+1] = 0;
}
grub_strcat (path, class_name);
grub_strcat (path, icon_extension);
ptr = grub_stpcpy (path, dir);
if (path == ptr || ptr[-1] != '/')
*ptr++ = '/';
ptr = grub_stpcpy (ptr, class_name);
ptr = grub_stpcpy (ptr, icon_extension);
*ptr = '\0';
struct grub_video_bitmap *raw_bitmap;
grub_video_bitmap_load (&raw_bitmap, path);
+18 -1
View File
@@ -213,6 +213,7 @@ redraw_timeouts (struct grub_gfxmenu_view *view)
{
grub_video_rect_t bounds;
cur->self->ops->get_bounds (cur->self, &bounds);
grub_video_set_area_status (GRUB_VIDEO_AREA_ENABLED);
grub_gfxmenu_view_redraw (view, &bounds);
}
}
@@ -321,6 +322,11 @@ grub_gfxmenu_view_redraw (grub_gfxmenu_view_t view,
grub_gfxterm_schedule_repaint ();
grub_video_set_active_render_target (GRUB_VIDEO_RENDER_TARGET_DISPLAY);
grub_video_area_status_t area_status;
grub_video_get_area_status (&area_status);
if (area_status == GRUB_VIDEO_AREA_ENABLED)
grub_video_set_region (region->x, region->y,
region->width, region->height);
redraw_background (view, region);
if (view->canvas)
@@ -328,6 +334,9 @@ grub_gfxmenu_view_redraw (grub_gfxmenu_view_t view,
draw_title (view);
if (grub_video_have_common_points (&view->progress_message_frame, region))
draw_message (view);
if (area_status == GRUB_VIDEO_AREA_ENABLED)
grub_video_set_area_status (GRUB_VIDEO_AREA_ENABLED);
}
void
@@ -350,10 +359,15 @@ grub_gfxmenu_view_draw (grub_gfxmenu_view_t view)
refresh_menu_components (view);
update_menu_components (view);
grub_video_set_area_status (GRUB_VIDEO_AREA_DISABLED);
grub_gfxmenu_view_redraw (view, &view->screen);
grub_video_swap_buffers ();
if (view->double_repaint)
grub_gfxmenu_view_redraw (view, &view->screen);
{
grub_video_set_area_status (GRUB_VIDEO_AREA_DISABLED);
grub_gfxmenu_view_redraw (view, &view->screen);
}
}
static void
@@ -367,6 +381,7 @@ redraw_menu_visit (grub_gui_component_t component,
grub_video_rect_t bounds;
component->ops->get_bounds (component, &bounds);
grub_video_set_area_status (GRUB_VIDEO_AREA_ENABLED);
grub_gfxmenu_view_redraw (view, &bounds);
}
}
@@ -404,6 +419,8 @@ grub_gfxmenu_draw_terminal_box (void)
if (!term_box)
return;
grub_video_set_area_status (GRUB_VIDEO_AREA_DISABLED);
term_box->set_content_size (term_box, term_view->terminal_rect.width,
term_view->terminal_rect.height);
+3 -3
View File
@@ -363,8 +363,6 @@ static ush mask_bits[] =
0x01ff, 0x03ff, 0x07ff, 0x0fff, 0x1fff, 0x3fff, 0x7fff, 0xffff
};
#pragma GCC diagnostic ignored "-Wunsafe-loop-optimizations"
#define NEEDBITS(n) do {while(k<(n)){b|=((ulg)get_byte(gzio))<<k;k+=8;}} while (0)
#define DUMPBITS(n) do {b>>=(n);k-=(n);} while (0)
@@ -544,7 +542,7 @@ huft_build (unsigned *b, /* code lengths in bits (all assumed <= BMAX) */
z = 1 << j; /* table entries for j-bit table */
/* allocate and link in new table */
q = (struct huft *) grub_malloc ((z + 1) * sizeof (struct huft));
q = (struct huft *) grub_zalloc ((z + 1) * sizeof (struct huft));
if (! q)
{
if (h)
@@ -1118,6 +1116,8 @@ initialize_tables (grub_gzio_t gzio)
/* Reset memory allocation stuff. */
huft_free (gzio->tl);
huft_free (gzio->td);
gzio->tl = NULL;
gzio->td = NULL;
}
+2 -6
View File
@@ -380,12 +380,8 @@ test_header (grub_file_t file)
sizeof (checksum))
goto CORRUPTED;
if (hcheck)
{
checksum = checksum;
if (grub_memcmp (&checksum, hcheck->read(context), sizeof(checksum)) != 0)
goto CORRUPTED;
}
if (hcheck && grub_memcmp (&checksum, hcheck->read(context), sizeof(checksum)) != 0)
goto CORRUPTED;
lzopio->start_block_off = grub_file_tell (lzopio->file);
+1
View File
@@ -33,6 +33,7 @@
/*
* Null divide-by-zero handler
*/
FUNCTION(__aeabi_unwind_cpp_pr0)
FUNCTION(raise)
mov r0, #0
bx lr
+38 -211
View File
@@ -31,18 +31,7 @@
/* The last time the disk was used. */
static grub_uint64_t grub_last_time = 0;
/* Disk cache. */
struct grub_disk_cache
{
enum grub_disk_dev_id dev_id;
unsigned long disk_id;
grub_disk_addr_t sector;
char *data;
int lock;
};
static struct grub_disk_cache grub_disk_cache_table[GRUB_DISK_CACHE_NUM];
struct grub_disk_cache grub_disk_cache_table[GRUB_DISK_CACHE_NUM];
void (*grub_disk_firmware_fini) (void);
int grub_disk_firmware_is_tainted;
@@ -59,35 +48,12 @@ grub_disk_cache_get_performance (unsigned long *hits, unsigned long *misses)
}
#endif
static unsigned
grub_disk_cache_get_index (unsigned long dev_id, unsigned long disk_id,
grub_disk_addr_t sector)
{
return ((dev_id * 524287UL + disk_id * 2606459UL
+ ((unsigned) (sector >> GRUB_DISK_CACHE_BITS)))
% GRUB_DISK_CACHE_NUM);
}
static void
grub_disk_cache_invalidate (unsigned long dev_id, unsigned long disk_id,
grub_disk_addr_t sector)
{
unsigned cache_index;
struct grub_disk_cache *cache;
sector &= ~(GRUB_DISK_CACHE_SIZE - 1);
cache_index = grub_disk_cache_get_index (dev_id, disk_id, sector);
cache = grub_disk_cache_table + cache_index;
if (cache->dev_id == dev_id && cache->disk_id == disk_id
&& cache->sector == sector && cache->data)
{
cache->lock = 1;
grub_free (cache->data);
cache->data = 0;
cache->lock = 0;
}
}
grub_err_t (*grub_disk_write_weak) (grub_disk_t disk,
grub_disk_addr_t sector,
grub_off_t offset,
grub_size_t size,
const void *buf);
#include "disk_common.c"
void
grub_disk_cache_invalidate_all (void)
@@ -233,6 +199,9 @@ grub_disk_open (const char *name)
if (! disk)
return 0;
disk->log_sector_size = GRUB_DISK_SECTOR_BITS;
/* Default 1MiB of maximum agglomerate. */
disk->max_agglomerate = 1048576 >> (GRUB_DISK_SECTOR_BITS
+ GRUB_DISK_CACHE_BITS);
p = find_part_sep (name);
if (p)
@@ -341,59 +310,12 @@ grub_disk_close (grub_disk_t disk)
grub_free (disk);
}
/* This function performs three tasks:
- Make sectors disk relative from partition relative.
- Normalize offset to be less than the sector size.
- Verify that the range is inside the partition. */
static grub_err_t
grub_disk_adjust_range (grub_disk_t disk, grub_disk_addr_t *sector,
grub_off_t *offset, grub_size_t size)
{
grub_partition_t part;
*sector += *offset >> GRUB_DISK_SECTOR_BITS;
*offset &= GRUB_DISK_SECTOR_SIZE - 1;
for (part = disk->partition; part; part = part->parent)
{
grub_disk_addr_t start;
grub_uint64_t len;
start = part->start;
len = part->len;
if (*sector >= len
|| len - *sector < ((*offset + size + GRUB_DISK_SECTOR_SIZE - 1)
>> GRUB_DISK_SECTOR_BITS))
return grub_error (GRUB_ERR_OUT_OF_RANGE,
N_("attempt to read or write outside of partition"));
*sector += start;
}
if (disk->total_sectors != GRUB_DISK_SIZE_UNKNOWN
&& ((disk->total_sectors << (disk->log_sector_size - GRUB_DISK_SECTOR_BITS)) <= *sector
|| ((*offset + size + GRUB_DISK_SECTOR_SIZE - 1)
>> GRUB_DISK_SECTOR_BITS) > (disk->total_sectors
<< (disk->log_sector_size
- GRUB_DISK_SECTOR_BITS)) - *sector))
return grub_error (GRUB_ERR_OUT_OF_RANGE,
N_("attempt to read or write outside of disk `%s'"), disk->name);
return GRUB_ERR_NONE;
}
static inline grub_disk_addr_t
transform_sector (grub_disk_t disk, grub_disk_addr_t sector)
{
return sector >> (disk->log_sector_size - GRUB_DISK_SECTOR_BITS);
}
/* Small read (less than cache size and not pass across cache unit boundaries).
sector is already adjusted and is divisible by cache unit size.
*/
static grub_err_t
grub_disk_read_small (grub_disk_t disk, grub_disk_addr_t sector,
grub_off_t offset, grub_size_t size, void *buf)
grub_disk_read_small_real (grub_disk_t disk, grub_disk_addr_t sector,
grub_off_t offset, grub_size_t size, void *buf)
{
char *data;
char *tmp_buf;
@@ -470,15 +392,27 @@ grub_disk_read_small (grub_disk_t disk, grub_disk_addr_t sector,
}
}
static grub_err_t
grub_disk_read_small (grub_disk_t disk, grub_disk_addr_t sector,
grub_off_t offset, grub_size_t size, void *buf)
{
grub_err_t err;
err = grub_disk_read_small_real (disk, sector, offset, size, buf);
if (err)
return err;
if (disk->read_hook)
(disk->read_hook) (sector + (offset >> GRUB_DISK_SECTOR_BITS),
offset & (GRUB_DISK_SECTOR_SIZE - 1),
size, disk->read_hook_data);
return GRUB_ERR_NONE;
}
/* Read data from the disk. */
grub_err_t
grub_disk_read (grub_disk_t disk, grub_disk_addr_t sector,
grub_off_t offset, grub_size_t size, void *buf)
{
grub_off_t real_offset;
grub_disk_addr_t real_sector;
grub_size_t real_size;
/* First of all, check if the region is within the disk. */
if (grub_disk_adjust_range (disk, &sector, &offset, size) != GRUB_ERR_NONE)
{
@@ -489,10 +423,6 @@ grub_disk_read (grub_disk_t disk, grub_disk_addr_t sector,
return grub_errno;
}
real_sector = sector;
real_offset = offset;
real_size = size;
/* First read until first cache boundary. */
if (offset || (sector & (GRUB_DISK_CACHE_SIZE - 1)))
{
@@ -527,7 +457,8 @@ grub_disk_read (grub_disk_t disk, grub_disk_addr_t sector,
/* agglomerate read until we find a first cached entry. */
for (agglomerate = 0; agglomerate
< (size >> (GRUB_DISK_SECTOR_BITS + GRUB_DISK_CACHE_BITS));
< (size >> (GRUB_DISK_SECTOR_BITS + GRUB_DISK_CACHE_BITS))
&& agglomerate < disk->max_agglomerate;
agglomerate++)
{
data = grub_disk_cache_fetch (disk->dev->id, disk->id,
@@ -567,6 +498,11 @@ grub_disk_read (grub_disk_t disk, grub_disk_addr_t sector,
+ (i << (GRUB_DISK_CACHE_BITS
+ GRUB_DISK_SECTOR_BITS)));
if (disk->read_hook)
(disk->read_hook) (sector, 0, agglomerate << (GRUB_DISK_CACHE_BITS + GRUB_DISK_SECTOR_BITS),
disk->read_hook_data);
sector += agglomerate << GRUB_DISK_CACHE_BITS;
size -= agglomerate << (GRUB_DISK_CACHE_BITS + GRUB_DISK_SECTOR_BITS);
buf = (char *) buf
@@ -575,6 +511,9 @@ grub_disk_read (grub_disk_t disk, grub_disk_addr_t sector,
if (data)
{
if (disk->read_hook)
(disk->read_hook) (sector, 0, (GRUB_DISK_CACHE_SIZE << GRUB_DISK_SECTOR_BITS),
disk->read_hook_data);
sector += GRUB_DISK_CACHE_SIZE;
buf = (char *) buf + (GRUB_DISK_CACHE_SIZE << GRUB_DISK_SECTOR_BITS);
size -= (GRUB_DISK_CACHE_SIZE << GRUB_DISK_SECTOR_BITS);
@@ -590,118 +529,6 @@ grub_disk_read (grub_disk_t disk, grub_disk_addr_t sector,
return err;
}
/* Call the read hook, if any. */
if (disk->read_hook)
{
grub_disk_addr_t s = real_sector;
grub_size_t l = real_size;
grub_off_t o = real_offset;
while (l)
{
grub_size_t cl;
cl = GRUB_DISK_SECTOR_SIZE - o;
if (cl > l)
cl = l;
(disk->read_hook) (s, o, cl, disk->read_hook_data);
s++;
l -= cl;
o = 0;
}
}
return grub_errno;
}
grub_err_t
grub_disk_write (grub_disk_t disk, grub_disk_addr_t sector,
grub_off_t offset, grub_size_t size, const void *buf)
{
unsigned real_offset;
grub_disk_addr_t aligned_sector;
grub_dprintf ("disk", "Writing `%s'...\n", disk->name);
if (grub_disk_adjust_range (disk, &sector, &offset, size) != GRUB_ERR_NONE)
return -1;
aligned_sector = (sector & ~((1 << (disk->log_sector_size
- GRUB_DISK_SECTOR_BITS)) - 1));
real_offset = offset + ((sector - aligned_sector) << GRUB_DISK_SECTOR_BITS);
sector = aligned_sector;
while (size)
{
if (real_offset != 0 || (size < (1U << disk->log_sector_size)
&& size != 0))
{
char *tmp_buf;
grub_size_t len;
grub_partition_t part;
tmp_buf = grub_malloc (1 << disk->log_sector_size);
if (!tmp_buf)
return grub_errno;
part = disk->partition;
disk->partition = 0;
if (grub_disk_read (disk, sector,
0, (1 << disk->log_sector_size), tmp_buf)
!= GRUB_ERR_NONE)
{
disk->partition = part;
grub_free (tmp_buf);
goto finish;
}
disk->partition = part;
len = (1 << disk->log_sector_size) - real_offset;
if (len > size)
len = size;
grub_memcpy (tmp_buf + real_offset, buf, len);
grub_disk_cache_invalidate (disk->dev->id, disk->id, sector);
if ((disk->dev->write) (disk, transform_sector (disk, sector),
1, tmp_buf) != GRUB_ERR_NONE)
{
grub_free (tmp_buf);
goto finish;
}
grub_free (tmp_buf);
sector += (1 << (disk->log_sector_size - GRUB_DISK_SECTOR_BITS));
buf = (const char *) buf + len;
size -= len;
real_offset = 0;
}
else
{
grub_size_t len;
grub_size_t n;
len = size & ~((1 << disk->log_sector_size) - 1);
n = size >> disk->log_sector_size;
if ((disk->dev->write) (disk, transform_sector (disk, sector),
n, buf) != GRUB_ERR_NONE)
goto finish;
while (n--)
{
grub_disk_cache_invalidate (disk->dev->id, disk->id, sector);
sector += (1 << (disk->log_sector_size - GRUB_DISK_SECTOR_BITS));
}
buf = (const char *) buf + len;
size -= len;
}
}
finish:
return grub_errno;
}
+55
View File
@@ -0,0 +1,55 @@
/* This function performs three tasks:
- Make sectors disk relative from partition relative.
- Normalize offset to be less than the sector size.
- Verify that the range is inside the partition. */
static grub_err_t
grub_disk_adjust_range (grub_disk_t disk, grub_disk_addr_t *sector,
grub_off_t *offset, grub_size_t size)
{
grub_partition_t part;
*sector += *offset >> GRUB_DISK_SECTOR_BITS;
*offset &= GRUB_DISK_SECTOR_SIZE - 1;
for (part = disk->partition; part; part = part->parent)
{
grub_disk_addr_t start;
grub_uint64_t len;
start = part->start;
len = part->len;
if (*sector >= len
|| len - *sector < ((*offset + size + GRUB_DISK_SECTOR_SIZE - 1)
>> GRUB_DISK_SECTOR_BITS))
return grub_error (GRUB_ERR_OUT_OF_RANGE,
N_("attempt to read or write outside of partition"));
*sector += start;
}
if (disk->total_sectors != GRUB_DISK_SIZE_UNKNOWN
&& ((disk->total_sectors << (disk->log_sector_size - GRUB_DISK_SECTOR_BITS)) <= *sector
|| ((*offset + size + GRUB_DISK_SECTOR_SIZE - 1)
>> GRUB_DISK_SECTOR_BITS) > (disk->total_sectors
<< (disk->log_sector_size
- GRUB_DISK_SECTOR_BITS)) - *sector))
return grub_error (GRUB_ERR_OUT_OF_RANGE,
N_("attempt to read or write outside of disk `%s'"), disk->name);
return GRUB_ERR_NONE;
}
static inline grub_disk_addr_t
transform_sector (grub_disk_t disk, grub_disk_addr_t sector)
{
return sector >> (disk->log_sector_size - GRUB_DISK_SECTOR_BITS);
}
static unsigned
grub_disk_cache_get_index (unsigned long dev_id, unsigned long disk_id,
grub_disk_addr_t sector)
{
return ((dev_id * 524287UL + disk_id * 2606459UL
+ ((unsigned) (sector >> GRUB_DISK_CACHE_BITS)))
% GRUB_DISK_CACHE_NUM);
}
+50 -62
View File
@@ -433,6 +433,24 @@ grub_dl_resolve_symbols (grub_dl_t mod, Elf_Ehdr *e)
return GRUB_ERR_NONE;
}
static Elf_Shdr *
grub_dl_find_section (Elf_Ehdr *e, const char *name)
{
Elf_Shdr *s;
const char *str;
unsigned i;
s = (Elf_Shdr *) ((char *) e + e->e_shoff + e->e_shstrndx * e->e_shentsize);
str = (char *) e + s->sh_offset;
for (i = 0, s = (Elf_Shdr *) ((char *) e + e->e_shoff);
i < e->e_shnum;
i++, s = (Elf_Shdr *) ((char *) s + e->e_shentsize))
if (grub_strcmp (str + s->sh_name, name) == 0)
return s;
return NULL;
}
/* Me, Vladimir Serbinenko, hereby I add this module check as per new
GNU module policy. Note that this license check is informative only.
Modules have to be licensed under GPLv3 or GPLv3+ (optionally
@@ -444,24 +462,11 @@ grub_dl_resolve_symbols (grub_dl_t mod, Elf_Ehdr *e)
static grub_err_t
grub_dl_check_license (Elf_Ehdr *e)
{
Elf_Shdr *s;
const char *str;
unsigned i;
s = (Elf_Shdr *) ((char *) e + e->e_shoff + e->e_shstrndx * e->e_shentsize);
str = (char *) e + s->sh_offset;
for (i = 0, s = (Elf_Shdr *) ((char *) e + e->e_shoff);
i < e->e_shnum;
i++, s = (Elf_Shdr *) ((char *) s + e->e_shentsize))
if (grub_strcmp (str + s->sh_name, ".module_license") == 0)
{
if (grub_strcmp ((char *) e + s->sh_offset, "LICENSE=GPLv3") == 0
Elf_Shdr *s = grub_dl_find_section (e, ".module_license");
if (s && (grub_strcmp ((char *) e + s->sh_offset, "LICENSE=GPLv3") == 0
|| grub_strcmp ((char *) e + s->sh_offset, "LICENSE=GPLv3+") == 0
|| grub_strcmp ((char *) e + s->sh_offset, "LICENSE=GPLv2+") == 0)
return GRUB_ERR_NONE;
}
|| grub_strcmp ((char *) e + s->sh_offset, "LICENSE=GPLv2+") == 0))
return GRUB_ERR_NONE;
return grub_error (GRUB_ERR_BAD_MODULE, "incompatible license");
}
@@ -469,26 +474,15 @@ static grub_err_t
grub_dl_resolve_name (grub_dl_t mod, Elf_Ehdr *e)
{
Elf_Shdr *s;
const char *str;
unsigned i;
s = (Elf_Shdr *) ((char *) e + e->e_shoff + e->e_shstrndx * e->e_shentsize);
str = (char *) e + s->sh_offset;
for (i = 0, s = (Elf_Shdr *) ((char *) e + e->e_shoff);
i < e->e_shnum;
i++, s = (Elf_Shdr *) ((char *) s + e->e_shentsize))
if (grub_strcmp (str + s->sh_name, ".modname") == 0)
{
mod->name = grub_strdup ((char *) e + s->sh_offset);
if (! mod->name)
return grub_errno;
break;
}
if (i == e->e_shnum)
s = grub_dl_find_section (e, ".modname");
if (!s)
return grub_error (GRUB_ERR_BAD_MODULE, "no module name found");
mod->name = grub_strdup ((char *) e + s->sh_offset);
if (! mod->name)
return grub_errno;
return GRUB_ERR_NONE;
}
@@ -496,42 +490,36 @@ static grub_err_t
grub_dl_resolve_dependencies (grub_dl_t mod, Elf_Ehdr *e)
{
Elf_Shdr *s;
const char *str;
unsigned i;
s = (Elf_Shdr *) ((char *) e + e->e_shoff + e->e_shstrndx * e->e_shentsize);
str = (char *) e + s->sh_offset;
s = grub_dl_find_section (e, ".moddeps");
for (i = 0, s = (Elf_Shdr *) ((char *) e + e->e_shoff);
i < e->e_shnum;
i++, s = (Elf_Shdr *) ((char *) s + e->e_shentsize))
if (grub_strcmp (str + s->sh_name, ".moddeps") == 0)
{
const char *name = (char *) e + s->sh_offset;
const char *max = name + s->sh_size;
if (!s)
return GRUB_ERR_NONE;
while ((name < max) && (*name))
{
grub_dl_t m;
grub_dl_dep_t dep;
const char *name = (char *) e + s->sh_offset;
const char *max = name + s->sh_size;
m = grub_dl_load (name);
if (! m)
return grub_errno;
while ((name < max) && (*name))
{
grub_dl_t m;
grub_dl_dep_t dep;
grub_dl_ref (m);
m = grub_dl_load (name);
if (! m)
return grub_errno;
dep = (grub_dl_dep_t) grub_malloc (sizeof (*dep));
if (! dep)
return grub_errno;
grub_dl_ref (m);
dep->mod = m;
dep->next = mod->dep;
mod->dep = dep;
dep = (grub_dl_dep_t) grub_malloc (sizeof (*dep));
if (! dep)
return grub_errno;
name += grub_strlen (name) + 1;
}
}
dep->mod = m;
dep->next = mod->dep;
mod->dep = dep;
name += grub_strlen (name) + 1;
}
return GRUB_ERR_NONE;
}
+36 -29
View File
@@ -309,7 +309,34 @@ grub_efi_modules_addr (void)
char *
grub_efi_get_filename (grub_efi_device_path_t *dp)
{
char *name = 0;
char *name = 0, *p;
grub_size_t filesize = 0;
while (1)
{
grub_efi_uint8_t type = GRUB_EFI_DEVICE_PATH_TYPE (dp);
grub_efi_uint8_t subtype = GRUB_EFI_DEVICE_PATH_SUBTYPE (dp);
if (type == GRUB_EFI_END_DEVICE_PATH_TYPE)
break;
if (type == GRUB_EFI_MEDIA_DEVICE_PATH_TYPE
&& subtype == GRUB_EFI_FILE_PATH_DEVICE_PATH_SUBTYPE)
{
grub_efi_uint16_t len;
len = ((GRUB_EFI_DEVICE_PATH_LENGTH (dp) - 4)
/ sizeof (grub_efi_char16_t));
filesize += GRUB_MAX_UTF8_PER_UTF16 * len + 1;
}
dp = GRUB_EFI_NEXT_DEVICE_PATH (dp);
}
if (!filesize)
return NULL;
p = name = grub_malloc (filesize);
if (!name)
return NULL;
while (1)
{
@@ -323,45 +350,25 @@ grub_efi_get_filename (grub_efi_device_path_t *dp)
{
grub_efi_file_path_device_path_t *fp;
grub_efi_uint16_t len;
char *p;
grub_size_t size;
if (name)
{
size = grub_strlen (name);
name[size] = '/';
size++;
}
else
size = 0;
if (p != name)
*p++ = '/';
len = ((GRUB_EFI_DEVICE_PATH_LENGTH (dp) - 4)
/ sizeof (grub_efi_char16_t));
p = grub_realloc (name, size + len * 4 + 1);
if (! p)
{
grub_free (name);
return 0;
}
name = p;
fp = (grub_efi_file_path_device_path_t *) dp;
*grub_utf16_to_utf8 ((grub_uint8_t *) name + size,
fp->path_name, len) = '\0';
p = (char *) grub_utf16_to_utf8 ((unsigned char *) p, fp->path_name, len);
}
dp = GRUB_EFI_NEXT_DEVICE_PATH (dp);
}
if (name)
{
/* EFI breaks paths with backslashes. */
char *p;
*p = '\0';
for (p = name; *p; p++)
if (*p == '\\')
*p = '/';
}
/* EFI breaks paths with backslashes. */
for (p = name; *p; p++)
if (*p == '\\')
*p = '/';
return name;
}
+1 -1
View File
@@ -511,7 +511,7 @@ grub_efi_mm_init (void)
grub_printf ("printing memory map\n");
print_memory_map (memory_map, desc_size,
NEXT_MEMORY_DESCRIPTOR (memory_map, map_size));
grub_abort ();
grub_fatal ("Debug. ");
#endif
/* Release the memory maps. */
+4 -3
View File
@@ -155,6 +155,7 @@ grub_util_biosdisk_open (const char *name, grub_disk_t disk)
disk->total_sectors = grub_util_get_fd_size (fd, map[drive].device,
&disk->log_sector_size);
disk->total_sectors >>= disk->log_sector_size;
disk->max_agglomerate = GRUB_DISK_MAX_MAX_AGGLOMERATE;
#if GRUB_UTIL_FD_STAT_IS_FUNCTIONAL
{
@@ -398,12 +399,12 @@ static struct grub_disk_dev grub_util_biosdisk_dev =
static int
grub_util_check_file_presence (const char *p)
{
#if defined (__MINGW32__) || defined(__CYGWIN__)
HANDLE h;
#if !GRUB_UTIL_FD_STAT_IS_FUNCTIONAL
grub_util_fd_t h;
h = grub_util_fd_open (p, GRUB_UTIL_FD_O_RDONLY);
if (!GRUB_UTIL_FD_IS_VALID(h))
return 0;
CloseHandle (h);
grub_util_fd_close (h);
return 1;
#else
struct stat st;
-5
View File
@@ -164,11 +164,6 @@ static struct argp argp = {
void grub_hostfs_init (void);
void grub_hostfs_fini (void);
void grub_host_init (void);
void grub_host_fini (void);
int
main (int argc, char *argv[])
{
-12
View File
@@ -47,18 +47,6 @@ grub_error (grub_err_t n, const char *fmt, ...)
return n;
}
void
grub_fatal (const char *fmt, ...)
{
va_list ap;
va_start (ap, fmt);
grub_vprintf (_(fmt), ap);
va_end (ap);
grub_abort ();
}
void
grub_error_push (void)
{
+31 -1
View File
@@ -24,6 +24,7 @@
#include <grub/time.h>
#include <grub/misc.h>
#include <grub/i386/tsc.h>
#include <grub/i386/cpuid.h>
#include <grub/i386/pit.h>
#include <grub/cpu/io.h>
@@ -35,6 +36,35 @@ static grub_uint64_t tsc_boot_time;
in 32-bit. */
grub_uint32_t grub_tsc_rate;
/* Read the TSC value, which increments with each CPU clock cycle. */
static __inline grub_uint64_t
grub_get_tsc (void)
{
grub_uint32_t lo, hi;
grub_uint32_t a,b,c,d;
/* The CPUID instruction is a 'serializing' instruction, and
avoids out-of-order execution of the RDTSC instruction. */
grub_cpuid (0,a,b,c,d);
/* Read TSC value. We cannot use "=A", since this would use
%rax on x86_64. */
__asm__ __volatile__ ("rdtsc":"=a" (lo), "=d" (hi));
return (((grub_uint64_t) hi) << 32) | lo;
}
static __inline int
grub_cpu_is_tsc_supported (void)
{
grub_uint32_t a,b,c,d;
if (! grub_cpu_is_cpuid_supported ())
return 0;
grub_cpuid(1,a,b,c,d);
return (d & (1 << 4)) != 0;
}
static void
grub_pit_wait (grub_uint16_t tics)
{
@@ -63,7 +93,7 @@ grub_pit_wait (grub_uint16_t tics)
GRUB_PIT_SPEAKER_PORT);
}
grub_uint64_t
static grub_uint64_t
grub_tsc_get_time_ms (void)
{
grub_uint64_t a = grub_get_tsc () - tsc_boot_time;
+1 -1
View File
@@ -22,7 +22,7 @@
#include <grub/types.h>
#include <grub/ieee1275/ieee1275.h>
int (*grub_ieee1275_entry_fn) (void *);
int (*grub_ieee1275_entry_fn) (void *) GRUB_IEEE1275_ENTRY_FN_ATTRIBUTE;
grub_ieee1275_phandle_t grub_ieee1275_chosen;
grub_ieee1275_ihandle_t grub_ieee1275_mmu;
+88 -89
View File
@@ -94,17 +94,6 @@ grub_strcpy (char *dest, const char *src)
return dest;
}
char *
grub_strncpy (char *dest, const char *src, int c)
{
char *p = dest;
while ((*p++ = *src++) != '\0' && --c)
;
return dest;
}
int
grub_printf (const char *fmt, ...)
{
@@ -465,6 +454,15 @@ grub_strndup (const char *s, grub_size_t n)
return p;
}
/* clang detects that we're implementing here a memset so it decides to
optimise and calls memset resulting in infinite recursion. With volatile
we make it not optimise in this way. */
#ifdef __clang__
#define VOLATILE_CLANG volatile
#else
#define VOLATILE_CLANG
#endif
void *
grub_memset (void *s, int c, grub_size_t len)
{
@@ -481,13 +479,13 @@ grub_memset (void *s, int c, grub_size_t len)
while (len > 0 && (((grub_addr_t) p) & (sizeof (unsigned long) - 1)))
{
*(grub_uint8_t *) p = pattern8;
*(VOLATILE_CLANG grub_uint8_t *) p = pattern8;
p = (grub_uint8_t *) p + 1;
len--;
}
while (len >= sizeof (unsigned long))
{
*(unsigned long *) p = patternl;
*(VOLATILE_CLANG unsigned long *) p = patternl;
p = (unsigned long *) p + 1;
len -= sizeof (unsigned long);
}
@@ -495,7 +493,7 @@ grub_memset (void *s, int c, grub_size_t len)
while (len > 0)
{
*(grub_uint8_t *) p = pattern8;
*(VOLATILE_CLANG grub_uint8_t *) p = pattern8;
p = (grub_uint8_t *) p + 1;
len--;
}
@@ -553,6 +551,11 @@ grub_divmod64 (grub_uint64_t n, grub_uint64_t d, grub_uint64_t *r)
grub_uint64_t q = 0;
grub_uint64_t m = 0;
/* ARM and IA64 don't have a fast 32-bit division.
Using that code would just make us use libgcc routines, calling
them twice (once for modulo and once for quotient.
*/
#if !defined (__arm__) && !defined (__ia64__)
/* Skip the slow computation if 32-bit arithmetic is possible. */
#ifndef __alpha__
if (n < 0xffffffff && d < 0xffffffff)
@@ -627,6 +630,31 @@ grub_lltoa (char *str, int c, unsigned long long n)
return p;
}
static inline void
write_char (char *str, grub_size_t *count, grub_size_t max_len, unsigned char ch)
{
if (*count < max_len)
str[*count] = ch;
(*count)++;
}
static inline void
write_str (char *str, grub_size_t *count, grub_size_t max_len, const char *s)
{
while (*s)
write_char (str, count, max_len, *s++);
}
static inline void
write_fill (char *str, grub_size_t *count, grub_size_t max_len, const char ch, int count_fill)
{
int i;
for (i = 0; i < count_fill; i++)
write_char (str, count, max_len, ch);
}
static int
grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list args_in)
{
@@ -635,30 +663,6 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
grub_size_t count = 0;
grub_size_t count_args = 0;
const char *fmt;
auto void write_char (unsigned char ch);
auto void write_str (const char *s);
auto void write_fill (const char ch, int count_fill);
void write_char (unsigned char ch)
{
if (count < max_len)
*str++ = ch;
count++;
}
void write_str (const char *s)
{
while (*s)
write_char (*s++);
}
void write_fill (const char ch, int count_fill)
{
int i;
for (i = 0; i < count_fill; i++)
write_char (ch);
}
fmt = fmt0;
while ((c = *fmt++) != 0)
@@ -666,34 +670,33 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
if (c != '%')
continue;
if (*fmt && *fmt =='-')
if (*fmt =='-')
fmt++;
while (*fmt && grub_isdigit (*fmt))
while (grub_isdigit (*fmt))
fmt++;
if (*fmt && *fmt == '$')
if (*fmt == '$')
fmt++;
if (*fmt && *fmt =='-')
if (*fmt =='-')
fmt++;
while (*fmt && grub_isdigit (*fmt))
while (grub_isdigit (*fmt))
fmt++;
if (*fmt && *fmt =='.')
if (*fmt =='.')
fmt++;
while (*fmt && grub_isdigit (*fmt))
while (grub_isdigit (*fmt))
fmt++;
c = *fmt++;
if (c == 'l')
{
c = *fmt++;
if (c == 'l')
c = *fmt++;
}
c = *fmt++;
if (c == 'l')
c = *fmt++;
switch (c)
{
case 'p':
@@ -708,16 +711,17 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
}
}
enum { INT, WCHAR, LONG, LONGLONG, POINTER } types[count_args];
enum { INT, LONG, LONGLONG, POINTER } types[count_args];
union
{
int i;
grub_uint32_t w;
long l;
long long ll;
void *p;
} args[count_args];
COMPILE_TIME_ASSERT (sizeof (int) == sizeof (grub_uint32_t));
grub_memset (types, 0, sizeof (types));
fmt = fmt0;
@@ -789,21 +793,16 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
case 's':
types[curn] = POINTER;
break;
case 'C':
case 'c':
types[curn] = INT;
break;
case 'C':
types[curn] = WCHAR;
break;
}
}
for (n = 0; n < count_args; n++)
switch (types[n])
{
case WCHAR:
args[n].w = va_arg (args_in, grub_uint32_t);
break;
case POINTER:
args[n].p = va_arg (args_in, void *);
break;
@@ -835,7 +834,7 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
if (c != '%')
{
write_char (c);
write_char (str, &count, max_len,c);
continue;
}
@@ -889,7 +888,7 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
if (c == '%')
{
write_char (c);
write_char (str, &count, max_len,c);
continue;
}
@@ -899,7 +898,7 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
switch (c)
{
case 'p':
write_str ("0x");
write_str (str, &count, max_len, "0x");
c = 'x';
longlongfmt |= (sizeof (void *) == sizeof (long long));
/* Fall through. */
@@ -919,19 +918,19 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
else
grub_lltoa (tmp, c, args[curn].i);
if (! rightfill && grub_strlen (tmp) < format1)
write_fill (zerofill, format1 - grub_strlen (tmp));
write_str (tmp);
write_fill (str, &count, max_len, zerofill, format1 - grub_strlen (tmp));
write_str (str, &count, max_len, tmp);
if (rightfill && grub_strlen (tmp) < format1)
write_fill (zerofill, format1 - grub_strlen (tmp));
write_fill (str, &count, max_len, zerofill, format1 - grub_strlen (tmp));
break;
case 'c':
write_char (args[curn].i & 0xff);
write_char (str, &count, max_len,args[curn].i & 0xff);
break;
case 'C':
{
grub_uint32_t code = args[curn].w;
grub_uint32_t code = args[curn].i;
int shift;
unsigned mask;
@@ -950,21 +949,11 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
shift = 12;
mask = 0xe0;
}
else if (code <= 0x1fffff)
else if (code <= 0x10ffff)
{
shift = 18;
mask = 0xf0;
}
else if (code <= 0x3ffffff)
{
shift = 24;
mask = 0xf8;
}
else if (code <= 0x7fffffff)
{
shift = 30;
mask = 0xfc;
}
else
{
code = '?';
@@ -972,10 +961,10 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
mask = 0;
}
write_char (mask | (code >> shift));
write_char (str, &count, max_len,mask | (code >> shift));
for (shift -= 6; shift >= 0; shift -= 6)
write_char (0x80 | (0x3f & (code >> shift)));
write_char (str, &count, max_len,0x80 | (0x3f & (code >> shift)));
}
break;
@@ -988,25 +977,28 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
len++;
if (!rightfill && len < format1)
write_fill (zerofill, format1 - len);
write_fill (str, &count, max_len, zerofill, format1 - len);
grub_size_t i;
for (i = 0; i < len; i++)
write_char (*p++);
write_char (str, &count, max_len,*p++);
if (rightfill && len < format1)
write_fill (zerofill, format1 - len);
write_fill (str, &count, max_len, zerofill, format1 - len);
}
break;
default:
write_char (c);
write_char (str, &count, max_len,c);
break;
}
}
*str = '\0';
if (count < max_len)
str[count] = '\0';
else
str[max_len] = '\0';
return count;
}
@@ -1080,7 +1072,7 @@ grub_xasprintf (const char *fmt, ...)
}
/* Abort GRUB. This function does not return. */
void
static void __attribute__ ((noreturn))
grub_abort (void)
{
grub_printf ("\nAborted.");
@@ -1096,10 +1088,17 @@ grub_abort (void)
grub_exit ();
}
#if ! defined (__APPLE__) && !defined (GRUB_UTIL)
/* GCC emits references to abort(). */
void abort (void) __attribute__ ((alias ("grub_abort")));
#endif
void
grub_fatal (const char *fmt, ...)
{
va_list ap;
va_start (ap, fmt);
grub_vprintf (_(fmt), ap);
va_end (ap);
grub_abort ();
}
#if NEED_REGISTER_FRAME_INFO && !defined(GRUB_UTIL)
void __register_frame_info (void)
+3 -2
View File
@@ -194,7 +194,7 @@ grub_real_malloc (grub_mm_header_t *first, grub_size_t n, grub_size_t align)
{
grub_off_t extra;
extra = ((grub_addr_t) (p + 1) >> GRUB_MM_ALIGN_LOG2) % align;
extra = ((grub_addr_t) (p + 1) >> GRUB_MM_ALIGN_LOG2) & (align - 1);
if (extra)
extra = align - extra;
@@ -483,7 +483,8 @@ grub_realloc (void *ptr, grub_size_t size)
if (! q)
return q;
grub_memcpy (q, ptr, size);
/* We've already checked that p->size < n. */
grub_memcpy (q, ptr, p->size << GRUB_MM_ALIGN_LOG2);
grub_free (ptr);
return q;
}
+25 -24
View File
@@ -106,6 +106,29 @@ check_varstate (grub_parser_state_t s)
|| s == GRUB_PARSER_STATE_QVARNAME2);
}
static void
add_var (char *varname, char **bp, char **vp,
grub_parser_state_t state, grub_parser_state_t newstate)
{
const char *val;
/* Check if a variable was being read in and the end of the name
was reached. */
if (!(check_varstate (state) && !check_varstate (newstate)))
return;
*((*vp)++) = '\0';
val = grub_env_get (varname);
*vp = varname;
if (!val)
return;
/* Insert the contents of the variable in the buffer. */
for (; *val; val++)
*((*bp)++) = *val;
}
grub_err_t
grub_parser_split_cmdline (const char *cmdline,
grub_reader_getline_t getline, void *getline_data,
@@ -122,28 +145,6 @@ grub_parser_split_cmdline (const char *cmdline,
char *args;
int i;
auto void add_var (grub_parser_state_t newstate);
void add_var (grub_parser_state_t newstate)
{
const char *val;
/* Check if a variable was being read in and the end of the name
was reached. */
if (!(check_varstate (state) && !check_varstate (newstate)))
return;
*(vp++) = '\0';
val = grub_env_get (varname);
vp = varname;
if (!val)
return;
/* Insert the contents of the variable in the buffer. */
for (; *val; val++)
*(bp++) = *val;
}
*argc = 0;
do
{
@@ -168,7 +169,7 @@ grub_parser_split_cmdline (const char *cmdline,
/* If a variable was being processed and this character does
not describe the variable anymore, write the variable to
the buffer. */
add_var (newstate);
add_var (varname, &bp, &vp, state, newstate);
if (check_varstate (newstate))
{
@@ -198,7 +199,7 @@ grub_parser_split_cmdline (const char *cmdline,
/* A special case for when the last character was part of a
variable. */
add_var (GRUB_PARSER_STATE_TEXT);
add_var (varname, &bp, &vp, state, GRUB_PARSER_STATE_TEXT);
if (bp != buffer && *(bp - 1))
{
+2
View File
@@ -38,6 +38,8 @@ grub_arch_dl_check_header (void *ehdr)
return GRUB_ERR_NONE;
}
#pragma GCC diagnostic ignored "-Wcast-align"
void
grub_arch_dl_get_tramp_got_size (const void *ehdr, grub_size_t *tramp,
grub_size_t *got)
+20 -20
View File
@@ -212,6 +212,22 @@ parse_option (grub_extcmd_t cmd, const struct grub_arg_option *opt,
return 0;
}
static inline grub_err_t
add_arg (char ***argl, int *num, char *s)
{
char **p = *argl;
*argl = grub_realloc (*argl, (++(*num) + 1) * sizeof (char *));
if (! *argl)
{
grub_free (p);
return grub_errno;
}
(*argl)[(*num) - 1] = s;
(*argl)[(*num)] = NULL;
return 0;
}
int
grub_arg_parse (grub_extcmd_t cmd, int argc, char **argv,
struct grub_arg_list *usr, char ***args, int *argnum)
@@ -220,22 +236,6 @@ grub_arg_parse (grub_extcmd_t cmd, int argc, char **argv,
int arglen;
char **argl = 0;
int num = 0;
auto grub_err_t add_arg (char *s);
grub_err_t add_arg (char *s)
{
char **p = argl;
argl = grub_realloc (argl, (++num + 1) * sizeof (char *));
if (! argl)
{
grub_free (p);
return grub_errno;
}
argl[num - 1] = s;
argl[num] = NULL;
return 0;
}
for (curarg = 0; curarg < argc; curarg++)
{
@@ -247,7 +247,7 @@ grub_arg_parse (grub_extcmd_t cmd, int argc, char **argv,
if ((num && (cmd->cmd->flags & GRUB_COMMAND_OPTIONS_AT_START))
|| arg[0] != '-' || grub_strlen (arg) == 1)
{
if (add_arg (arg) != 0)
if (add_arg (&argl, &num, arg) != 0)
goto fail;
continue;
@@ -266,7 +266,7 @@ grub_arg_parse (grub_extcmd_t cmd, int argc, char **argv,
if (*curshort)
{
if (add_arg (arg) != 0)
if (add_arg (&argl, &num, arg) != 0)
goto fail;
continue;
}
@@ -319,7 +319,7 @@ grub_arg_parse (grub_extcmd_t cmd, int argc, char **argv,
if (grub_strlen (arg) == 2)
{
for (curarg++; curarg < argc; curarg++)
if (add_arg (argv[curarg]) != 0)
if (add_arg (&argl, &num, argv[curarg]) != 0)
goto fail;
break;
}
@@ -341,7 +341,7 @@ grub_arg_parse (grub_extcmd_t cmd, int argc, char **argv,
if (!opt && (cmd->cmd->flags & GRUB_COMMAND_ACCEPT_DASH))
{
if (add_arg (arg) != 0)
if (add_arg (&argl, &num, arg) != 0)
goto fail;
continue;
}
+161
View File
@@ -0,0 +1,161 @@
/*
* GRUB -- GRand Unified Bootloader
* Copyright (C) 2002,2003,2004,2006,2007,2008,2009,2010 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/disk.h>
#include <grub/err.h>
#include <grub/mm.h>
#include <grub/types.h>
#include <grub/partition.h>
#include <grub/misc.h>
#include <grub/time.h>
#include <grub/file.h>
#include <grub/i18n.h>
GRUB_MOD_LICENSE ("GPLv3+");
#include "../kern/disk_common.c"
static void
grub_disk_cache_invalidate (unsigned long dev_id, unsigned long disk_id,
grub_disk_addr_t sector)
{
unsigned cache_index;
struct grub_disk_cache *cache;
sector &= ~(GRUB_DISK_CACHE_SIZE - 1);
cache_index = grub_disk_cache_get_index (dev_id, disk_id, sector);
cache = grub_disk_cache_table + cache_index;
if (cache->dev_id == dev_id && cache->disk_id == disk_id
&& cache->sector == sector && cache->data)
{
cache->lock = 1;
grub_free (cache->data);
cache->data = 0;
cache->lock = 0;
}
}
grub_err_t
grub_disk_write (grub_disk_t disk, grub_disk_addr_t sector,
grub_off_t offset, grub_size_t size, const void *buf)
{
unsigned real_offset;
grub_disk_addr_t aligned_sector;
grub_dprintf ("disk", "Writing `%s'...\n", disk->name);
if (grub_disk_adjust_range (disk, &sector, &offset, size) != GRUB_ERR_NONE)
return -1;
aligned_sector = (sector & ~((1 << (disk->log_sector_size
- GRUB_DISK_SECTOR_BITS)) - 1));
real_offset = offset + ((sector - aligned_sector) << GRUB_DISK_SECTOR_BITS);
sector = aligned_sector;
while (size)
{
if (real_offset != 0 || (size < (1U << disk->log_sector_size)
&& size != 0))
{
char *tmp_buf;
grub_size_t len;
grub_partition_t part;
tmp_buf = grub_malloc (1 << disk->log_sector_size);
if (!tmp_buf)
return grub_errno;
part = disk->partition;
disk->partition = 0;
if (grub_disk_read (disk, sector,
0, (1 << disk->log_sector_size), tmp_buf)
!= GRUB_ERR_NONE)
{
disk->partition = part;
grub_free (tmp_buf);
goto finish;
}
disk->partition = part;
len = (1 << disk->log_sector_size) - real_offset;
if (len > size)
len = size;
grub_memcpy (tmp_buf + real_offset, buf, len);
grub_disk_cache_invalidate (disk->dev->id, disk->id, sector);
if ((disk->dev->write) (disk, transform_sector (disk, sector),
1, tmp_buf) != GRUB_ERR_NONE)
{
grub_free (tmp_buf);
goto finish;
}
grub_free (tmp_buf);
sector += (1 << (disk->log_sector_size - GRUB_DISK_SECTOR_BITS));
buf = (const char *) buf + len;
size -= len;
real_offset = 0;
}
else
{
grub_size_t len;
grub_size_t n;
len = size & ~((1 << disk->log_sector_size) - 1);
n = size >> disk->log_sector_size;
if (n > (disk->max_agglomerate
<< (GRUB_DISK_CACHE_BITS + GRUB_DISK_SECTOR_BITS
- disk->log_sector_size)))
n = (disk->max_agglomerate
<< (GRUB_DISK_CACHE_BITS + GRUB_DISK_SECTOR_BITS
- disk->log_sector_size));
if ((disk->dev->write) (disk, transform_sector (disk, sector),
n, buf) != GRUB_ERR_NONE)
goto finish;
while (n--)
{
grub_disk_cache_invalidate (disk->dev->id, disk->id, sector);
sector += (1 << (disk->log_sector_size - GRUB_DISK_SECTOR_BITS));
}
buf = (const char *) buf + len;
size -= len;
}
}
finish:
return grub_errno;
}
GRUB_MOD_INIT(disk)
{
grub_disk_write_weak = grub_disk_write;
}
GRUB_MOD_FINI(disk)
{
grub_disk_write_weak = NULL;
}
+86 -52
View File
@@ -43,6 +43,16 @@
#define prop_entry_size(prop_len) \
(3 * sizeof(grub_uint32_t) + ALIGN_UP(prop_len, sizeof(grub_uint32_t)))
#define SKIP_NODE_NAME(name, token, end) \
name = (char *) ((token) + 1); \
while (name < (char *) end) \
{ \
if (!*name++) \
break; \
} \
token = (grub_uint32_t *) ALIGN_UP((grub_addr_t) (name), sizeof(*token))
static grub_uint32_t *get_next_node (const void *fdt, char *node_name)
{
grub_uint32_t *end = (void *) struct_end (fdt);
@@ -50,9 +60,9 @@ static grub_uint32_t *get_next_node (const void *fdt, char *node_name)
if (node_name >= (char *) end)
return NULL;
while (*node_name)
while (*node_name++)
{
if (++node_name >= (char *) end)
if (node_name >= (char *) end)
return NULL;
}
token = (grub_uint32_t *) ALIGN_UP ((grub_addr_t) node_name, 4);
@@ -73,7 +83,8 @@ static grub_uint32_t *get_next_node (const void *fdt, char *node_name)
case FDT_PROP:
/* Skip property token and following data (len, nameoff and property
value). */
token += 3 + grub_be_to_cpu32 (*(token + 1));
token += prop_entry_size(grub_be_to_cpu32(*(token + 1)))
/ sizeof(*token);
break;
case FDT_NOP:
token++;
@@ -116,12 +127,14 @@ static grub_uint32_t get_free_space (void *fdt)
static int add_subnode (void *fdt, int parentoffset, const char *name)
{
grub_uint32_t *begin = (void *) ((grub_addr_t) fdt
grub_uint32_t *token = (void *) ((grub_addr_t) fdt
+ grub_fdt_get_off_dt_struct(fdt)
+ parentoffset);
grub_uint32_t *end = (void *) struct_end (fdt);
unsigned int entry_size = node_entry_size (name);
grub_uint32_t *token = begin;
char *node_name;
SKIP_NODE_NAME(node_name, token, end);
/* Insert the new subnode just after the properties of the parent node (if
any).*/
@@ -132,28 +145,28 @@ static int add_subnode (void *fdt, int parentoffset, const char *name)
switch (grub_be_to_cpu32(*token))
{
case FDT_PROP:
/* Skip len and nameoff. */
token += 2;
/* Skip len, nameoff and property value. */
token += prop_entry_size(grub_be_to_cpu32(*(token + 1)))
/ sizeof(*token);
break;
case FDT_BEGIN_NODE:
case FDT_END_NODE:
goto insert;
case FDT_NOP:
token++;
break;
default:
/* invalid token */
return -1;
}
token++;
}
insert:
grub_memmove (token + entry_size, token,
grub_memmove (token + entry_size / sizeof(*token), token,
(grub_addr_t) end - (grub_addr_t) token);
*token = grub_cpu_to_be32(FDT_BEGIN_NODE);
token[entry_size / sizeof(*token) - 2] = 0; /* padding bytes */
grub_strcpy((char *) (token + 1), name);
token += entry_size / sizeof(*token) - 1;
*token = grub_cpu_to_be32(FDT_END_NODE);
token[entry_size / sizeof(*token) - 1] = grub_cpu_to_be32(FDT_END_NODE);
return ((grub_addr_t) token - (grub_addr_t) fdt
- grub_fdt_get_off_dt_struct(fdt));
}
@@ -175,29 +188,32 @@ static int rearrange_blocks (void *fdt, unsigned int clearance)
if ((grub_fdt_get_off_mem_rsvmap (fdt) == off_mem_rsvmap)
&& (grub_fdt_get_off_dt_struct (fdt) == off_dt_struct))
{
/* No need to allocate memory for a temporary FDT, just move the strings
block if needed. */
if (grub_fdt_get_off_dt_strings (fdt) != off_dt_strings)
grub_memmove(fdt_ptr + off_dt_strings,
fdt_ptr + grub_fdt_get_off_dt_strings (fdt),
grub_fdt_get_size_dt_strings (fdt));
return 0;
}
{
/* No need to allocate memory for a temporary FDT, just move the strings
block if needed. */
if (grub_fdt_get_off_dt_strings (fdt) != off_dt_strings)
{
grub_memmove(fdt_ptr + off_dt_strings,
fdt_ptr + grub_fdt_get_off_dt_strings (fdt),
grub_fdt_get_size_dt_strings (fdt));
grub_fdt_set_off_dt_strings (fdt, off_dt_strings);
}
return 0;
}
tmp_fdt = grub_malloc (grub_fdt_get_totalsize (fdt));
if (!tmp_fdt)
return -1;
grub_memcpy (tmp_fdt + off_mem_rsvmap,
fdt_ptr + grub_fdt_get_off_mem_rsvmap (fdt),
get_mem_rsvmap_size (fdt));
fdt_ptr + grub_fdt_get_off_mem_rsvmap (fdt),
get_mem_rsvmap_size (fdt));
grub_fdt_set_off_mem_rsvmap (fdt, off_mem_rsvmap);
grub_memcpy (tmp_fdt + off_dt_struct,
fdt_ptr + grub_fdt_get_off_dt_struct (fdt),
grub_fdt_get_size_dt_struct (fdt));
fdt_ptr + grub_fdt_get_off_dt_struct (fdt),
grub_fdt_get_size_dt_struct (fdt));
grub_fdt_set_off_dt_struct (fdt, off_dt_struct);
grub_memcpy (tmp_fdt + off_dt_strings,
fdt_ptr + grub_fdt_get_off_dt_strings (fdt),
grub_fdt_get_size_dt_strings (fdt));
fdt_ptr + grub_fdt_get_off_dt_strings (fdt),
grub_fdt_get_size_dt_strings (fdt));
grub_fdt_set_off_dt_strings (fdt, off_dt_strings);
/* Copy reordered blocks back to fdt. */
@@ -214,9 +230,12 @@ static grub_uint32_t *find_prop (void *fdt, unsigned int nodeoffset,
grub_uint32_t *prop = (void *) ((grub_addr_t) fdt
+ grub_fdt_get_off_dt_struct (fdt)
+ nodeoffset);
grub_uint32_t *end = (void *) struct_end(fdt);
grub_uint32_t nameoff;
char *node_name;
do
SKIP_NODE_NAME(node_name, prop, end);
while (prop < end - 2)
{
if (grub_be_to_cpu32(*prop) == FDT_PROP)
{
@@ -224,15 +243,19 @@ static grub_uint32_t *find_prop (void *fdt, unsigned int nodeoffset,
if ((nameoff + grub_strlen (name) < grub_fdt_get_size_dt_strings (fdt))
&& !grub_strcmp (name, (char *) fdt +
grub_fdt_get_off_dt_strings (fdt) + nameoff))
return prop;
prop += prop_entry_size(grub_be_to_cpu32(*prop + 1)) / sizeof (*prop);
{
if (prop + prop_entry_size(grub_be_to_cpu32(*(prop + 1)))
/ sizeof (*prop) >= end)
return NULL;
return prop;
}
prop += prop_entry_size(grub_be_to_cpu32(*(prop + 1))) / sizeof (*prop);
}
else if (grub_be_to_cpu32(*prop) != FDT_NOP)
else if (grub_be_to_cpu32(*prop) == FDT_NOP)
prop++;
else
return NULL;
prop++;
} while ((grub_addr_t) prop < ((grub_addr_t) fdt
+ grub_fdt_get_off_dt_struct (fdt)
+ grub_fdt_get_size_dt_struct (fdt)));
}
return NULL;
}
@@ -271,6 +294,9 @@ int grub_fdt_find_subnode (const void *fdt, unsigned int parentoffset,
token = (void *) ((grub_addr_t) fdt + grub_fdt_get_off_dt_struct(fdt)
+ parentoffset);
end = (void *) struct_end (fdt);
if ((token >= end) || (grub_be_to_cpu32(*token) != FDT_BEGIN_NODE))
return -1;
SKIP_NODE_NAME(node_name, token, end);
while (token < end)
{
switch (grub_be_to_cpu32(*token))
@@ -280,19 +306,19 @@ int grub_fdt_find_subnode (const void *fdt, unsigned int parentoffset,
if (node_name + grub_strlen (name) >= (char *) end)
return -1;
if (!grub_strcmp (node_name, name))
return (int) ((grub_addr_t) token
+ ALIGN_UP(grub_strlen (name) + 1, 4)
return (int) ((grub_addr_t) token - (grub_addr_t) fdt
- grub_fdt_get_off_dt_struct (fdt));
token = get_next_node (fdt, node_name);
if (!token)
return -1;
break;
case FDT_END_NODE:
return -1;
case FDT_PROP:
/* Skip property token and following data (len, nameoff and property
value). */
token += 3 + grub_be_to_cpu32 (*(token + 1));
if (token >= end - 1)
return -1;
token += prop_entry_size(grub_be_to_cpu32(*(token + 1)))
/ sizeof(*token);
break;
case FDT_NOP:
token++;
@@ -327,7 +353,10 @@ int grub_fdt_set_prop (void *fdt, unsigned int nodeoffset, const char *name,
int prop_name_present = 0;
grub_uint32_t nameoff = 0;
if ((nodeoffset >= grub_fdt_get_size_dt_struct (fdt)) || (nodeoffset & 0x3))
if ((nodeoffset >= grub_fdt_get_size_dt_struct (fdt)) || (nodeoffset & 0x3)
|| (grub_be_to_cpu32(*(grub_uint32_t *) ((grub_addr_t) fdt
+ grub_fdt_get_off_dt_struct (fdt) + nodeoffset))
!= FDT_BEGIN_NODE))
return -1;
prop = find_prop (fdt, nodeoffset, name);
if (prop)
@@ -339,7 +368,7 @@ int grub_fdt_set_prop (void *fdt, unsigned int nodeoffset, const char *name,
prop_name_present = 1;
for (i = 0; i < prop_len / sizeof(grub_uint32_t); i++)
*(prop + 3 + i) = grub_cpu_to_be32 (FDT_NOP);
if (len > prop_len)
if (len > ALIGN_UP(prop_len, sizeof(grub_uint32_t)))
{
/* Length of new property value is greater than the space allocated
for the current value: a new entry needs to be created, so save the
@@ -371,19 +400,24 @@ int grub_fdt_set_prop (void *fdt, unsigned int nodeoffset, const char *name,
+ grub_strlen (name) + 1);
}
if (!prop) {
prop = (void *) ((grub_addr_t) fdt + grub_fdt_get_off_dt_struct (fdt)
+ nodeoffset);
grub_memmove (prop + prop_entry_size(len), prop,
grub_fdt_get_size_dt_struct (fdt) - nodeoffset);
char *node_name = (char *) ((grub_addr_t) fdt
+ grub_fdt_get_off_dt_struct (fdt) + nodeoffset
+ sizeof(grub_uint32_t));
prop = (void *) (node_name + ALIGN_UP(grub_strlen(node_name) + 1, 4));
grub_memmove (prop + prop_entry_size(len) / sizeof(*prop), prop,
struct_end(fdt) - (grub_addr_t) prop);
grub_fdt_set_size_dt_struct (fdt, grub_fdt_get_size_dt_struct (fdt)
+ prop_entry_size(len));
*prop = grub_cpu_to_be32 (FDT_PROP);
*(prop + 1) = grub_cpu_to_be32 (len);
*(prop + 2) = grub_cpu_to_be32 (nameoff);
/* Insert padding bytes at the end of the value; if they are not needed,
they will be overwritten by the follozing memcpy. */
*(prop + prop_entry_size(len) / sizeof(grub_uint32_t) - 1) = 0;
grub_memcpy (prop + 3, val, len);
}
*(prop + 1) = grub_cpu_to_be32 (len);
/* Insert padding bytes at the end of the value; if they are not needed, they
will be overwritten by the following memcpy. */
*(prop + prop_entry_size(len) / sizeof(grub_uint32_t) - 1) = 0;
grub_memcpy (prop + 3, val, len);
return 0;
}
+51 -33
View File
@@ -70,13 +70,14 @@ static struct legacy_command legacy_commands[] =
"Print the blocklist notation of the file FILE."},
{"boot", "boot\n", NULL, 0, 0, {}, 0, 0,
"Boot the OS/chain-loader which has been loaded."},
{"bootp", "net_bootp; net_ls_addr; if [ x%s = x--with-configfile ]; then "
{"bootp", "net_bootp; net_ls_addr; echo $\"" N_("Default server is ${net_default_server}") "\"; if [ x%s = x--with-configfile ]; then "
"if net_get_dhcp_option configfile_name pxe 150 string; then "
"configfile $configfile_name; fi; fi\n", NULL, 0, 1,
{TYPE_WITH_CONFIGFILE_OPTION}, FLAG_IGNORE_REST, "[--with-configfile]",
"Initialize a network device via BOOTP. If the option `--with-configfile'"
" is given, try to load a configuration file specified by the 150 vendor"
" tag."},
/* FIXME: border unsupported. */
{"cat", "cat '%s'\n", NULL, 0, 1, {TYPE_FILE}, 0, "FILE",
"Print the contents of the file FILE."},
{"chainloader", "chainloader %s '%s'\n", NULL, 0,
@@ -295,6 +296,7 @@ static struct legacy_command legacy_commands[] =
" STOP is the length of stop bit(s). The option --device can be used only"
" in the grub shell, which specifies the file name of a tty device. The"
" default values are COM1, 9600, 8N1."},
/* FIXME: shade unsupported. */
/* FIXME: silent unsupported. */
/* FIXME: splashimage unsupported. */
/* FIXME: setkey unsupported. */ /* NUL_TERMINATE */
@@ -305,7 +307,7 @@ static struct legacy_command legacy_commands[] =
/* FIXME: graphics unsupported. */
{"terminal", NULL, NULL, 0, 0, {}, FLAG_TERMINAL | FLAG_IGNORE_REST,
"[--dumb] [--no-echo] [--no-edit] [--timeout=SECS] [--lines=LINES] "
"[--silent] [console] [serial] [hercules]",
"[--silent] [console] [serial] [hercules] [graphics]",
"Select a terminal. When multiple terminals are specified, wait until"
" you push any key to continue. If both console and serial are specified,"
" the terminal to which you input a key first will be selected. If no"
@@ -346,6 +348,7 @@ static struct legacy_command legacy_commands[] =
FLAG_FALLBACK, NULL, NULL}
/* FIXME: verbose unsupported. */
/* FIXME: version unsupported. */
/* FIXME: viewport unsupported. */
};
char *
@@ -385,6 +388,29 @@ adjust_file (const char *in, grub_size_t len)
if (*ptr == '\'' || *ptr == '\\')
overhead++;
comma = ptr;
if (*comma == ')' && comma - in == 3
&& in[1] == 'n' && in[2] == 'd')
{
rest = comma + 1;
for (ptr = rest; ptr < in + len && *ptr; ptr++)
if (*ptr == '\'' || *ptr == '\\')
overhead++;
ret = grub_malloc (ptr - in + overhead + 15);
if (!ret)
return NULL;
outptr = grub_stpcpy (ret, "(tftp)");;
for (ptr = rest; ptr < in + len; ptr++)
{
if (*ptr == '\'' || *ptr == '\\')
*outptr++ = '\\';
*outptr++ = *ptr;
}
*outptr = 0;
return ret;
}
if (*comma != ',')
return grub_legacy_escape (in, len);
part = grub_strtoull (comma + 1, (char **) &rest, 0);
@@ -398,7 +424,7 @@ adjust_file (const char *in, grub_size_t len)
overhead++;
/* 35 is enough for any 2 numbers. */
ret = grub_malloc (ptr - in + overhead + 35);
ret = grub_malloc (ptr - in + overhead + 35 + 5);
if (!ret)
return NULL;
@@ -521,9 +547,9 @@ grub_legacy_parse (const char *buf, char **entryname, char **suffix)
int no_echo = 0, no_edit = 0;
#endif
int hercules = 0;
int console = 0, serial = 0;
int console = 0, serial = 0, graphics = 0;
/* Big enough for any possible resulting command. */
char outbuf[256] = "";
char outbuf[512] = "";
char *outptr;
while (*ptr)
{
@@ -555,46 +581,38 @@ grub_legacy_parse (const char *buf, char **entryname, char **suffix)
serial = 1;
if (grub_memcmp (ptr, "hercules", sizeof ("hercules") - 1) == 0)
hercules = 1;
if (grub_memcmp (ptr, "graphics", sizeof ("graphics") - 1) == 0)
graphics = 1;
while (*ptr && !grub_isspace (*ptr))
ptr++;
while (*ptr && grub_isspace (*ptr))
ptr++;
}
if (!console && !serial)
if (!console && !serial && !hercules && !graphics)
return grub_strdup ("terminal_input; terminal_output; terminfo\n");
grub_strcpy (outbuf, "terminal_input ");
outptr = outbuf + grub_strlen (outbuf);
outptr = outbuf;
if (graphics)
outptr = grub_stpcpy (outptr, "insmod all_video; ");
outptr = grub_stpcpy (outptr, "terminal_input ");
if (serial)
{
grub_strcpy (outptr, "serial ");
outptr += grub_strlen (outptr);
}
if (console || hercules)
{
grub_strcpy (outptr, "console ");
outptr += grub_strlen (outptr);
}
grub_strcpy (outptr, "; terminal_output ");
outptr += grub_strlen (outptr);
outptr = grub_stpcpy (outptr, "serial ");
if (console || hercules || graphics)
outptr = grub_stpcpy (outptr, "console ");
outptr = grub_stpcpy (outptr, "; terminal_output ");
if (serial)
{
grub_strcpy (outptr, "serial ");
outptr += grub_strlen (outptr);
}
outptr = grub_stpcpy (outptr, "serial ");
if (console)
{
grub_strcpy (outptr, "console ");
outptr += grub_strlen (outptr);
}
outptr = grub_stpcpy (outptr, "console ");
if (hercules)
{
grub_strcpy (outptr, "mda_text ");
outptr += grub_strlen (outptr);
}
grub_strcpy (outptr, "; ");
outptr += grub_strlen (outptr);
outptr = grub_stpcpy (outptr, "mda_text ");
if (graphics)
outptr = grub_stpcpy (outptr, "gfxterm ");
outptr = grub_stpcpy (outptr, "; ");
*outptr = '\0';
if (serial)
{
grub_snprintf (outptr, outbuf + sizeof (outbuf) - outptr,
File diff suppressed because it is too large. Load diff
+3 -2
View File
@@ -35,7 +35,7 @@ libcipher_la_DEPENDENCIES = $(GCRYPT_MODULES)
libcipher_la_LIBADD = $(GCRYPT_MODULES)
libcipher_la_SOURCES = \
cipher.c pubkey.c ac.c md.c \
cipher.c pubkey.c ac.c md.c kdf.c \
hmac-tests.c \
bithelp.h \
primegen.c \
@@ -51,6 +51,7 @@ des.c \
dsa.c \
elgamal.c \
ecc.c \
idea.c \
md4.c \
md5.c \
rijndael.c rijndael-tables.h \
@@ -68,7 +69,7 @@ rfc2268.c \
camellia.c camellia.h camellia-glue.c
if ENABLE_O_FLAG_MUNGING
o_flag_munging = sed -e 's/-O[2-9s]*/-O1/g'
o_flag_munging = sed -e 's/-O\([2-9s][2-9s]*\)/-O1/' -e 's/-Ofast/-O1/g'
else
o_flag_munging = cat
endif
-1
View File
@@ -153,4 +153,3 @@ gcry_cipher_spec_t _gcry_cipher_spec_arcfour =
"ARCFOUR", NULL, NULL, 1, 128, sizeof (ARCFOUR_context),
arcfour_setkey, NULL, NULL, encrypt_stream, encrypt_stream,
};
+109 -63
View File
@@ -1,6 +1,6 @@
/* cipher.c - cipher dispatcher
* Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003
* 2005, 2007, 2008, 2009 Free Software Foundation, Inc.
* 2005, 2007, 2008, 2009, 2011 Free Software Foundation, Inc.
*
* This file is part of Libgcrypt.
*
@@ -33,9 +33,12 @@
#define CTX_MAGIC_NORMAL 0x24091964
#define CTX_MAGIC_SECURE 0x46919042
/* Try to use 16 byte aligned cipher context for better performance.
We use the aligned attribute, thus it is only possible to implement
this with gcc. */
#undef NEED_16BYTE_ALIGNED_CONTEXT
#if defined (__i386__) && SIZEOF_UNSIGNED_LONG == 4 && defined (__GNUC__)
#define NEED_16BYTE_ALIGNED_CONTEXT 1
#if defined (__GNUC__)
# define NEED_16BYTE_ALIGNED_CONTEXT 1
#endif
/* A dummy extraspec so that we do not need to tests the extraspec
@@ -108,6 +111,10 @@ static struct cipher_table_entry
&dummy_extra_spec, GCRY_CIPHER_CAMELLIA192 },
{ &_gcry_cipher_spec_camellia256,
&dummy_extra_spec, GCRY_CIPHER_CAMELLIA256 },
#endif
#ifdef USE_IDEA
{ &_gcry_cipher_spec_idea,
&dummy_extra_spec, GCRY_CIPHER_IDEA },
#endif
{ NULL }
};
@@ -137,13 +144,14 @@ static int default_ciphers_registered;
while (0)
/* A VIA processor with the Padlock engine requires an alignment of
most data on a 16 byte boundary. Because we trick out the compiler
while allocating the context, the align attribute as used in
rijndael.c does not work on its own. Thus we need to make sure
that the entire context structure is a aligned on that boundary.
We achieve this by defining a new type and use that instead of our
usual alignment type. */
/* A VIA processor with the Padlock engine as well as the Intel AES_NI
instructions require an alignment of most data on a 16 byte
boundary. Because we trick out the compiler while allocating the
context, the align attribute as used in rijndael.c does not work on
its own. Thus we need to make sure that the entire context
structure is a aligned on that boundary. We achieve this by
defining a new type and use that instead of our usual alignment
type. */
typedef union
{
PROPERLY_ALIGNED_TYPE foo;
@@ -186,6 +194,9 @@ struct gcry_cipher_handle
void (*cbc_dec)(void *context, unsigned char *iv,
void *outbuf_arg, const void *inbuf_arg,
unsigned int nblocks);
void (*ctr_enc)(void *context, unsigned char *iv,
void *outbuf_arg, const void *inbuf_arg,
unsigned int nblocks);
} bulk;
@@ -197,19 +208,24 @@ struct gcry_cipher_handle
unsigned int iv:1; /* Set to 1 if a IV has been set. */
} marks;
/* The initialization vector. To help code optimization we make
sure that it is aligned on an unsigned long and u32 boundary. */
/* The initialization vector. For best performance we make sure
that it is properly aligned. In particular some implementations
of bulk operations expect an 16 byte aligned IV. */
union {
unsigned long dummy_iv;
u32 dummy_u32_iv;
cipher_context_alignment_t iv_align;
unsigned char iv[MAX_BLOCKSIZE];
} u_iv;
/* The counter for CTR mode. This field is also used by AESWRAP and
thus we can't use the U_IV union. */
union {
cipher_context_alignment_t iv_align;
unsigned char ctr[MAX_BLOCKSIZE];
} u_ctr;
/* Space to save an IV or CTR for chaining operations. */
unsigned char lastiv[MAX_BLOCKSIZE];
int unused; /* Number of unused bytes in the IV. */
unsigned char ctr[MAX_BLOCKSIZE]; /* For Counter (CTR) mode. */
int unused; /* Number of unused bytes in LASTIV. */
/* What follows are two contexts of the cipher in use. The first
one needs to be aligned well enough for the cipher operation
@@ -598,10 +614,8 @@ check_cipher_algo (int algorithm)
}
/* Return the standard length of the key for the cipher algorithm with
the identifier ALGORITHM. This function expects a valid algorithm
and will abort if the algorithm is not available or the length of
the key is not known. */
/* Return the standard length in bits of the key for the cipher
algorithm with the identifier ALGORITHM. */
static unsigned int
cipher_get_keylen (int algorithm)
{
@@ -619,17 +633,13 @@ cipher_get_keylen (int algorithm)
log_bug ("cipher %d w/o key length\n", algorithm);
_gcry_module_release (cipher);
}
else
log_bug ("cipher %d not found\n", algorithm);
ath_mutex_unlock (&ciphers_registered_lock);
return len;
}
/* Return the block length of the cipher algorithm with the identifier
ALGORITHM. This function expects a valid algorithm and will abort
if the algorithm is not available or the length of the key is not
known. */
ALGORITHM. This function return 0 for an invalid algorithm. */
static unsigned int
cipher_get_blocksize (int algorithm)
{
@@ -647,8 +657,6 @@ cipher_get_blocksize (int algorithm)
log_bug ("cipher %d w/o blocksize\n", algorithm);
_gcry_module_release (cipher);
}
else
log_bug ("cipher %d not found\n", algorithm);
ath_mutex_unlock (&ciphers_registered_lock);
return len;
@@ -774,7 +782,7 @@ gcry_cipher_open (gcry_cipher_hd_t *handle,
h = gcry_calloc (1, size);
if (! h)
err = gpg_err_code_from_errno (errno);
err = gpg_err_code_from_syserror ();
else
{
size_t off = 0;
@@ -810,6 +818,7 @@ gcry_cipher_open (gcry_cipher_hd_t *handle,
h->bulk.cfb_dec = _gcry_aes_cfb_dec;
h->bulk.cbc_enc = _gcry_aes_cbc_enc;
h->bulk.cbc_dec = _gcry_aes_cbc_dec;
h->bulk.ctr_enc = _gcry_aes_ctr_enc;
break;
#endif /*USE_AES*/
@@ -932,7 +941,7 @@ cipher_reset (gcry_cipher_hd_t c)
memset (&c->marks, 0, sizeof c->marks);
memset (c->u_iv.iv, 0, c->cipher->blocksize);
memset (c->lastiv, 0, c->cipher->blocksize);
memset (c->ctr, 0, c->cipher->blocksize);
memset (c->u_ctr.ctr, 0, c->cipher->blocksize);
}
@@ -1437,35 +1446,72 @@ do_ctr_encrypt (gcry_cipher_hd_t c,
const unsigned char *inbuf, unsigned int inbuflen)
{
unsigned int n;
unsigned char tmp[MAX_BLOCKSIZE];
int i;
unsigned int blocksize = c->cipher->blocksize;
unsigned int nblocks;
if (outbuflen < inbuflen)
return GPG_ERR_BUFFER_TOO_SHORT;
if ((inbuflen % blocksize))
return GPG_ERR_INV_LENGTH;
for (n=0; n < inbuflen; n++)
/* First process a left over encrypted counter. */
if (c->unused)
{
if ((n % blocksize) == 0)
{
c->cipher->encrypt (&c->context.c, tmp, c->ctr);
for (i = blocksize; i > 0; i--)
{
c->ctr[i-1]++;
if (c->ctr[i-1] != 0)
break;
}
}
/* XOR input with encrypted counter and store in output. */
outbuf[n] = inbuf[n] ^ tmp[n % blocksize];
gcry_assert (c->unused < blocksize);
i = blocksize - c->unused;
for (n=0; c->unused && n < inbuflen; c->unused--, n++, i++)
{
/* XOR input with encrypted counter and store in output. */
outbuf[n] = inbuf[n] ^ c->lastiv[i];
}
inbuf += n;
outbuf += n;
inbuflen -= n;
}
/* Use a bulk method if available. */
nblocks = inbuflen / blocksize;
if (nblocks && c->bulk.ctr_enc)
{
c->bulk.ctr_enc (&c->context.c, c->u_ctr.ctr, outbuf, inbuf, nblocks);
inbuf += nblocks * blocksize;
outbuf += nblocks * blocksize;
inbuflen -= nblocks * blocksize;
}
/* If we don't have a bulk method use the standard method. We also
use this method for the a remaining partial block. */
if (inbuflen)
{
unsigned char tmp[MAX_BLOCKSIZE];
for (n=0; n < inbuflen; n++)
{
if ((n % blocksize) == 0)
{
c->cipher->encrypt (&c->context.c, tmp, c->u_ctr.ctr);
for (i = blocksize; i > 0; i--)
{
c->u_ctr.ctr[i-1]++;
if (c->u_ctr.ctr[i-1] != 0)
break;
}
}
/* XOR input with encrypted counter and store in output. */
outbuf[n] = inbuf[n] ^ tmp[n % blocksize];
}
/* Save the unused bytes of the counter. */
n %= blocksize;
c->unused = (blocksize - n) % blocksize;
if (c->unused)
memcpy (c->lastiv+n, tmp+n, c->unused);
wipememory (tmp, sizeof tmp);
}
wipememory (tmp, sizeof tmp);
return 0;
}
@@ -1513,7 +1559,7 @@ do_aeswrap_encrypt (gcry_cipher_hd_t c, byte *outbuf, unsigned int outbuflen,
r = outbuf;
a = outbuf; /* We store A directly in OUTBUF. */
b = c->ctr; /* B is also used to concatenate stuff. */
b = c->u_ctr.ctr; /* B is also used to concatenate stuff. */
/* If an IV has been set we use that IV as the Alternative Initial
Value; if it has not been set we use the standard value. */
@@ -1589,7 +1635,7 @@ do_aeswrap_decrypt (gcry_cipher_hd_t c, byte *outbuf, unsigned int outbuflen,
r = outbuf;
a = c->lastiv; /* We use c->LASTIV as buffer for A. */
b = c->ctr; /* B is also used to concatenate stuff. */
b = c->u_ctr.ctr; /* B is also used to concatenate stuff. */
/* Copy the inbuf to the outbuf and save A. */
memcpy (a, inbuf, 8);
@@ -1857,9 +1903,15 @@ gpg_error_t
_gcry_cipher_setctr (gcry_cipher_hd_t hd, const void *ctr, size_t ctrlen)
{
if (ctr && ctrlen == hd->cipher->blocksize)
memcpy (hd->ctr, ctr, hd->cipher->blocksize);
{
memcpy (hd->u_ctr.ctr, ctr, hd->cipher->blocksize);
hd->unused = 0;
}
else if (!ctr || !ctrlen)
memset (hd->ctr, 0, hd->cipher->blocksize);
{
memset (hd->u_ctr.ctr, 0, hd->cipher->blocksize);
hd->unused = 0;
}
else
return gpg_error (GPG_ERR_INV_ARG);
return 0;
@@ -1918,12 +1970,7 @@ gcry_cipher_ctl( gcry_cipher_hd_t h, int cmd, void *buffer, size_t buflen)
break;
case GCRYCTL_SET_CTR: /* Deprecated; use gcry_cipher_setctr. */
if (buffer && buflen == h->cipher->blocksize)
memcpy (h->ctr, buffer, h->cipher->blocksize);
else if (buffer == NULL || buflen == 0)
memset (h->ctr, 0, h->cipher->blocksize);
else
rc = GPG_ERR_INV_ARG;
rc = gpg_err_code (_gcry_cipher_setctr (h, buffer, buflen));
break;
case 61: /* Disable weak key detection (private). */
@@ -2033,8 +2080,7 @@ gcry_cipher_algo_info (int algo, int what, void *buffer, size_t *nbytes)
if ((ui > 0) && (ui <= 512))
*nbytes = (size_t) ui / 8;
else
/* The only reason is an invalid algo or a strange
blocksize. */
/* The only reason for an error is an invalid algo. */
err = GPG_ERR_CIPHER_ALGO;
}
break;
+18 -7
View File
@@ -141,6 +141,11 @@ gen_k( gcry_mpi_t q )
unsigned int nbytes = (nbits+7)/8;
char *rndbuf = NULL;
/* To learn why we don't use mpi_mod to get the requested bit size,
read the paper: "The Insecurity of the Digital Signature
Algorithm with Partially Known Nonces" by Nguyen and Shparlinski.
Journal of Cryptology, New York. Vol 15, nr 3 (2003) */
if ( DBG_CIPHER )
log_debug("choosing a random k ");
for (;;)
@@ -156,13 +161,20 @@ gen_k( gcry_mpi_t q )
else
{ /* Change only some of the higher bits. We could improve
this by directly requesting more memory at the first call
to get_random_bytes() and use this the here maybe it is
easier to do this directly in random.c. */
to get_random_bytes() and use these extra bytes here.
However the required management code is more complex and
thus we better use this simple method. */
char *pp = gcry_random_bytes_secure( 4, GCRY_STRONG_RANDOM );
memcpy( rndbuf,pp, 4 );
gcry_free(pp);
}
_gcry_mpi_set_buffer( k, rndbuf, nbytes, 0 );
/* Make sure we have the requested number of bits. This code
looks a bit funny but it is easy to understand if you
consider that mpi_set_highbit clears all higher bits. We
don't have a clear_highbit, thus we first set the high bit
and then clear it again. */
if ( mpi_test_bit( k, nbits-1 ) )
mpi_set_highbit( k, nbits-1 );
else
@@ -1031,11 +1043,11 @@ static const char *
selftest_sign_1024 (gcry_sexp_t pkey, gcry_sexp_t skey)
{
static const char sample_data[] =
"(data (flags pkcs1)"
" (hash sha1 #a0b1c2d3e4f500102030405060708090a1b2c3d4#))";
"(data (flags raw)"
" (value #a0b1c2d3e4f500102030405060708090a1b2c3d4#))";
static const char sample_data_bad[] =
"(data (flags pkcs1)"
" (hash sha1 #a0b1c2d3e4f510102030405060708090a1b2c3d4#))";
"(data (flags raw)"
" (value #a0b1c2d3e4f510102030405060708090a1b2c3d4#))";
const char *errtxt = NULL;
gcry_error_t err;
@@ -1179,4 +1191,3 @@ pk_extra_spec_t _gcry_pubkey_extraspec_dsa =
run_selftests,
dsa_generate_ext
};
+479 -89
View File
@@ -1,5 +1,5 @@
/* ecc.c - Elliptic Curve Cryptography
Copyright (C) 2007, 2008, 2010 Free Software Foundation, Inc.
Copyright (C) 2007, 2008, 2010, 2011 Free Software Foundation, Inc.
This file is part of Libgcrypt.
@@ -33,20 +33,21 @@
up. In fact there is not much left of the orginally code except for
some variable names and the text book implementaion of the sign and
verification algorithms. The arithmetic functions have entirely
been rewritten and moved to mpi/ec.c. */
been rewritten and moved to mpi/ec.c.
ECDH encrypt and decrypt code written by Andrey Jivsov,
*/
/* TODO:
- If we support point compression we need to decide how to compute
the keygrip - it should not change due to compression.
- If we support point compression we need to uncompress before
computing the keygrip
- In mpi/ec.c we use mpi_powm for x^2 mod p: Either implement a
special case in mpi_powm or check whether mpi_mulm is faster.
- Decide whether we should hide the mpi_point_t definition.
- Support more than just ECDSA.
*/
@@ -59,7 +60,6 @@
#include "mpi.h"
#include "cipher.h"
/* Definition of a curve. */
typedef struct
{
@@ -68,6 +68,7 @@ typedef struct
gcry_mpi_t b; /* Second coefficient of the Weierstrass equation. */
mpi_point_t G; /* Base point (generator). */
gcry_mpi_t n; /* Order of G. */
const char *name; /* Name of curve or NULL. */
} elliptic_curve_t;
@@ -120,11 +121,7 @@ static const struct
{ NULL, NULL}
};
/* This static table defines all available curves. */
static const struct
{
typedef struct {
const char *desc; /* Description of the curve. */
unsigned int nbits; /* Number of bits. */
unsigned int fips:1; /* True if this is a FIPS140-2 approved curve. */
@@ -132,7 +129,10 @@ static const struct
const char *a, *b; /* The coefficients. */
const char *n; /* The order of the base point. */
const char *g_x, *g_y; /* Base point. */
} domain_parms[] =
} ecc_domain_parms_t;
/* This static table defines all available curves. */
static const ecc_domain_parms_t domain_parms[] =
{
{
"NIST P-192", 192, 1,
@@ -369,7 +369,6 @@ curve_copy (elliptic_curve_t E)
}
/* Helper to scan a hex string. */
static gcry_mpi_t
scanval (const char *string)
@@ -412,9 +411,6 @@ gen_y_2 (gcry_mpi_t x, elliptic_curve_t *base)
}
/* Generate a random secret scalar k with an order of p
At the beginning this was identical to the code is in elgamal.c.
@@ -428,7 +424,8 @@ gen_k (gcry_mpi_t p, int security_level)
nbits = mpi_get_nbits (p);
k = mpi_snew (nbits);
if (DBG_CIPHER)
log_debug ("choosing a random k of %u bits\n", nbits);
log_debug ("choosing a random k of %u bits at seclevel %d\n",
nbits, security_level);
gcry_mpi_randomize (k, nbits, security_level);
@@ -437,23 +434,27 @@ gen_k (gcry_mpi_t p, int security_level)
return k;
}
/****************
* Generate the crypto system setup.
* As of now the fix NIST recommended values are used.
* The subgroup generator point is in another function: gen_big_point.
*/
/* Generate the crypto system setup. This function takes the NAME of
a curve or the desired number of bits and stores at R_CURVE the
parameters of the named curve or those of a suitable curve. The
chosen number of bits is stored on R_NBITS. */
static gpg_err_code_t
generate_curve (unsigned int nbits, const char *name,
elliptic_curve_t *curve, unsigned int *r_nbits)
fill_in_curve (unsigned int nbits, const char *name,
elliptic_curve_t *curve, unsigned int *r_nbits)
{
int idx, aliasno;
const char *resname = NULL; /* Set to a found curve name. */
if (name)
{
/* First check nor native curves. */
/* First check our native curves. */
for (idx = 0; domain_parms[idx].desc; idx++)
if (!strcmp (name, domain_parms[idx].desc))
break;
{
resname = domain_parms[idx].desc;
break;
}
/* If not found consult the alias table. */
if (!domain_parms[idx].desc)
{
@@ -465,7 +466,10 @@ generate_curve (unsigned int nbits, const char *name,
for (idx = 0; domain_parms[idx].desc; idx++)
if (!strcmp (curve_aliases[aliasno].name,
domain_parms[idx].desc))
break;
{
resname = domain_parms[idx].desc;
break;
}
}
}
}
@@ -484,7 +488,6 @@ generate_curve (unsigned int nbits, const char *name,
if (fips_mode () && !domain_parms[idx].fips )
return GPG_ERR_NOT_SUPPORTED;
*r_nbits = domain_parms[idx].nbits;
curve->p = scanval (domain_parms[idx].p);
curve->a = scanval (domain_parms[idx].a);
@@ -493,6 +496,7 @@ generate_curve (unsigned int nbits, const char *name,
curve->G.x = scanval (domain_parms[idx].g_x);
curve->G.y = scanval (domain_parms[idx].g_y);
curve->G.z = mpi_alloc_set_ui (1);
curve->name = resname;
return 0;
}
@@ -506,7 +510,8 @@ static gpg_err_code_t
generate_key (ECC_secret_key *sk, unsigned int nbits, const char *name,
int transient_key,
gcry_mpi_t g_x, gcry_mpi_t g_y,
gcry_mpi_t q_x, gcry_mpi_t q_y)
gcry_mpi_t q_x, gcry_mpi_t q_y,
const char **r_usedcurve)
{
gpg_err_code_t err;
elliptic_curve_t E;
@@ -515,25 +520,26 @@ generate_key (ECC_secret_key *sk, unsigned int nbits, const char *name,
mpi_ec_t ctx;
gcry_random_level_t random_level;
err = generate_curve (nbits, name, &E, &nbits);
*r_usedcurve = NULL;
err = fill_in_curve (nbits, name, &E, &nbits);
if (err)
return err;
if (DBG_CIPHER)
{
log_mpidump ("ecc generation p", E.p);
log_mpidump ("ecc generation a", E.a);
log_mpidump ("ecc generation b", E.b);
log_mpidump ("ecc generation n", E.n);
log_mpidump ("ecc generation Gx", E.G.x);
log_mpidump ("ecc generation Gy", E.G.y);
log_mpidump ("ecc generation Gz", E.G.z);
log_mpidump ("ecgen curve p", E.p);
log_mpidump ("ecgen curve a", E.a);
log_mpidump ("ecgen curve b", E.b);
log_mpidump ("ecgen curve n", E.n);
log_mpidump ("ecgen curve Gx", E.G.x);
log_mpidump ("ecgen curve Gy", E.G.y);
log_mpidump ("ecgen curve Gz", E.G.z);
if (E.name)
log_debug ("ecgen curve used: %s\n", E.name);
}
random_level = transient_key ? GCRY_STRONG_RANDOM : GCRY_VERY_STRONG_RANDOM;
if (DBG_CIPHER)
log_debug ("choosing a random x of size %u%s\n", nbits,
transient_key? " (transient-key)":"");
d = gen_k (E.n, random_level);
/* Compute Q. */
@@ -556,27 +562,29 @@ generate_key (ECC_secret_key *sk, unsigned int nbits, const char *name,
if (g_x && g_y)
{
if (_gcry_mpi_ec_get_affine (g_x, g_y, &sk->E.G, ctx))
log_fatal ("ecc generate: Failed to get affine coordinates\n");
log_fatal ("ecgen: Failed to get affine coordinates\n");
}
if (q_x && q_y)
{
if (_gcry_mpi_ec_get_affine (q_x, q_y, &sk->Q, ctx))
log_fatal ("ecc generate: Failed to get affine coordinates\n");
log_fatal ("ecgen: Failed to get affine coordinates\n");
}
_gcry_mpi_ec_free (ctx);
point_free (&Q);
mpi_free (d);
*r_usedcurve = E.name;
curve_free (&E);
/* Now we can test our keys (this should never fail!). */
/* Now we can test our keys (this should never fail!). */
test_keys (sk, nbits - 64);
return 0;
}
/****************
/*
* To verify correct skey it use a random information.
* First, encrypt and decrypt this dummy value,
* test if the information is recuperated.
@@ -626,54 +634,56 @@ test_keys (ECC_secret_key *sk, unsigned int nbits)
mpi_free (test);
}
/****************
/*
* To check the validity of the value, recalculate the correspondence
* between the public value and the secret one.
*/
static int
check_secret_key (ECC_secret_key * sk)
{
int rc = 1;
mpi_point_t Q;
gcry_mpi_t y_2, y2 = mpi_alloc (0);
mpi_ec_t ctx;
gcry_mpi_t y_2, y2;
mpi_ec_t ctx = NULL;
point_init (&Q);
/* ?primarity test of 'p' */
/* (...) //!! */
/* G in E(F_p) */
y_2 = gen_y_2 (sk->E.G.x, &sk->E); /* y^2=x^3+a*x+b */
y2 = mpi_alloc (0);
mpi_mulm (y2, sk->E.G.y, sk->E.G.y, sk->E.p); /* y^2=y*y */
if (mpi_cmp (y_2, y2))
{
if (DBG_CIPHER)
log_debug ("Bad check: Point 'G' does not belong to curve 'E'!\n");
return (1);
goto leave;
}
/* G != PaI */
if (!mpi_cmp_ui (sk->E.G.z, 0))
{
if (DBG_CIPHER)
log_debug ("Bad check: 'G' cannot be Point at Infinity!\n");
return (1);
goto leave;
}
point_init (&Q);
ctx = _gcry_mpi_ec_init (sk->E.p, sk->E.a);
_gcry_mpi_ec_mul_point (&Q, sk->E.n, &sk->E.G, ctx);
if (mpi_cmp_ui (Q.z, 0))
{
if (DBG_CIPHER)
log_debug ("check_secret_key: E is not a curve of order n\n");
point_free (&Q);
_gcry_mpi_ec_free (ctx);
return 1;
goto leave;
}
/* pubkey cannot be PaI */
if (!mpi_cmp_ui (sk->Q.z, 0))
{
if (DBG_CIPHER)
log_debug ("Bad check: Q can not be a Point at Infinity!\n");
_gcry_mpi_ec_free (ctx);
return (1);
goto leave;
}
/* pubkey = [d]G over E */
_gcry_mpi_ec_mul_point (&Q, sk->d, &sk->E.G, ctx);
@@ -682,12 +692,16 @@ check_secret_key (ECC_secret_key * sk)
if (DBG_CIPHER)
log_debug
("Bad check: There is NO correspondence between 'd' and 'Q'!\n");
_gcry_mpi_ec_free (ctx);
return (1);
goto leave;
}
rc = 0; /* Okay. */
leave:
_gcry_mpi_ec_free (ctx);
mpi_free (y2);
mpi_free (y_2);
point_free (&Q);
return 0;
return rc;
}
@@ -703,6 +717,9 @@ sign (gcry_mpi_t input, ECC_secret_key *skey, gcry_mpi_t r, gcry_mpi_t s)
mpi_point_t I;
mpi_ec_t ctx;
if (DBG_CIPHER)
log_mpidump ("ecdsa sign hash ", input );
k = NULL;
dr = mpi_alloc (0);
sum = mpi_alloc (0);
@@ -741,6 +758,12 @@ sign (gcry_mpi_t input, ECC_secret_key *skey, gcry_mpi_t r, gcry_mpi_t s)
mpi_mulm (s, k_1, sum, skey->E.n); /* s = k^(-1)*(hash+(d*r)) mod n */
}
if (DBG_CIPHER)
{
log_mpidump ("ecdsa sign result r ", r);
log_mpidump ("ecdsa sign result s ", s);
}
leave:
_gcry_mpi_ec_free (ctx);
point_free (&I);
@@ -753,6 +776,7 @@ sign (gcry_mpi_t input, ECC_secret_key *skey, gcry_mpi_t r, gcry_mpi_t s)
return err;
}
/*
* Check if R and S verifies INPUT.
*/
@@ -824,10 +848,10 @@ verify (gcry_mpi_t input, ECC_public_key *pkey, gcry_mpi_t r, gcry_mpi_t s)
{
if (DBG_CIPHER)
{
log_mpidump (" x", x);
log_mpidump (" y", y);
log_mpidump (" r", r);
log_mpidump (" s", s);
log_mpidump (" x", x);
log_mpidump (" y", y);
log_mpidump (" r", r);
log_mpidump (" s", s);
log_debug ("ecc verify: Not verified\n");
}
err = GPG_ERR_BAD_SIGNATURE;
@@ -850,7 +874,7 @@ verify (gcry_mpi_t input, ECC_public_key *pkey, gcry_mpi_t r, gcry_mpi_t s)
}
/*********************************************
************** interface ******************
*********************************************/
@@ -889,12 +913,10 @@ ec2os (gcry_mpi_t x, gcry_mpi_t y, gcry_mpi_t p)
log_fatal ("mpi_scan failed: %s\n", gpg_strerror (err));
gcry_free (buf);
mpi_free (x);
mpi_free (y);
return result;
}
/* RESULT must have been initialized and is set on success to the
point given by VALUE. */
static gcry_error_t
@@ -967,10 +989,10 @@ ecc_generate_ext (int algo, unsigned int nbits, unsigned long evalue,
char *curve_name = NULL;
gcry_sexp_t l1;
int transient_key = 0;
const char *usedcurve = NULL;
(void)algo;
(void)evalue;
(void)r_extrainfo;
if (genparms)
{
@@ -1001,28 +1023,45 @@ ecc_generate_ext (int algo, unsigned int nbits, unsigned long evalue,
g_y = mpi_new (0);
q_x = mpi_new (0);
q_y = mpi_new (0);
ec = generate_key (&sk, nbits, curve_name, transient_key, g_x, g_y, q_x, q_y);
ec = generate_key (&sk, nbits, curve_name, transient_key, g_x, g_y, q_x, q_y,
&usedcurve);
gcry_free (curve_name);
if (ec)
return ec;
if (usedcurve) /* Fixme: No error return checking. */
gcry_sexp_build (r_extrainfo, NULL, "(curve %s)", usedcurve);
skey[0] = sk.E.p;
skey[1] = sk.E.a;
skey[2] = sk.E.b;
/* The function ec2os releases g_x and g_y. */
skey[3] = ec2os (g_x, g_y, sk.E.p);
skey[4] = sk.E.n;
/* The function ec2os releases g_x and g_y. */
skey[5] = ec2os (q_x, q_y, sk.E.p);
skey[6] = sk.d;
mpi_free (g_x);
mpi_free (g_y);
mpi_free (q_x);
mpi_free (q_y);
point_free (&sk.E.G);
point_free (&sk.Q);
/* Make an empty list of factors. */
*retfactors = gcry_calloc ( 1, sizeof **retfactors );
if (!*retfactors)
return gpg_err_code_from_syserror ();
return gpg_err_code_from_syserror (); /* Fixme: relase mem? */
if (DBG_CIPHER)
{
log_mpidump ("ecgen result p", skey[0]);
log_mpidump ("ecgen result a", skey[1]);
log_mpidump ("ecgen result b", skey[2]);
log_mpidump ("ecgen result G", skey[3]);
log_mpidump ("ecgen result n", skey[4]);
log_mpidump ("ecgen result Q", skey[5]);
log_mpidump ("ecgen result d", skey[6]);
}
return 0;
}
@@ -1037,7 +1076,7 @@ ecc_generate (int algo, unsigned int nbits, unsigned long evalue,
}
/* Return the parameters of the curve NAME. */
/* Return the parameters of the curve NAME in an MPI array. */
static gcry_err_code_t
ecc_get_param (const char *name, gcry_mpi_t *pkey)
{
@@ -1047,7 +1086,7 @@ ecc_get_param (const char *name, gcry_mpi_t *pkey)
mpi_ec_t ctx;
gcry_mpi_t g_x, g_y;
err = generate_curve (0, name, &E, &nbits);
err = fill_in_curve (0, name, &E, &nbits);
if (err)
return err;
@@ -1066,10 +1105,120 @@ ecc_get_param (const char *name, gcry_mpi_t *pkey)
pkey[4] = E.n;
pkey[5] = NULL;
mpi_free (g_x);
mpi_free (g_y);
return 0;
}
/* Return the parameters of the curve NAME as an S-expression. */
static gcry_sexp_t
ecc_get_param_sexp (const char *name)
{
gcry_mpi_t pkey[6];
gcry_sexp_t result;
int i;
if (ecc_get_param (name, pkey))
return NULL;
if (gcry_sexp_build (&result, NULL,
"(public-key(ecc(p%m)(a%m)(b%m)(g%m)(n%m)))",
pkey[0], pkey[1], pkey[2], pkey[3], pkey[4]))
result = NULL;
for (i=0; pkey[i]; i++)
gcry_mpi_release (pkey[i]);
return result;
}
/* Return the name matching the parameters in PKEY. */
static const char *
ecc_get_curve (gcry_mpi_t *pkey, int iterator, unsigned int *r_nbits)
{
gpg_err_code_t err;
elliptic_curve_t E;
int idx;
gcry_mpi_t tmp;
const char *result = NULL;
if (r_nbits)
*r_nbits = 0;
if (!pkey)
{
idx = iterator;
if (idx >= 0 && idx < DIM (domain_parms))
{
result = domain_parms[idx].desc;
if (r_nbits)
*r_nbits = domain_parms[idx].nbits;
}
return result;
}
if (!pkey[0] || !pkey[1] || !pkey[2] || !pkey[3] || !pkey[4])
return NULL;
E.p = pkey[0];
E.a = pkey[1];
E.b = pkey[2];
point_init (&E.G);
err = os2ec (&E.G, pkey[3]);
if (err)
{
point_free (&E.G);
return NULL;
}
E.n = pkey[4];
for (idx = 0; domain_parms[idx].desc; idx++)
{
tmp = scanval (domain_parms[idx].p);
if (!mpi_cmp (tmp, E.p))
{
mpi_free (tmp);
tmp = scanval (domain_parms[idx].a);
if (!mpi_cmp (tmp, E.a))
{
mpi_free (tmp);
tmp = scanval (domain_parms[idx].b);
if (!mpi_cmp (tmp, E.b))
{
mpi_free (tmp);
tmp = scanval (domain_parms[idx].n);
if (!mpi_cmp (tmp, E.n))
{
mpi_free (tmp);
tmp = scanval (domain_parms[idx].g_x);
if (!mpi_cmp (tmp, E.G.x))
{
mpi_free (tmp);
tmp = scanval (domain_parms[idx].g_y);
if (!mpi_cmp (tmp, E.G.y))
{
result = domain_parms[idx].desc;
if (r_nbits)
*r_nbits = domain_parms[idx].nbits;
break;
}
}
}
}
}
}
mpi_free (tmp);
}
point_free (&E.G);
return result;
}
static gcry_err_code_t
ecc_check_secret_key (int algo, gcry_mpi_t *skey)
{
@@ -1078,8 +1227,9 @@ ecc_check_secret_key (int algo, gcry_mpi_t *skey)
(void)algo;
/* FIXME: This check looks a bit fishy: Now long is the array? */
if (!skey[0] || !skey[1] || !skey[2] || !skey[3] || !skey[4] || !skey[5]
|| !skey[6] || !skey[7] || !skey[8] || !skey[9] || !skey[10])
|| !skey[6])
return GPG_ERR_BAD_MPI;
sk.E.p = skey[0];
@@ -1163,6 +1313,7 @@ ecc_sign (int algo, gcry_mpi_t *resarr, gcry_mpi_t data, gcry_mpi_t *skey)
return err;
}
static gcry_err_code_t
ecc_verify (int algo, gcry_mpi_t hash, gcry_mpi_t *data, gcry_mpi_t *pkey,
int (*cmp)(void *, gcry_mpi_t), void *opaquev)
@@ -1206,6 +1357,221 @@ ecc_verify (int algo, gcry_mpi_t hash, gcry_mpi_t *data, gcry_mpi_t *pkey,
}
/* ecdh raw is classic 2-round DH protocol published in 1976.
*
* Overview of ecc_encrypt_raw and ecc_decrypt_raw.
*
* As with any PK operation, encrypt version uses a public key and
* decrypt -- private.
*
* Symbols used below:
* G - field generator point
* d - private long-term scalar
* dG - public long-term key
* k - ephemeral scalar
* kG - ephemeral public key
* dkG - shared secret
*
* ecc_encrypt_raw description:
* input:
* data[0] : private scalar (k)
* output:
* result[0] : shared point (kdG)
* result[1] : generated ephemeral public key (kG)
*
* ecc_decrypt_raw description:
* input:
* data[0] : a point kG (ephemeral public key)
* output:
* result[0] : shared point (kdG)
*/
static gcry_err_code_t
ecc_encrypt_raw (int algo, gcry_mpi_t *resarr, gcry_mpi_t k,
gcry_mpi_t *pkey, int flags)
{
ECC_public_key pk;
mpi_ec_t ctx;
gcry_mpi_t result[2];
int err;
(void)algo;
(void)flags;
if (!k
|| !pkey[0] || !pkey[1] || !pkey[2] || !pkey[3] || !pkey[4] || !pkey[5])
return GPG_ERR_BAD_MPI;
pk.E.p = pkey[0];
pk.E.a = pkey[1];
pk.E.b = pkey[2];
point_init (&pk.E.G);
err = os2ec (&pk.E.G, pkey[3]);
if (err)
{
point_free (&pk.E.G);
return err;
}
pk.E.n = pkey[4];
point_init (&pk.Q);
err = os2ec (&pk.Q, pkey[5]);
if (err)
{
point_free (&pk.E.G);
point_free (&pk.Q);
return err;
}
ctx = _gcry_mpi_ec_init (pk.E.p, pk.E.a);
/* The following is false: assert( mpi_cmp_ui( R.x, 1 )==0 );, so */
{
mpi_point_t R; /* Result that we return. */
gcry_mpi_t x, y;
x = mpi_new (0);
y = mpi_new (0);
point_init (&R);
/* R = kQ <=> R = kdG */
_gcry_mpi_ec_mul_point (&R, k, &pk.Q, ctx);
if (_gcry_mpi_ec_get_affine (x, y, &R, ctx))
log_fatal ("ecdh: Failed to get affine coordinates for kdG\n");
result[0] = ec2os (x, y, pk.E.p);
/* R = kG */
_gcry_mpi_ec_mul_point (&R, k, &pk.E.G, ctx);
if (_gcry_mpi_ec_get_affine (x, y, &R, ctx))
log_fatal ("ecdh: Failed to get affine coordinates for kG\n");
result[1] = ec2os (x, y, pk.E.p);
mpi_free (x);
mpi_free (y);
point_free (&R);
}
_gcry_mpi_ec_free (ctx);
point_free (&pk.E.G);
point_free (&pk.Q);
if (!result[0] || !result[1])
{
mpi_free (result[0]);
mpi_free (result[1]);
return GPG_ERR_ENOMEM;
}
/* Success. */
resarr[0] = result[0];
resarr[1] = result[1];
return 0;
}
/* input:
* data[0] : a point kG (ephemeral public key)
* output:
* resaddr[0] : shared point kdG
*
* see ecc_encrypt_raw for details.
*/
static gcry_err_code_t
ecc_decrypt_raw (int algo, gcry_mpi_t *result, gcry_mpi_t *data,
gcry_mpi_t *skey, int flags)
{
ECC_secret_key sk;
mpi_point_t R; /* Result that we return. */
mpi_point_t kG;
mpi_ec_t ctx;
gcry_mpi_t r;
int err;
(void)algo;
(void)flags;
*result = NULL;
if (!data || !data[0]
|| !skey[0] || !skey[1] || !skey[2] || !skey[3] || !skey[4]
|| !skey[5] || !skey[6] )
return GPG_ERR_BAD_MPI;
point_init (&kG);
err = os2ec (&kG, data[0]);
if (err)
{
point_free (&kG);
return err;
}
sk.E.p = skey[0];
sk.E.a = skey[1];
sk.E.b = skey[2];
point_init (&sk.E.G);
err = os2ec (&sk.E.G, skey[3]);
if (err)
{
point_free (&kG);
point_free (&sk.E.G);
return err;
}
sk.E.n = skey[4];
point_init (&sk.Q);
err = os2ec (&sk.Q, skey[5]);
if (err)
{
point_free (&kG);
point_free (&sk.E.G);
point_free (&sk.Q);
return err;
}
sk.d = skey[6];
ctx = _gcry_mpi_ec_init (sk.E.p, sk.E.a);
/* R = dkG */
point_init (&R);
_gcry_mpi_ec_mul_point (&R, sk.d, &kG, ctx);
point_free (&kG);
/* The following is false: assert( mpi_cmp_ui( R.x, 1 )==0 );, so: */
{
gcry_mpi_t x, y;
x = mpi_new (0);
y = mpi_new (0);
if (_gcry_mpi_ec_get_affine (x, y, &R, ctx))
log_fatal ("ecdh: Failed to get affine coordinates\n");
r = ec2os (x, y, sk.E.p);
mpi_free (x);
mpi_free (y);
}
point_free (&R);
_gcry_mpi_ec_free (ctx);
point_free (&kG);
point_free (&sk.E.G);
point_free (&sk.Q);
if (!r)
return GPG_ERR_ENOMEM;
/* Success. */
*result = r;
return 0;
}
static unsigned int
ecc_get_nbits (int algo, gcry_mpi_t *pkey)
@@ -1216,23 +1582,23 @@ ecc_get_nbits (int algo, gcry_mpi_t *pkey)
}
/* See rsa.c for a description of this function. */
static gpg_err_code_t
compute_keygrip (gcry_md_hd_t md, gcry_sexp_t keyparam)
{
static const char names[] = "pabgnq";
#define N_COMPONENTS 6
static const char names[N_COMPONENTS+1] = "pabgnq";
gpg_err_code_t ec = 0;
gcry_sexp_t l1;
gcry_mpi_t values[6];
gcry_mpi_t values[N_COMPONENTS];
int idx;
/* Clear the values for easier error cleanup. */
for (idx=0; idx < 6; idx++)
for (idx=0; idx < N_COMPONENTS; idx++)
values[idx] = NULL;
/* Fill values with all available parameters. */
for (idx=0; idx < 6; idx++)
/* Fill values with all provided parameters. */
for (idx=0; idx < N_COMPONENTS; idx++)
{
l1 = gcry_sexp_find_token (keyparam, names+idx, 1);
if (l1)
@@ -1253,12 +1619,13 @@ compute_keygrip (gcry_md_hd_t md, gcry_sexp_t keyparam)
if (l1)
{
char *curve;
gcry_mpi_t tmpvalues[6];
gcry_mpi_t tmpvalues[N_COMPONENTS];
for (idx = 0; idx < 6; idx++)
for (idx = 0; idx < N_COMPONENTS; idx++)
tmpvalues[idx] = NULL;
curve = _gcry_sexp_nth_string (l1, 1);
gcry_sexp_release (l1);
if (!curve)
{
ec = GPG_ERR_INV_OBJ; /* Name missing or out of core. */
@@ -1269,7 +1636,7 @@ compute_keygrip (gcry_md_hd_t md, gcry_sexp_t keyparam)
if (ec)
goto leave;
for (idx = 0; idx < 6; idx++)
for (idx = 0; idx < N_COMPONENTS; idx++)
{
if (!values[idx])
values[idx] = tmpvalues[idx];
@@ -1281,7 +1648,7 @@ compute_keygrip (gcry_md_hd_t md, gcry_sexp_t keyparam)
/* Check that all parameters are known and normalize all MPIs (that
should not be required but we use an internal function later and
thus we better make 100% sure that they are normalized). */
for (idx = 0; idx < 6; idx++)
for (idx = 0; idx < N_COMPONENTS; idx++)
if (!values[idx])
{
ec = GPG_ERR_NO_OBJ;
@@ -1291,7 +1658,7 @@ compute_keygrip (gcry_md_hd_t md, gcry_sexp_t keyparam)
_gcry_mpi_normalize (values[idx]);
/* Hash them all. */
for (idx = 0; idx < 6; idx++)
for (idx = 0; idx < N_COMPONENTS; idx++)
{
char buf[30];
unsigned char *rawmpi;
@@ -1311,10 +1678,11 @@ compute_keygrip (gcry_md_hd_t md, gcry_sexp_t keyparam)
}
leave:
for (idx = 0; idx < 6; idx++)
for (idx = 0; idx < N_COMPONENTS; idx++)
_gcry_mpi_release (values[idx]);
return ec;
#undef N_COMPONENTS
}
@@ -1378,6 +1746,12 @@ static const char *ecdsa_names[] =
"ecc",
NULL,
};
static const char *ecdh_names[] =
{
"ecdh",
"ecc",
NULL,
};
gcry_pk_spec_t _gcry_pubkey_spec_ecdsa =
{
@@ -1393,11 +1767,27 @@ gcry_pk_spec_t _gcry_pubkey_spec_ecdsa =
ecc_get_nbits
};
gcry_pk_spec_t _gcry_pubkey_spec_ecdh =
{
"ECDH", ecdh_names,
"pabgnq", "pabgnqd", "se", "", "pabgnq",
GCRY_PK_USAGE_ENCR,
ecc_generate,
ecc_check_secret_key,
ecc_encrypt_raw,
ecc_decrypt_raw,
NULL,
NULL,
ecc_get_nbits
};
pk_extra_spec_t _gcry_pubkey_extraspec_ecdsa =
{
run_selftests,
ecc_generate_ext,
compute_keygrip,
ecc_get_param
ecc_get_param,
ecc_get_curve,
ecc_get_param_sexp
};
-1
View File
@@ -843,4 +843,3 @@ pk_extra_spec_t _gcry_pubkey_extraspec_elg =
elg_generate_ext,
NULL
};
@@ -91,4 +91,3 @@ _gcry_hash_selftest_check_one (int algo,
return result;
}
+378
View File
@@ -0,0 +1,378 @@
/* idea.c - IDEA function
* Copyright 1997, 1998, 1999, 2001 Werner Koch (dd9jn)
* Copyright 2013 g10 Code GmbH
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
* WERNER KOCH BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
* Except as contained in this notice, the name of Werner Koch shall not be
* used in advertising or otherwise to promote the sale, use or other dealings
* in this Software without prior written authorization from Werner Koch.
*
* Patents on IDEA have expired:
* Europe: EP0482154 on 2011-05-16,
* Japan: JP3225440 on 2011-05-16,
* U.S.: 5,214,703 on 2012-01-07.
*/
/*
* Please see http://www.noepatents.org/ to learn why software patents
* are bad for society and what you can do to fight them.
*
* The code herein is based on the one from:
* Bruce Schneier: Applied Cryptography. John Wiley & Sons, 1996.
* ISBN 0-471-11709-9.
*/
#include <config.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include "types.h" /* for byte and u32 typedefs */
#include "g10lib.h"
#include "cipher.h"
#define IDEA_KEYSIZE 16
#define IDEA_BLOCKSIZE 8
#define IDEA_ROUNDS 8
#define IDEA_KEYLEN (6*IDEA_ROUNDS+4)
typedef struct {
u16 ek[IDEA_KEYLEN];
u16 dk[IDEA_KEYLEN];
int have_dk;
} IDEA_context;
static const char *selftest(void);
static u16
mul_inv( u16 x )
{
u16 t0, t1;
u16 q, y;
if( x < 2 )
return x;
t1 = 0x10001UL / x;
y = 0x10001UL % x;
if( y == 1 )
return (1-t1) & 0xffff;
t0 = 1;
do {
q = x / y;
x = x % y;
t0 += q * t1;
if( x == 1 )
return t0;
q = y / x;
y = y % x;
t1 += q * t0;
} while( y != 1 );
return (1-t1) & 0xffff;
}
static void
expand_key( const byte *userkey, u16 *ek )
{
int i,j;
for(j=0; j < 8; j++ ) {
ek[j] = (*userkey << 8) + userkey[1];
userkey += 2;
}
for(i=0; j < IDEA_KEYLEN; j++ ) {
i++;
ek[i+7] = ek[i&7] << 9 | ek[(i+1)&7] >> 7;
ek += i & 8;
i &= 7;
}
}
static void
invert_key( u16 *ek, u16 dk[IDEA_KEYLEN] )
{
int i;
u16 t1, t2, t3;
u16 temp[IDEA_KEYLEN];
u16 *p = temp + IDEA_KEYLEN;
t1 = mul_inv( *ek++ );
t2 = -*ek++;
t3 = -*ek++;
*--p = mul_inv( *ek++ );
*--p = t3;
*--p = t2;
*--p = t1;
for(i=0; i < IDEA_ROUNDS-1; i++ ) {
t1 = *ek++;
*--p = *ek++;
*--p = t1;
t1 = mul_inv( *ek++ );
t2 = -*ek++;
t3 = -*ek++;
*--p = mul_inv( *ek++ );
*--p = t2;
*--p = t3;
*--p = t1;
}
t1 = *ek++;
*--p = *ek++;
*--p = t1;
t1 = mul_inv( *ek++ );
t2 = -*ek++;
t3 = -*ek++;
*--p = mul_inv( *ek++ );
*--p = t3;
*--p = t2;
*--p = t1;
memcpy(dk, temp, sizeof(temp) );
memset(temp, 0, sizeof(temp) ); /* burn temp */
}
static void
cipher( byte *outbuf, const byte *inbuf, u16 *key )
{
u16 s2, s3;
u16 in[4];
int r = IDEA_ROUNDS;
#define x1 (in[0])
#define x2 (in[1])
#define x3 (in[2])
#define x4 (in[3])
#define MUL(x,y) \
do {u16 _t16; u32 _t32; \
if( (_t16 = (y)) ) { \
if( (x = (x)&0xffff) ) { \
_t32 = (u32)x * _t16; \
x = _t32 & 0xffff; \
_t16 = _t32 >> 16; \
x = ((x)-_t16) + (x<_t16?1:0); \
} \
else { \
x = 1 - _t16; \
} \
} \
else { \
x = 1 - x; \
} \
} while(0)
memcpy (in, inbuf, sizeof in);
#ifndef WORDS_BIGENDIAN
x1 = (x1>>8) | (x1<<8);
x2 = (x2>>8) | (x2<<8);
x3 = (x3>>8) | (x3<<8);
x4 = (x4>>8) | (x4<<8);
#endif
do {
MUL(x1, *key++);
x2 += *key++;
x3 += *key++;
MUL(x4, *key++ );
s3 = x3;
x3 ^= x1;
MUL(x3, *key++);
s2 = x2;
x2 ^=x4;
x2 += x3;
MUL(x2, *key++);
x3 += x2;
x1 ^= x2;
x4 ^= x3;
x2 ^= s3;
x3 ^= s2;
} while( --r );
MUL(x1, *key++);
x3 += *key++;
x2 += *key++;
MUL(x4, *key);
#ifndef WORDS_BIGENDIAN
x1 = (x1>>8) | (x1<<8);
x2 = (x2>>8) | (x2<<8);
x3 = (x3>>8) | (x3<<8);
x4 = (x4>>8) | (x4<<8);
#endif
memcpy (outbuf+0, &x1, 2);
memcpy (outbuf+2, &x3, 2);
memcpy (outbuf+4, &x2, 2);
memcpy (outbuf+6, &x4, 2);
#undef MUL
#undef x1
#undef x2
#undef x3
#undef x4
}
static int
do_setkey( IDEA_context *c, const byte *key, unsigned int keylen )
{
static int initialized = 0;
static const char *selftest_failed = 0;
if( !initialized ) {
initialized = 1;
selftest_failed = selftest();
if( selftest_failed )
log_error( "%s\n", selftest_failed );
}
if( selftest_failed )
return GPG_ERR_SELFTEST_FAILED;
assert(keylen == 16);
c->have_dk = 0;
expand_key( key, c->ek );
invert_key( c->ek, c->dk );
return 0;
}
static gcry_err_code_t
idea_setkey (void *context, const byte *key, unsigned int keylen)
{
IDEA_context *ctx = context;
int rc = do_setkey (ctx, key, keylen);
_gcry_burn_stack (23+6*sizeof(void*));
return rc;
}
static void
encrypt_block( IDEA_context *c, byte *outbuf, const byte *inbuf )
{
cipher( outbuf, inbuf, c->ek );
}
static void
idea_encrypt (void *context, byte *out, const byte *in)
{
IDEA_context *ctx = context;
encrypt_block (ctx, out, in);
_gcry_burn_stack (24+3*sizeof (void*));
}
static void
decrypt_block( IDEA_context *c, byte *outbuf, const byte *inbuf )
{
if( !c->have_dk ) {
c->have_dk = 1;
invert_key( c->ek, c->dk );
}
cipher( outbuf, inbuf, c->dk );
}
static void
idea_decrypt (void *context, byte *out, const byte *in)
{
IDEA_context *ctx = context;
decrypt_block (ctx, out, in);
_gcry_burn_stack (24+3*sizeof (void*));
}
static const char *
selftest( void )
{
static struct {
byte key[16];
byte plain[8];
byte cipher[8];
} test_vectors[] = {
{ { 0x00, 0x01, 0x00, 0x02, 0x00, 0x03, 0x00, 0x04,
0x00, 0x05, 0x00, 0x06, 0x00, 0x07, 0x00, 0x08 },
{ 0x00, 0x00, 0x00, 0x01, 0x00, 0x02, 0x00, 0x03 },
{ 0x11, 0xFB, 0xED, 0x2B, 0x01, 0x98, 0x6D, 0xE5 } },
{ { 0x00, 0x01, 0x00, 0x02, 0x00, 0x03, 0x00, 0x04,
0x00, 0x05, 0x00, 0x06, 0x00, 0x07, 0x00, 0x08 },
{ 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08 },
{ 0x54, 0x0E, 0x5F, 0xEA, 0x18, 0xC2, 0xF8, 0xB1 } },
{ { 0x00, 0x01, 0x00, 0x02, 0x00, 0x03, 0x00, 0x04,
0x00, 0x05, 0x00, 0x06, 0x00, 0x07, 0x00, 0x08 },
{ 0x00, 0x19, 0x32, 0x4B, 0x64, 0x7D, 0x96, 0xAF },
{ 0x9F, 0x0A, 0x0A, 0xB6, 0xE1, 0x0C, 0xED, 0x78 } },
{ { 0x00, 0x01, 0x00, 0x02, 0x00, 0x03, 0x00, 0x04,
0x00, 0x05, 0x00, 0x06, 0x00, 0x07, 0x00, 0x08 },
{ 0xF5, 0x20, 0x2D, 0x5B, 0x9C, 0x67, 0x1B, 0x08 },
{ 0xCF, 0x18, 0xFD, 0x73, 0x55, 0xE2, 0xC5, 0xC5 } },
{ { 0x00, 0x01, 0x00, 0x02, 0x00, 0x03, 0x00, 0x04,
0x00, 0x05, 0x00, 0x06, 0x00, 0x07, 0x00, 0x08 },
{ 0xFA, 0xE6, 0xD2, 0xBE, 0xAA, 0x96, 0x82, 0x6E },
{ 0x85, 0xDF, 0x52, 0x00, 0x56, 0x08, 0x19, 0x3D } },
{ { 0x00, 0x01, 0x00, 0x02, 0x00, 0x03, 0x00, 0x04,
0x00, 0x05, 0x00, 0x06, 0x00, 0x07, 0x00, 0x08 },
{ 0x0A, 0x14, 0x1E, 0x28, 0x32, 0x3C, 0x46, 0x50 },
{ 0x2F, 0x7D, 0xE7, 0x50, 0x21, 0x2F, 0xB7, 0x34 } },
{ { 0x00, 0x01, 0x00, 0x02, 0x00, 0x03, 0x00, 0x04,
0x00, 0x05, 0x00, 0x06, 0x00, 0x07, 0x00, 0x08 },
{ 0x05, 0x0A, 0x0F, 0x14, 0x19, 0x1E, 0x23, 0x28 },
{ 0x7B, 0x73, 0x14, 0x92, 0x5D, 0xE5, 0x9C, 0x09 } },
{ { 0x00, 0x05, 0x00, 0x0A, 0x00, 0x0F, 0x00, 0x14,
0x00, 0x19, 0x00, 0x1E, 0x00, 0x23, 0x00, 0x28 },
{ 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08 },
{ 0x3E, 0xC0, 0x47, 0x80, 0xBE, 0xFF, 0x6E, 0x20 } },
{ { 0x3A, 0x98, 0x4E, 0x20, 0x00, 0x19, 0x5D, 0xB3,
0x2E, 0xE5, 0x01, 0xC8, 0xC4, 0x7C, 0xEA, 0x60 },
{ 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08 },
{ 0x97, 0xBC, 0xD8, 0x20, 0x07, 0x80, 0xDA, 0x86 } },
{ { 0x00, 0x64, 0x00, 0xC8, 0x01, 0x2C, 0x01, 0x90,
0x01, 0xF4, 0x02, 0x58, 0x02, 0xBC, 0x03, 0x20 },
{ 0x05, 0x32, 0x0A, 0x64, 0x14, 0xC8, 0x19, 0xFA },
{ 0x65, 0xBE, 0x87, 0xE7, 0xA2, 0x53, 0x8A, 0xED } },
{ { 0x9D, 0x40, 0x75, 0xC1, 0x03, 0xBC, 0x32, 0x2A,
0xFB, 0x03, 0xE7, 0xBE, 0x6A, 0xB3, 0x00, 0x06 },
{ 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08 },
{ 0xF5, 0xDB, 0x1A, 0xC4, 0x5E, 0x5E, 0xF9, 0xF9 } }
};
IDEA_context c;
byte buffer[8];
int i;
for(i=0; i < DIM(test_vectors); i++ ) {
do_setkey( &c, test_vectors[i].key, 16 );
encrypt_block( &c, buffer, test_vectors[i].plain );
if( memcmp( buffer, test_vectors[i].cipher, 8 ) )
return "IDEA test encryption failed.";
decrypt_block( &c, buffer, test_vectors[i].cipher );
if( memcmp( buffer, test_vectors[i].plain, 8 ) )
return "IDEA test decryption failed.";
}
return NULL;
}
gcry_cipher_spec_t _gcry_cipher_spec_idea =
{
"IDEA", NULL, NULL, IDEA_BLOCKSIZE, 128,
sizeof (IDEA_context),
idea_setkey, idea_encrypt, idea_decrypt
};
+278
View File
@@ -0,0 +1,278 @@
/* kdf.c - Key Derivation Functions
* Copyright (C) 1998, 2011 Free Software Foundation, Inc.
*
* This file is part of Libgcrypt.
*
* Libgcrypt is free software; you can redistribute it and/or modify
* it under the terms of the GNU Lesser general Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* Libgcrypt 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 Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this program; if not, see <http://www.gnu.org/licenses/>.
*/
#include <config.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "g10lib.h"
#include "cipher.h"
#include "ath.h"
/* Transform a passphrase into a suitable key of length KEYSIZE and
store this key in the caller provided buffer KEYBUFFER. The caller
must provide an HASHALGO, a valid ALGO and depending on that algo a
SALT of 8 bytes and the number of ITERATIONS. Code taken from
gnupg/agent/protect.c:hash_passphrase. */
gpg_err_code_t
openpgp_s2k (const void *passphrase, size_t passphraselen,
int algo, int hashalgo,
const void *salt, size_t saltlen,
unsigned long iterations,
size_t keysize, void *keybuffer)
{
gpg_err_code_t ec;
gcry_md_hd_t md;
char *key = keybuffer;
int pass, i;
int used = 0;
int secmode;
if ((algo == GCRY_KDF_SALTED_S2K || algo == GCRY_KDF_ITERSALTED_S2K)
&& (!salt || saltlen != 8))
return GPG_ERR_INV_VALUE;
secmode = gcry_is_secure (passphrase) || gcry_is_secure (keybuffer);
ec = gpg_err_code (gcry_md_open (&md, hashalgo,
secmode? GCRY_MD_FLAG_SECURE : 0));
if (ec)
return ec;
for (pass=0; used < keysize; pass++)
{
if (pass)
{
gcry_md_reset (md);
for (i=0; i < pass; i++) /* Preset the hash context. */
gcry_md_putc (md, 0);
}
if (algo == GCRY_KDF_SALTED_S2K || algo == GCRY_KDF_ITERSALTED_S2K)
{
int len2 = passphraselen + 8;
unsigned long count = len2;
if (algo == GCRY_KDF_ITERSALTED_S2K)
{
count = iterations;
if (count < len2)
count = len2;
}
while (count > len2)
{
gcry_md_write (md, salt, saltlen);
gcry_md_write (md, passphrase, passphraselen);
count -= len2;
}
if (count < saltlen)
gcry_md_write (md, salt, count);
else
{
gcry_md_write (md, salt, saltlen);
count -= saltlen;
gcry_md_write (md, passphrase, count);
}
}
else
gcry_md_write (md, passphrase, passphraselen);
gcry_md_final (md);
i = gcry_md_get_algo_dlen (hashalgo);
if (i > keysize - used)
i = keysize - used;
memcpy (key+used, gcry_md_read (md, hashalgo), i);
used += i;
}
gcry_md_close (md);
return 0;
}
/* Transform a passphrase into a suitable key of length KEYSIZE and
store this key in the caller provided buffer KEYBUFFER. The caller
must provide PRFALGO which indicates the pseudorandom function to
use: This shall be the algorithms id of a hash algorithm; it is
used in HMAC mode. SALT is a salt of length SALTLEN and ITERATIONS
gives the number of iterations. */
gpg_err_code_t
pkdf2 (const void *passphrase, size_t passphraselen,
int hashalgo,
const void *salt, size_t saltlen,
unsigned long iterations,
size_t keysize, void *keybuffer)
{
gpg_err_code_t ec;
gcry_md_hd_t md;
int secmode;
unsigned int dklen = keysize;
char *dk = keybuffer;
unsigned int hlen; /* Output length of the digest function. */
unsigned int l; /* Rounded up number of blocks. */
unsigned int r; /* Number of octets in the last block. */
char *sbuf; /* Malloced buffer to concatenate salt and iter
as well as space to hold TBUF and UBUF. */
char *tbuf; /* Buffer for T; ptr into SBUF, size is HLEN. */
char *ubuf; /* Buffer for U; ptr into SBUF, size is HLEN. */
unsigned int lidx; /* Current block number. */
unsigned long iter; /* Current iteration number. */
unsigned int i;
if (!salt || !saltlen || !iterations || !dklen)
return GPG_ERR_INV_VALUE;
hlen = gcry_md_get_algo_dlen (hashalgo);
if (!hlen)
return GPG_ERR_DIGEST_ALGO;
secmode = gcry_is_secure (passphrase) || gcry_is_secure (keybuffer);
/* We ignore step 1 from pksc5v2.1 which demands a check that dklen
is not larger that 0xffffffff * hlen. */
/* Step 2 */
l = ((dklen - 1)/ hlen) + 1;
r = dklen - (l - 1) * hlen;
/* Setup buffers and prepare a hash context. */
sbuf = (secmode
? gcry_malloc_secure (saltlen + 4 + hlen + hlen)
: gcry_malloc (saltlen + 4 + hlen + hlen));
if (!sbuf)
return gpg_err_code_from_syserror ();
tbuf = sbuf + saltlen + 4;
ubuf = tbuf + hlen;
ec = gpg_err_code (gcry_md_open (&md, hashalgo,
(GCRY_MD_FLAG_HMAC
| (secmode?GCRY_MD_FLAG_SECURE:0))));
if (ec)
{
gcry_free (sbuf);
return ec;
}
/* Step 3 and 4. */
memcpy (sbuf, salt, saltlen);
for (lidx = 1; lidx <= l; lidx++)
{
for (iter = 0; iter < iterations; iter++)
{
ec = gpg_err_code (gcry_md_setkey (md, passphrase, passphraselen));
if (ec)
{
gcry_md_close (md);
gcry_free (sbuf);
return ec;
}
if (!iter) /* Compute U_1: */
{
sbuf[saltlen] = (lidx >> 24);
sbuf[saltlen + 1] = (lidx >> 16);
sbuf[saltlen + 2] = (lidx >> 8);
sbuf[saltlen + 3] = lidx;
gcry_md_write (md, sbuf, saltlen + 4);
memcpy (ubuf, gcry_md_read (md, 0), hlen);
memcpy (tbuf, ubuf, hlen);
}
else /* Compute U_(2..c): */
{
gcry_md_write (md, ubuf, hlen);
memcpy (ubuf, gcry_md_read (md, 0), hlen);
for (i=0; i < hlen; i++)
tbuf[i] ^= ubuf[i];
}
}
if (lidx == l) /* Last block. */
memcpy (dk, tbuf, r);
else
{
memcpy (dk, tbuf, hlen);
dk += hlen;
}
}
gcry_md_close (md);
gcry_free (sbuf);
return 0;
}
/* Derive a key from a passphrase. KEYSIZE gives the requested size
of the keys in octets. KEYBUFFER is a caller provided buffer
filled on success with the derived key. The input passphrase is
taken from (PASSPHRASE,PASSPHRASELEN) which is an arbitrary memory
buffer. ALGO specifies the KDF algorithm to use; these are the
constants GCRY_KDF_*. SUBALGO specifies an algorithm used
internally by the KDF algorithms; this is usually a hash algorithm
but certain KDF algorithm may use it differently. {SALT,SALTLEN}
is a salt as needed by most KDF algorithms. ITERATIONS is a
positive integer parameter to most KDFs. 0 is returned on success,
or an error code on failure. */
gpg_error_t
gcry_kdf_derive (const void *passphrase, size_t passphraselen,
int algo, int subalgo,
const void *salt, size_t saltlen,
unsigned long iterations,
size_t keysize, void *keybuffer)
{
gpg_err_code_t ec;
if (!passphrase || (!passphraselen && algo != GCRY_KDF_PBKDF2))
{
ec = GPG_ERR_INV_DATA;
goto leave;
}
if (!keybuffer || !keysize)
{
ec = GPG_ERR_INV_VALUE;
goto leave;
}
switch (algo)
{
case GCRY_KDF_SIMPLE_S2K:
case GCRY_KDF_SALTED_S2K:
case GCRY_KDF_ITERSALTED_S2K:
ec = openpgp_s2k (passphrase, passphraselen, algo, subalgo,
salt, saltlen, iterations, keysize, keybuffer);
break;
case GCRY_KDF_PBKDF1:
ec = GPG_ERR_UNSUPPORTED_ALGORITHM;
break;
case GCRY_KDF_PBKDF2:
ec = pkdf2 (passphrase, passphraselen, subalgo,
salt, saltlen, iterations, keysize, keybuffer);
break;
default:
ec = GPG_ERR_UNKNOWN_ALGORITHM;
break;
}
leave:
return gpg_error (ec);
}
+1
View File
@@ -1232,6 +1232,7 @@ md_stop_debug( gcry_md_hd_t md )
volatile u64 b = 42;
volatile u64 c;
c = a * b;
(void)c;
}
#endif
}
-1
View File
@@ -325,4 +325,3 @@ gcry_md_spec_t _gcry_digest_spec_md4 =
md4_init, md4_write, md4_final, md4_read,
sizeof (MD4_CONTEXT)
};
+4 -5
View File
@@ -738,12 +738,12 @@ gcry_mpi_t
_gcry_generate_elg_prime (int mode, unsigned pbits, unsigned qbits,
gcry_mpi_t g, gcry_mpi_t **ret_factors)
{
gcry_err_code_t err = GPG_ERR_NO_ERROR;
gcry_mpi_t prime = NULL;
err = prime_generate_internal ((mode == 1), &prime, pbits, qbits, g,
ret_factors, GCRY_WEAK_RANDOM, 0, 0,
NULL, NULL);
if (prime_generate_internal ((mode == 1), &prime, pbits, qbits, g,
ret_factors, GCRY_WEAK_RANDOM, 0, 0,
NULL, NULL))
prime = NULL; /* (Should be NULL in the error case anyway.) */
return prime;
}
@@ -1859,4 +1859,3 @@ _gcry_generate_fips186_3_prime (unsigned int pbits, unsigned int qbits,
gcry_mpi_release (val_2);
return ec;
}
File diff suppressed because it is too large. Load diff
-1
View File
@@ -342,4 +342,3 @@ gcry_cipher_spec_t _gcry_cipher_spec_rfc2268_40 = {
RFC2268_BLOCKSIZE, 40, sizeof(RFC2268_context),
do_setkey, do_encrypt, do_decrypt
};
@@ -1684,4 +1684,3 @@ static const u32 rcon[30] =
0xd8, 0xab, 0x4d, 0x9a, 0x2f, 0x5e, 0xbc, 0x63, 0xc6, 0x97, 0x35,
0x6a, 0xd4, 0xb3, 0x7d, 0xfa, 0xef, 0xc5, 0x91
};
Loaded 100 of 234 files, more files were not shown because too many files have changed in this diff. Show more