From a4b99122ebb1fa64e41f76a22bde7aa0fb997d37 Mon Sep 17 00:00:00 2001 From: Arslaan Pathan Date: Tue, 2 Jun 2026 20:48:19 +1200 Subject: Add checks to ensure we don't redundantly rebuild, add rootfs targets, add iso/limine targets, and more (aka. i forgot to commit for too long) --- Makefile | 158 +++++++++++++++++++++++++++++++++++++++++++++++++-------------- 1 file changed, 124 insertions(+), 34 deletions(-) (limited to 'Makefile') diff --git a/Makefile b/Makefile index 271cfab..ad33683 100644 --- a/Makefile +++ b/Makefile @@ -1,12 +1,20 @@ -EXTERNAL_DIR=/yerba/external -BUILD_DIR=/yerba/build -LINUX_DIR=$(EXTERNAL_DIR)/linux -LINUX_REPO=https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git -BUSYBOX_DIR=$(EXTERNAL_DIR)/busybox -BUSYBOX_REPO=https://git.busybox.net/busybox -INITRAMFS_INIT=initramfs_init +WORKING_DIR?=$(shell pwd) +EXTERNAL_DIR?=$(WORKING_DIR)/external +BUILD_DIR?=$(WORKING_DIR)/build +LINUX_DIR?=$(EXTERNAL_DIR)/linux +LINUX_REPO?=https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git +BUSYBOX_DIR?=$(EXTERNAL_DIR)/busybox +BUSYBOX_REPO?=https://git.busybox.net/busybox +INITRAMFS_INIT?=initramfs_init +ROOTFS_DIR?=$(BUILD_DIR)/rootfs +INITRAMFS_DIR?=$(BUILD_DIR)/initramfs +LIMINE_REPO?=https://github.com/limine-bootloader/limine.git +LIMINE_BRANCH?=v8.x-binary +ISO_ROOT?=$(BUILD_DIR)/iso_root +LIMINE_DIR?=$(EXTERNAL_DIR)/limine +ISO_PATH?=$(BUILD_DIR)/yerba-linux.iso -.PHONY: all kernel initramfs iso run clean +.PHONY: all kernel initramfs rootfs iso run clean all: iso @@ -17,44 +25,126 @@ $(BUILD_DIR): @mkdir -p $(BUILD_DIR) $(LINUX_DIR): $(EXTERNAL_DIR) - @echo "[yerba] cloning Linux kernel..." - git clone --depth 1 $(LINUX_REPO) $(LINUX_DIR) + @if [ -d $(LINUX_DIR) ]; then \ + echo "[yerba] Linux kernel already cloned, skipping..."; \ + else \ + echo "[yerba] cloning Linux kernel..."; \ + git clone --depth 1 $(LINUX_REPO) $(LINUX_DIR); \ + fi kernel: $(LINUX_DIR) $(BUILD_DIR) - @echo "[yerba] building kernel (default defconfig)..." - $(MAKE) -C $(LINUX_DIR) defconfig - $(MAKE) -C $(LINUX_DIR) -j$(shell nproc) bzImage - cp $(LINUX_DIR)/arch/x86/boot/bzImage $(BUILD_DIR)/bzImage + @if [ -f $(BUILD_DIR)/bzImage ]; then \ + echo "[yerba] bzImage already exists, skipping kernel build..."; \ + else \ + echo "[yerba] building kernel (default defconfig)..."; \ + $(MAKE) -C $(LINUX_DIR) defconfig; \ + $(MAKE) -C $(LINUX_DIR) -j$(shell nproc) bzImage; \ + cp $(LINUX_DIR)/arch/x86/boot/bzImage $(BUILD_DIR)/bzImage; \ + fi -initramfs: busybox kernel - @echo "[yerba] creating initramfs..." - rm -rf $(BUILD_DIR)/initramfs - mkdir -p $(BUILD_DIR)/initramfs/{bin,sbin,etc,proc,sys,dev} - cp -a $(BUSYBOX_DIR)/_install/. $(BUILD_DIR)/initramfs/ - cp initramfs_init $(BUILD_DIR)/initramfs/init - chmod +x $(BUILD_DIR)/initramfs/init - cd $(BUILD_DIR)/initramfs && find . | cpio -o -H newc | gzip > $(BUILD_DIR)/initramfs.cpio.gz +initramfs: busybox kernel | $(BUILD_DIR) + @if [ -f $(BUILD_DIR)/initramfs.cpio.gz ]; then \ + echo "[yerba] initramfs already created, skipping..."; \ + else \ + echo "[yerba] creating initramfs..."; \ + rm -rf $(INITRAMFS_DIR); \ + mkdir -p $(INITRAMFS_DIR)/bin; \ + mkdir -p $(INITRAMFS_DIR)/sbin; \ + mkdir -p $(INITRAMFS_DIR)/etc; \ + mkdir -p $(INITRAMFS_DIR)/proc; \ + mkdir -p $(INITRAMFS_DIR)/sys; \ + mkdir -p $(INITRAMFS_DIR)/dev; \ + cp -a $(BUSYBOX_DIR)/_install/. $(INITRAMFS_DIR)/; \ + cp $(WORKING_DIR)/initramfs_init $(INITRAMFS_DIR)/init; \ + chmod +x $(INITRAMFS_DIR)/init; \ + cd $(INITRAMFS_DIR) && find . | cpio -o -H newc | gzip > $(BUILD_DIR)/initramfs.cpio.gz; \ + fi + +$(ROOTFS_DIR): $(BUILD_DIR) + mkdir -p $(ROOTFS_DIR) + +rootfs: $(ROOTFS_DIR) kernel initramfs busybox + @if [ -f $(ROOTFS_DIR)/rootfs.squashfs ]; then \ + echo "[yerba] rootfs squashfs image already exists, skipping..."; \ + else \ + rm -rf $(ROOTFS_DIR); \ + mkdir -p $(ROOTFS_DIR); \ + echo "[yerba] creating rootfs..."; \ + mkdir -p $(ROOTFS_DIR)/bin; \ + mkdir -p $(ROOTFS_DIR)/sbin; \ + mkdir -p $(ROOTFS_DIR)/etc; \ + mkdir -p $(ROOTFS_DIR)/proc; \ + mkdir -p $(ROOTFS_DIR)/sys; \ + mkdir -p $(ROOTFS_DIR)/dev; \ + mkdir -p $(ROOTFS_DIR)/home; \ + mkdir -p $(ROOTFS_DIR)/var; \ + mkdir -p $(ROOTFS_DIR)/usr; \ + mkdir -p $(ROOTFS_DIR)/root; \ + mkdir -p $(ROOTFS_DIR)/mnt; \ + mkdir -p $(ROOTFS_DIR)/tmp; \ + cp -a $(BUSYBOX_DIR)/_install/. $(ROOTFS_DIR)/; \ + ln -sf sbin/init $(ROOTFS_DIR)/init; \ + echo "proc /proc proc defaults 0 0" > $(ROOTFS_DIR)/etc/fstab; \ + echo "sysfs /sys sysfs defaults 0 0" >> $(ROOTFS_DIR)/etc/fstab; \ + echo "devtmpfs /dev devtmpfs defaults 0 0" >> $(ROOTFS_DIR)/etc/fstab; \ + echo "::sysinit:/bin/mount -a" > $(ROOTFS_DIR)/etc/inittab; \ + echo "::askfirst:/bin/sh" >> $(ROOTFS_DIR)/etc/inittab; \ + echo "::ctrlaltdel:/sbin/reboot" >> $(ROOTFS_DIR)/etc/inittab; \ + echo "[yerba] creating squashfs image..."; \ + mksquashfs $(ROOTFS_DIR) $(BUILD_DIR)/rootfs.squashfs -comp zstd -noappend; \ + fi $(BUSYBOX_DIR): $(EXTERNAL_DIR) - @echo "[yerba] cloning BusyBox..." - git clone --depth 1 $(BUSYBOX_REPO) $(BUSYBOX_DIR) + @if [ -d $(BUSYBOX_DIR) ]; then \ + echo "[yerba] BusyBox already cloned, skipping..."; \ + else \ + echo "[yerba] cloning BusyBox..."; \ + git clone --depth 1 $(BUSYBOX_REPO) $(BUSYBOX_DIR); \ + fi busybox: $(BUSYBOX_DIR) $(BUILD_DIR) - @echo "[yerba] building BusyBox..." - rm $(BUSYBOX_DIR)/.config - cp busybox_config $(BUSYBOX_DIR)/.config - $(MAKE) -C $(BUSYBOX_DIR) -j$(shell nproc) - $(MAKE) -C $(BUSYBOX_DIR) CONFIG_PREFIX=$(BUSYBOX_DIR)/_install install + @if [ -d $(BUSYBOX_DIR)/_install ]; then \ + echo "[yerba] BusyBox already built, skipping..."; \ + else \ + echo "[yerba] building BusyBox..."; \ + rm -f $(BUSYBOX_DIR)/.config; \ + cp $(WORKING_DIR)/busybox_config $(BUSYBOX_DIR)/.config; \ + $(MAKE) -C $(BUSYBOX_DIR) -j$(shell nproc); \ + $(MAKE) -C $(BUSYBOX_DIR) CONFIG_PREFIX=$(BUSYBOX_DIR)/_install install; \ + fi + +$(LIMINE_DIR): $(EXTERNAL_DIR) + @if [ -d $(LIMINE_DIR) ]; then \ + echo "[yerba] Limine already cloned, skipping..."; \ + else \ + echo "[yerba] cloning Limine..."; \ + git clone --depth 1 --branch=$(LIMINE_BRANCH) $(LIMINE_REPO) $(LIMINE_DIR); \ + fi + echo "[yerba] building Limine..." + $(MAKE) -C $(LIMINE_DIR) -iso: kernel initramfs busybox - @echo "[yerba] TODO: make this output an ISO when ready" - @echo "[yerba] Kernel located at $(BUILD_DIR)/bzImage" - @echo "[yerba] Initramfs located at $(BUILD_DIR)/initramfs.cpio.gz" +iso: kernel initramfs busybox rootfs $(LIMINE_DIR) + @if [ -f $(ISO_PATH) ]; then \ + echo "[yerba] iso already created, skipping..."; \ + else \ + echo "[yerba] bootstrapping Limine and creating ISO..."; \ + mkdir -p $(ISO_ROOT)/boot/limine; \ + mkdir -p $(ISO_ROOT)/EFI/BOOT; \ + cp $(BUILD_DIR)/bzImage $(ISO_ROOT)/boot/; \ + cp $(BUILD_DIR)/initramfs.cpio.gz $(ISO_ROOT)/boot/; \ + cp $(WORKING_DIR)/limine.conf $(ISO_ROOT)/boot/limine; \ + cp $(LIMINE_DIR)/limine-bios.sys $(LIMINE_DIR)/limine-bios-cd.bin $(LIMINE_DIR)/limine-uefi-cd.bin $(ISO_ROOT)/boot/limine; \ + cp $(LIMINE_DIR)/BOOTX64.EFI $(ISO_ROOT)/EFI/BOOT/; \ + cp $(LIMINE_DIR)/BOOTIA32.EFI $(ISO_ROOT)/EFI/BOOT/; \ + xorriso -as mkisofs -R -r -J -b boot/limine/limine-bios-cd.bin -no-emul-boot -boot-load-size 4 -boot-info-table -hfsplus -apm-block-size 2048 --efi-boot boot/limine/limine-uefi-cd.bin -efi-boot-part --efi-boot-image --protective-msdos-label $(ISO_ROOT) -o $(ISO_PATH); \ + $(LIMINE_DIR)/limine bios-install $(ISO_PATH); \ + fi clean: rm -rf $(EXTERNAL_DIR) $(BUILD_DIR) run: iso @echo "[yerba] booting in QEMU..." - qemu-system-x86_64 -kernel $(BUILD_DIR)/bzImage -initrd $(BUILD_DIR)/initramfs.cpio.gz -nographic -append "console=ttyS0" + # qemu-system-x86_64 -kernel $(BUILD_DIR)/bzImage -initrd $(BUILD_DIR)/initramfs.cpio.gz -nographic -append "console=ttyS0" + qemu-system-x86_64 -cdrom $(ISO_PATH) -m 2G -cpu host -enable-kvm -- cgit v1.2.3