diff --git a/.gitignore b/.gitignore index 38ef80e8..1293e9ee 100644 --- a/.gitignore +++ b/.gitignore @@ -16,6 +16,7 @@ /cdrom/netinit /cdrom/mod/* /cdrom/ramdisk.img +/cdrom/ramdisk.igz /cdrom/boot.sys /cdrom/fat.img /fatbase/extra @@ -23,6 +24,7 @@ /fatbase/netinit /fatbase/mod/* /fatbase/ramdisk.img +/fatbase/ramdisk.igz /fatbase/efi/boot/bootia32.efi /util/tarballs /util/build diff --git a/Makefile b/Makefile index c5c80ac5..5f41e9be 100644 --- a/Makefile +++ b/Makefile @@ -26,7 +26,7 @@ TARGET_TRIPLET=i686-pc-toaru CC=$(TARGET_TRIPLET)-gcc AR=$(TARGET_TRIPLET)-ar AS=$(TARGET_TRIPLET)-as -CFLAGS= -O3 -g -std=gnu99 -I. -Iapps -pipe -mmmx -msse -msse2 -fplan9-extensions -Wall -Wextra -Wno-unused-parameter +CFLAGS= -O3 -s -std=gnu99 -I. -Iapps -pipe -mmmx -msse -msse2 -fplan9-extensions -Wall -Wextra -Wno-unused-parameter ## # C library objects from libc/ C sources (and setjmp, which is assembly) @@ -259,8 +259,10 @@ base/bin/%.krk: apps/%.krk chmod +x $@ # Ramdisk -fatbase/ramdisk.img: ${RAMDISK_FILES} $(shell find base) Makefile util/createramdisk.py | dirs +fatbase/ramdisk.igz: ${RAMDISK_FILES} $(shell find base) Makefile util/createramdisk.py | dirs python3 util/createramdisk.py + gzip -c fatbase/ramdisk.img > fatbase/ramdisk.igz + rm fatbase/ramdisk.img # CD image @@ -274,7 +276,7 @@ EFI_UPDATE=util/update-extents.py image.iso: ${EFI_BOOT} cdrom/boot.sys fatbase/netinit ${MODULES} util/update-extents.py xorriso -as mkisofs -R -J -c bootcat \ - -b boot.sys -no-emul-boot -boot-load-size 24 \ + -b boot.sys -no-emul-boot -boot-load-size full \ ${EFI_XORRISO} \ -o image.iso cdrom ${EFI_UPDATE} @@ -286,7 +288,7 @@ image.iso: ${EFI_BOOT} cdrom/boot.sys fatbase/netinit ${MODULES} util/update-ext # This is the filesystem the EFI loaders see, so it must contain # the kernel, modules, and ramdisk, plus anything else we want # available to the bootloader (eg., netinit). -cdrom/fat.img: fatbase/ramdisk.img ${MODULES} fatbase/kernel fatbase/netinit fatbase/efi/boot/bootia32.efi fatbase/efi/boot/bootx64.efi util/mkdisk.sh | dirs +cdrom/fat.img: fatbase/ramdisk.igz ${MODULES} fatbase/kernel fatbase/netinit fatbase/efi/boot/bootia32.efi fatbase/efi/boot/bootx64.efi util/mkdisk.sh | dirs util/mkdisk.sh $@ fatbase ## @@ -317,7 +319,7 @@ cdrom/boot.sys: boot/boot.o boot/cstuff.o boot/link.ld | dirs ${KLD} -T boot/link.ld -o $@ boot/boot.o boot/cstuff.o boot/cstuff.o: boot/cstuff.c boot/*.h - ${CC} -c -Os -o $@ $< + ${CC} -c -Os -s -o $@ $< boot/boot.o: boot/boot.S ${AS} -o $@ $< @@ -329,7 +331,7 @@ clean: rm -f ${APPS_X} ${APPS_SH_X} rm -f libc/*.o libc/*/*.o rm -f image.iso - rm -f fatbase/ramdisk.img + rm -f fatbase/ramdisk.img fatbase/ramdisk.igz rm -f cdrom/boot.sys rm -f boot/*.o rm -f boot/*.efi diff --git a/boot/cstuff.c b/boot/cstuff.c index 8a58affa..0d7128a1 100644 --- a/boot/cstuff.c +++ b/boot/cstuff.c @@ -6,6 +6,18 @@ EFI_HANDLE ImageHandleIn; # include "types.h" #endif +#define _BOOT_LOADER +struct huff_ring; +struct inflate_context { + void * input_priv; + void * output_priv; + uint8_t (*get_input)(struct inflate_context * ctx); + void (*write_output)(struct inflate_context * ctx, unsigned int sym); + int bit_buffer; + int buffer_size; + struct huff_ring * ring; +}; +#include "../lib/inflate.c" #include "ata.h" #include "text.h" #include "util.h" @@ -49,7 +61,7 @@ EFI_HANDLE ImageHandleIn; char * module_dir = "MOD"; char * kernel_path = "KERNEL."; -char * ramdisk_path = "RAMDISK.IMG"; +char * ramdisk_path = "RAMDISK.IGZ"; #ifdef EFI_PLATFORM int _efi_do_mode_set = 0; diff --git a/boot/moremultiboot.h b/boot/moremultiboot.h index 75a8ad51..3c9c7af7 100644 --- a/boot/moremultiboot.h +++ b/boot/moremultiboot.h @@ -418,6 +418,19 @@ done_video: ); #endif +static uint8_t _get(struct inflate_context * ctx) { + uint8_t * x = ctx->input_priv; + uint8_t out = *x++; + ctx->input_priv = (void*)x; + return out; +} + +static void _write(struct inflate_context * ctx, unsigned int sym) { + uint8_t * x = ctx->output_priv; + *x++ = (uint8_t)sym; + ctx->output_priv = (void*)x; +} + #ifndef EFI_PLATFORM static void do_it(struct ata_device * _device) { device = _device; @@ -480,30 +493,45 @@ done: if (navigate(ramdisk_path)) { //clear_(); ramdisk_off = KERNEL_LOAD_START + offset; - ramdisk_len = dir_entry->extent_length_LSB; - modules_mboot[multiboot_header.mods_count-1].mod_start = ramdisk_off; - modules_mboot[multiboot_header.mods_count-1].mod_end = ramdisk_off + ramdisk_len; print_("Loading ramdisk"); int i = dir_entry->extent_start_LSB; int sectors = dir_entry->extent_length_LSB / 2048 + 1; + size_t off = 0; +#define RAMDISK_OFFSET 0x5000000 #define SECTORS 512 while (sectors >= SECTORS) { print_("."); - ata_device_read_sectors_atapi(device, i, (uint8_t *)KERNEL_LOAD_START + offset, SECTORS); + ata_device_read_sectors_atapi(device, i, (uint8_t *)RAMDISK_OFFSET + off, SECTORS); sectors -= SECTORS; - offset += 2048 * SECTORS; + off += 2048 * SECTORS; i += SECTORS; } if (sectors > 0) { print_("!"); - ata_device_read_sectors_atapi(device, i, (uint8_t *)KERNEL_LOAD_START + offset, sectors); - offset += 2048 * sectors; + ata_device_read_sectors_atapi(device, i, (uint8_t *)RAMDISK_OFFSET + off, sectors); + off += 2048 * sectors; } - final_offset = (uint8_t *)KERNEL_LOAD_START + offset; + struct inflate_context ctx; + ctx.input_priv = (char *)RAMDISK_OFFSET; + ctx.output_priv = (char *)ramdisk_off; + ctx.get_input = _get; + ctx.write_output = _write; + ctx.ring = NULL; /* Use the global one */ + print_("\nDecompressing ramdisk... "); + if (gzip_decompress(&ctx)) { + print_("Failed?\n"); + } + ramdisk_len = (uint32_t)ctx.output_priv - ramdisk_off; + + modules_mboot[multiboot_header.mods_count-1].mod_start = ramdisk_off; + modules_mboot[multiboot_header.mods_count-1].mod_end = ramdisk_off + ramdisk_len; + + final_offset = ((uint8_t *)ctx.output_priv) + ((uintptr_t)ctx.output_priv) % 4096; + set_attr(0x07); print("Done.\n"); move_kernel(); @@ -868,12 +896,24 @@ _try_module_again: status = uefi_call_wrapper(root->Open, 5, root, &file, name, EFI_FILE_MODE_READ, 0); if (!EFI_ERROR(status)) { +#define RAMDISK_OFFSET 0x5000000 status = uefi_call_wrapper(file->Read, - 3, file, &bytes, (void *)(KERNEL_LOAD_START + (uintptr_t)offset)); + 3, file, &bytes, (void *)(RAMDISK_OFFSET)); if (!EFI_ERROR(status)) { + struct inflate_context ctx; + ctx.input_priv = (char *)RAMDISK_OFFSET; + ctx.output_priv = (char *)KERNEL_LOAD_START + offset; + ctx.get_input = _get; + ctx.write_output = _write; + ctx.ring = NULL; /* Use the global one */ + print_("\nDecompressing ramdisk... "); + if (gzip_decompress(&ctx)) { + print_("Failed?\n"); + } + print_("Loaded "); print_(c); print_("\n"); modules_mboot[multiboot_header.mods_count-1].mod_start = KERNEL_LOAD_START + offset; - modules_mboot[multiboot_header.mods_count-1].mod_end = KERNEL_LOAD_START + offset + bytes; + modules_mboot[multiboot_header.mods_count-1].mod_end = (uintptr_t)ctx.output_priv; offset += bytes; while (offset % 4096) offset++; final_offset = (uint8_t *)KERNEL_LOAD_START + offset; diff --git a/util/mkdisk.sh b/util/mkdisk.sh index 164615de..cf1ba48d 100755 --- a/util/mkdisk.sh +++ b/util/mkdisk.sh @@ -12,8 +12,8 @@ SPACE_REQ=$(du -sb "$DIR/../fatbase" | cut -f 1) let "SIZE = ($SPACE_REQ / 1000000)" # Minimum size -if [ $SIZE -lt 24 ]; then - SIZE=24 +if [ $SIZE -lt 14 ]; then + SIZE=14 fi # Use more sectors-per-cluster for larger disk sizes