From 262020773cd0ba113d04bbae9ae0a9709234f82a Mon Sep 17 00:00:00 2001 From: d0p1 Date: Wed, 8 Oct 2025 15:01:16 +0200 Subject: [PATCH] build: rework the whole build system Still WIP & messy --- .gitignore | 2 + Makefile | 180 +++++++------- bin/Makefile | 2 +- bin/cmd/Makefile | 16 +- bin/fasdump/main.c | 2 + bin/readcoff/main.c | 437 ++++++++++++++++++++++++++++++++-- boot/Makefile | 4 +- boot/bootsect/Makefile | 30 ++- boot/bootsect/mbr.asm | 7 +- boot/efi/Makefile | 26 +- boot/loader/Makefile | 27 ++- compile_flags.txt | 4 + external/Makefile | 12 +- include/Makefile | 4 +- include/fas.h | 9 +- include/stupidc.h | 62 +++++ kernel/Makefile | 40 ++-- lib/Makefile | 2 +- lib/c/Makefile | 5 +- lib/crypto/Makefile | 13 +- lib/csu/Makefile | 2 + lib/lzp/Makefile | 7 +- lib/stupidc/progname.c | 30 +++ lib/stupidc/version.c | 20 ++ modules/Makefile | 2 +- modules/dummy/Makefile | 22 +- rules.mk | 87 ------- sbin/Makefile | 1 + sbin/mtree/main.c | 77 ++++++ sbin/mtree/mtree.h | 47 ++++ sbin/parted/cmd.c | 120 ++++++++++ sbin/parted/disk.c | 13 + sbin/parted/disk.h | 4 + sbin/parted/fdisk/cmd.h | 29 +++ sbin/parted/fdisk/device.h | 33 +++ sbin/parted/fdisk/disk.h | 37 +++ sbin/parted/fdisk/partition.h | 12 + sbin/parted/fdisk/version.h | 6 + sbin/parted/fildev.c | 119 +++++++++ sbin/parted/gpt.h | 28 +++ sbin/parted/guid.h | 16 ++ sbin/parted/label/msdos.c | 11 + sbin/parted/main.c | 144 +++++++++-- sbin/parted/parted.8 | 13 + sbin/parted/parted.h | 26 ++ sbin/parted/repl.c | 123 ++++++++++ sbin/parted/version.c | 24 ++ share/mk/stpd.base.mk | 79 ++++++ share/mk/stpd.clean.mk | 12 + share/mk/stpd.hostlib.mk | 27 +++ share/mk/stpd.hostprog.mk | 31 +++ share/mk/stpd.inc.mk | 17 ++ share/mk/stpd.subdirs.mk | 33 +++ tests/Makefile | 6 +- tools/Makefile | 42 +--- tools/ar/Makefile | 5 + tools/elf2coff/Makefile | 5 + tools/fas2sym/Makefile | 5 + tools/fasdump/Makefile | 5 + tools/fdisk/Makefile | 6 + tools/ld/Makefile | 5 + tools/libstupidc/Makefile | 6 + tools/mtree/Makefile | 5 + tools/ranlib/Makefile | 5 + tools/readcoff/Makefile | 5 + 65 files changed, 1873 insertions(+), 363 deletions(-) create mode 100644 compile_flags.txt create mode 100644 include/stupidc.h create mode 100644 lib/stupidc/progname.c create mode 100644 lib/stupidc/version.c delete mode 100644 rules.mk create mode 100644 sbin/Makefile create mode 100644 sbin/mtree/main.c create mode 100644 sbin/mtree/mtree.h create mode 100644 sbin/parted/cmd.c create mode 100644 sbin/parted/disk.c create mode 100644 sbin/parted/disk.h create mode 100644 sbin/parted/fdisk/cmd.h create mode 100644 sbin/parted/fdisk/device.h create mode 100644 sbin/parted/fdisk/disk.h create mode 100644 sbin/parted/fdisk/partition.h create mode 100644 sbin/parted/fdisk/version.h create mode 100644 sbin/parted/fildev.c create mode 100644 sbin/parted/gpt.h create mode 100644 sbin/parted/guid.h create mode 100644 sbin/parted/label/msdos.c create mode 100644 sbin/parted/parted.8 create mode 100644 sbin/parted/parted.h create mode 100644 sbin/parted/repl.c create mode 100644 sbin/parted/version.c create mode 100644 share/mk/stpd.base.mk create mode 100644 share/mk/stpd.clean.mk create mode 100644 share/mk/stpd.hostlib.mk create mode 100644 share/mk/stpd.hostprog.mk create mode 100644 share/mk/stpd.inc.mk create mode 100644 share/mk/stpd.subdirs.mk create mode 100644 tools/ar/Makefile create mode 100644 tools/elf2coff/Makefile create mode 100644 tools/fas2sym/Makefile create mode 100644 tools/fasdump/Makefile create mode 100644 tools/fdisk/Makefile create mode 100644 tools/ld/Makefile create mode 100644 tools/libstupidc/Makefile create mode 100644 tools/mtree/Makefile create mode 100644 tools/ranlib/Makefile create mode 100644 tools/readcoff/Makefile diff --git a/.gitignore b/.gitignore index 6bf9e4d..1643365 100644 --- a/.gitignore +++ b/.gitignore @@ -1,4 +1,5 @@ *.o +*.lo *.img *.bin *.iso @@ -40,3 +41,4 @@ webring.json webring.txt kernel/const.inc boot/common/const.inc +.build diff --git a/Makefile b/Makefile index 1ca8d44..a55c30e 100644 --- a/Makefile +++ b/Makefile @@ -1,135 +1,151 @@ .DEFAULT_GOAL:=all -export MAKEFLAGS += --no-print-directory - -export LIB = - export TOPDIR := $(dir $(realpath $(lastword $(MAKEFILE_LIST)))) -export SYSROOTDIR := $(TOPDIR)/sysroot -export TOOLSDIR := $(TOPDIR)/tools +export BUILDDIR := $(TOPDIR)/.build +export SYSROOTDIR := $(BUILDDIR)/sysroot +export TOOLSDIR := $(BUILDDIR)/tools +export SYMSDIR := $(BUILDDIR)/syms -export BINDIR = /bin -export LIBDIR = /usr/lib -export INCDIR = /usr/include -export ASMDIR = /usr/asm +export MAKEFLAGS += -I $(TOPDIR)/share/mk -Orecurse --no-print-directory -export AS = fasm -export CC ?= gcc -export LD = $(TOOLSDIR)/ld -export RM = rm -f -export TOOL_CC ?= gcc -export TOOL_LD ?= ld +define subdir-rule -export MK_BUGREPORT := \"https://git.cute.engineering/d0p1/StupidOS/issues\" -export MK_COMMIT := \"$(shell git rev-parse --short HEAD)\" -export MK_PACKAGE := \"StupidOS\" +.PHONY: $1-$2 +$1-$2: + @echo "📁 $2" + @DESTDIR=$(SYSROOTDIR) $$(MAKE) -C $2 $1 -export CFLAGS = -DMK_COMMIT="$(MK_COMMIT)" \ - -DMK_BUGREPORT="$(MK_BUGREPORT)" \ - -DMK_PACKAGE="$(MK_PACKAGE)" \ - -I$(TOPDIR)include -export LDFLAGS = +endef +SUBDIRS := external tools include lib bin sbin boot kernel modules tests +BUILD_RULES := build-tools .WAIT +BUILD_RULES += includes-kernel includes-include includes-lib .WAIT +BUILD_RULES += build-user build-kernel + +USER_RULES := install-bin install-sbin +KERNEL_RULES := install-boot install-kernel install-modules + +IMAGES = stupid.iso stupid.hdd floppy1440.img floppy2880.img + +BUILD_START := $(shell date) + +QEMU = qemu-system-i386 QEMU_COMMON = \ - -rtc base=localtime \ - -vga cirrus \ - -serial stdio \ - -monitor telnet::4545,server,nowait \ - -net nic,model=ne2k_isa \ - -machine isapc - -SUBDIRS := external tools include boot kernel modules lib bin - -TARGET = stupid.tar.gz floppy1440.img floppy2880.img -ifneq ($(OS),Windows_NT) -EXEXT = -TARGET += stupid.iso stupid.hdd -else -EXEXT = .exe -endif -export EXEXT + -rtc base=localtime \ + -vga cirrus \ + -serial stdio \ + -monitor telnet::4545,server,nowait \ + -net nic,model=ne2k_isa \ + -machine isapc .PHONY: all -all: $(TARGET) +all: $(IMAGES) + @echo "build start: $(BUILD_START)" + @printf "build end: " & date -GOAL:=install -clean: GOAL:=clean +.PHONY: build-tools +build-tools: + @echo "📁 tools" + @$(MAKE) -C tools install -.PHONY: $(SUBDIRS) -$(SUBDIRS): - @echo "📁 $@" - @DESTDIR=$(SYSROOTDIR) $(MAKE) -C $@ $(GOAL) +.PHONY: build-user +build-user: $(USER_RULES) -.PHONY: stupid.iso -stupid.iso: $(SUBDIRS) - $(TOPDIR)/tools/create-iso $@ sysroot +.PHONY: build-kernel +build-kernel: $(KERNEL_RULES) -.PHONY: stupid.hdd -stupid.hdd: $(SUBDIRS) - dd if=/dev/zero of=$@ bs=1M count=0 seek=64 - mformat -L 12 -i $@ - mcopy -i $@ boot/loader/stpdldr.sys ::/STPDLDR.SYS - mcopy -i $@ kernel/vmstupid.sys ::/VMSTUPID.SYS +$(eval $(foreach X,kernel include lib,$(call subdir-rule,includes,$X))) +$(eval $(foreach X,bin sbin,$(call subdir-rule,install,$X))) +$(eval $(foreach X,boot kernel modules,$(call subdir-rule,install,$X))) .PHONY: stupid.tar.gz -stupid.tar.gz: $(SUBDIRS) - tar -czvf $@ sysroot +stupid.tar.gz: $(BUILD_RULES) + tar -czvf $@ $(SYSROOTDIR) + +# +------------------------------------------------------------------+ +# | Disk images | +# +------------------------------------------------------------------+ + +.PHONY: stupid.iso +stupid.iso: $(BUILD_RULES) + @echo "TODO" + +.PHONY: stupid.hdd +stupid.hdd: $(BUILD_RULES) + dd if=/dev/zero of=$@ bs=1M count=0 seek=64 + mformat -L 12 -i $@ + mcopy -i $@ boot/loader/stpdldr.sys "::/STPDLDR.SYS" + mcopy -i $@ kernel/vmstupid.sys "::/VMSTUPID.SYS" .PHONY: floppy1440.img -floppy1440.img: $(SUBDIRS) +floppy1440.img: $(BUILD_RULES) dd if=/dev/zero of=$@ bs=512 count=1440 mformat -C -f 1440 -i $@ dd if=boot/bootsect/boot_floppy1440.bin of=$@ conv=notrunc - mcopy -i $@ boot/loader/stpdldr.sys ::/STPDLDR.SYS - mcopy -i $@ kernel/vmstupid.sys ::/VMSTUPID.SYS + mcopy -i $@ boot/loader/stpdldr.sys "::/STPDLDR.SYS" + mcopy -i $@ kernel/vmstupid.sys "::/VMSTUPID.SYS" .PHONY: floppy2880.img -floppy2880.img: $(SUBDIRS) +floppy2880.img: $(BUILD_RULES) dd if=/dev/zero of=$@ bs=512 count=2880 mformat -C -f 2880 -i $@ dd if=boot/bootsect/boot_floppy2880.bin of=$@ conv=notrunc - mcopy -i $@ boot/loader/stpdldr.sys ::/STPDLDR.SYS - mcopy -i $@ kernel/vmstupid.sys ::/VMSTUPID.SYS + mcopy -i $@ boot/loader/stpdldr.sys "::/STPDLDR.SYS" + mcopy -i $@ kernel/vmstupid.sys "::/VMSTUPID.SYS" + +# +------------------------------------------------------------------+ +# | QEMU / bochs | +# +------------------------------------------------------------------+ OVMF32.fd: wget 'https://retrage.github.io/edk2-nightly/bin/DEBUGIa32_OVMF.fd' -O $@ .PHONY: run -run: all - qemu-system-i386 \ - $(QEMU_COMMON) \ +run: floppy1440.img + $(QEMU) $(QEMU_COMMON) \ -drive file=floppy1440.img,if=none,format=raw,id=boot \ - -drive file=fat:rw:./sysroot,if=none,id=hdd \ + -drive file=flat:rw:$(SYSROOTDIR),if=none,id=hdd \ -device floppy,drive=boot \ -global isa-fdc.bootindexA=0 .PHONY: run-iso -run-iso: all - qemu-system-i386 \ - $(QEMU_COMMON) \ +run-iso: $(BUILD_RULES) + $(QEMU) $(QEMU_COMMON) \ -cdrom stupid.iso .PHONY: run-efi -run-efi: all OVMF32.fd - qemu-system-i386 \ - -bios OVMF32.fd \ - -drive file=fat:rw:./sysroot,if=none,id=hdd \ +run-efi: OVMF32.fd $(BUILD_RULES) + $(QEMU) -bios OVMF32.fd \ + -drive file=fat:rw:$(SYSROOTDIR),if=none,id=hdd \ -device ide-hd,drive=hdd .PHONY: bochs -bochs: +bochs: $(BUILD_RULES) bochs -f .bochsrc +# +------------------------------------------------------------------+ +# | Website / docs | +# +------------------------------------------------------------------+ .PHONY: docs docs: @mkdir -p docs/html - wget -O docs/webring.json https://webring.devse.wiki/webring.json + wget -O docs/webring.json "https://webring.devse.wiki/webring.json" python3 docs/devsewebring.py docs/webring.json docs/webring.txt - naturaldocs -p docs/config -img docs/img -xi sysroot -i . -ro -o HTML docs/html - cp docs/img/favicon.ico docs/html/ + naturaldocs -p docs/config -img docs/img -xi .build -i . -ro -o HTML docs/html + cp docs/img/favicon.ico docs/html + +# +------------------------------------------------------------------+ +# | clean | +# +------------------------------------------------------------------+ + +$(eval $(foreach X,$(SUBDIRS),$(call subdir-rule,clean,$X))) .PHONY: clean -clean: $(SUBDIRS) - $(RM) $(TARGET) +clean: $(foreach X,$(SUBDIRS),clean-$X) + rm -f $(IMAGES) + +.PHONY: cleandir +cleandir: clean + rm -rf $(BUILDDIR) diff --git a/bin/Makefile b/bin/Makefile index 215832b..f34aa6b 100644 --- a/bin/Makefile +++ b/bin/Makefile @@ -1,3 +1,3 @@ SUBDIRS = cmd -include $(TOPDIR)/rules.mk +include stpd.subdirs.mk diff --git a/bin/cmd/Makefile b/bin/cmd/Makefile index 10ffce1..bcbd1da 100644 --- a/bin/cmd/Makefile +++ b/bin/cmd/Makefile @@ -1,6 +1,10 @@ -all: - fasm cmd.asm - -clean: - -install: all +all: cmd.o + +clean: + +install: all + +CLEANFILES = cmd.o + +include stpd.base.mk +include stpd.clean.mk diff --git a/bin/fasdump/main.c b/bin/fasdump/main.c index 5ca6443..488c90a 100644 --- a/bin/fasdump/main.c +++ b/bin/fasdump/main.c @@ -281,6 +281,8 @@ process_file(char *file) print_symbols(); } + fas_cleanup(); + return (EXIT_SUCCESS); } diff --git a/bin/readcoff/main.c b/bin/readcoff/main.c index 185cdba..1b46b31 100644 --- a/bin/readcoff/main.c +++ b/bin/readcoff/main.c @@ -1,16 +1,36 @@ #include #include +#include +#include +#include #include +#include +#include #include -#include -#ifndef __stupidos__ -# include -#endif +#include #include +static const char *prg_name = NULL; + +static FILHDR filhdr; +static AOUTHDR aouthdr; +static SCNHDR *scnhdrs = NULL; +static SYMENT *symtab = NULL; +static char *strtab = NULL; +static size_t sym_cnt = 0; +static size_t sec_cnt = 0; +static const char *machine = NULL; +static const char *aoutmag = NULL; +static RELOC **relocs = NULL; +static uint8_t **secdata = NULL; + +static int display_file_header = 0; +static int display_optional_header = 0; +static int display_sections = 0; + static const struct { - int magic; - char *machine; + uint16_t magic; + const char *machine; } MACHINES[] = { {F_MACH_AM33, "Matsushita AM33"}, {F_MACH_AMD64, "Intel amd64"}, @@ -52,24 +72,312 @@ static const struct { {0, NULL} }; -/* */ -static const char *prg_name; -static const char *mach = NULL; -static const char *aoutmag = NULL; +static void +msg_err_common(const char *fmt, va_list ap) +{ + fprintf(stderr, "%s: ", prg_name); + if (fmt) + { + vfprintf(stderr, fmt, ap); + } +} -/* */ -static int display_header = 0; -static int display_optional_header = 0; -static int display_sections = 0; -static int display_symbol_table = 0; -static int display_relocs = 0; +static void +msg_errx(const char *fmt, ...) +{ + va_list ap; + + va_start(ap, fmt); + msg_err_common(fmt, ap); + fprintf(stderr, "\n"); + va_end(ap); +} + +static void +msg_err(const char *fmt, ...) +{ + va_list ap; + + va_start(ap, fmt); + msg_err_common(fmt, ap); + if (fmt) + { + fprintf(stderr, ": "); + } + fprintf(stderr, "%s\n", strerror(errno)); + va_end(ap); +} + +static void +coff_cleanup(void) +{ + size_t idx; + + if (relocs != NULL) + { + for (idx = 0; idx < filhdr.f_nscns; idx++) + { + free(relocs[idx]); + } + free(relocs); + relocs = NULL; + } + if (secdata != NULL) + { + for (idx = 0; idx < filhdr.f_nscns; idx++) + { + free(secdata[idx]); + } + free(secdata); + secdata = NULL; + } + free(scnhdrs); + scnhdrs = NULL; + free(symtab); + symtab = NULL; + free(strtab); + strtab = NULL; + sym_cnt = 0; + sec_cnt = 0; + machine = NULL; + aoutmag = NULL; +} + +static int +coff_load_headers(const char *file, FILE *fp) +{ + size_t idx; + + if (fread(&filhdr, FILHSZ, 1, fp) != 1) + { + msg_errx("%s: An unexpected error/eof occured while reading " \ + "COFF header", file); + return (-1); + } + + for (idx = 0; MACHINES[idx].magic != F_MACH_UNKNOWN; idx++) + { + if (filhdr.f_magic == MACHINES[idx].magic) + { + machine = MACHINES[idx].machine; + break; + } + } + + if (machine == NULL) + { + msg_errx("%s: Unknown magic '0x%04" PRIX16 "'", + file, filhdr.f_magic); + return (-1); + } + + if (filhdr.f_opthdr == 0) + { + return (0); + } + + if (filhdr.f_opthdr != AOUTHSZ) + { + msg_errx("%s: Invalid optional header size", file); + return (-1); + } + + if (fread(&aouthdr, AOUTHSZ, 1, fp) != 1) + { + msg_errx("%s: An unexpected error/eof occured while reading " \ + "optional header", file); + return (-1); + } + + for (idx = 0; AOUTMAG[idx].str != NULL; idx++) + { + if (aouthdr.magic == AOUTMAG[idx].mag) + { + aoutmag = AOUTMAG[idx].str; + break; + } + } + + if (aoutmag == NULL) + { + msg_errx("%s: Invalid optional header magic", file); + return (-1); + } + + return (0); +} + +static int +coff_load_sections(const char *file, FILE *fp) +{ + uint16_t idx; + + relocs = (RELOC **)malloc(sizeof(RELOC *) * filhdr.f_nscns); + if (relocs == NULL) + { + msg_err("%s", file); + return (-1); + } + memset(relocs, 0, sizeof(RELOC *) * filhdr.f_nscns); + + secdata = (uint8_t **)malloc(sizeof(uint8_t *) * filhdr.f_nscns); + if (secdata == NULL) + { + msg_err("%s", file); + return (-1); + } + memset(secdata, 0, sizeof(uint8_t *) * filhdr.f_nscns); + + scnhdrs = (SCNHDR *)malloc(SCNHSZ * filhdr.f_nscns); + if (scnhdrs == NULL) + { + msg_err("%s", file); + return (-1); + } + + if (fread(scnhdrs, SCNHSZ * filhdr.f_nscns, 1, fp) != 1) + { + msg_errx("%s: An unexpected error/eof occured while reading " \ + "section headers", file); + return (-1); + } + + return (0); +} + +static int +coff_load_file(const char *file) +{ + FILE *fp; + + fp = fopen(file, "rb"); + if (fp == NULL) + { + return (-1); + } + + if (coff_load_headers(file, fp) != 0) + { + goto err; + } + + if (coff_load_sections(file, fp) != 0) + { + goto err_cleanup; + } + + fclose(fp); + return (0); +err_cleanup: + coff_cleanup(); +err: + fclose(fp); + return (-1); +} + +static void +print_file_header(void) +{ + size_t idx; + time_t timdat; + + printf("COFF Header:\n"); + printf(" Machine: %s\n", machine); + printf(" Number of section headers: %" PRIu16 "\n", filhdr.f_nscns); + timdat = filhdr.f_timdat; + printf(" Created at: %s", ctime(&timdat)); + printf(" Start of Symbol Table: %" PRId32 " (bytes into file)\n", + filhdr.f_symptr); + printf(" Number of Symbols: %" PRId32 "\n", filhdr.f_nsyms); + printf(" Size of optional header: %" PRIu16 " (bytes)\n", + filhdr.f_opthdr); + printf(" Flags: "); + for (idx = 0; FLAGS[idx].str != NULL; idx++) + { + if (filhdr.f_flags & FLAGS[idx].flag) + { + printf("%s ", FLAGS[idx].str); + } + } + printf("\n\n"); +} + +static void +print_optional_header(void) +{ + if (filhdr.f_opthdr) + { + printf("A.out Header:\n"); + printf(" Magic: %s\n", aoutmag); + printf(" Version stamp: %" PRId16 "\n", aouthdr.vstamp); + printf(" Text size: %" PRId32 " (bytes)\n", aouthdr.tsize); + printf(" Data size: %" PRId32 " (bytes)\n", aouthdr.dsize); + printf(" BSS size: %" PRId32 " (bytes)\n", aouthdr.bsize); + printf(" Entry point: 0x%08" PRIX32 "\n", aouthdr.entry); + printf(" Text start: 0x%08" PRIX32 "\n", aouthdr.text_start); + printf(" Data start: 0x%08" PRIX32 "\n", aouthdr.data_start); + printf("\n"); + } + else + { + printf("There is no optional header.\n\n"); + } +} + +static void +print_section_type(uint16_t idx) +{ + if (scnhdrs[idx].s_flags & STYP_TEXT) + { + printf("TEXT "); + } + else if (scnhdrs[idx].s_flags & STYP_DATA) + { + printf("DATA "); + } + else if (scnhdrs[idx].s_flags & STYP_BSS) + { + printf("BSS "); + } + else + { + printf("??? "); + } +} + +static void +print_sections(void) +{ + uint16_t idx; + char name[9]; + + printf("Section Headers:\n"); + printf(" [Nr] Name Type Paddr Vaddr Offset Size\n"); + + for (idx = 0; idx < filhdr.f_nscns; idx++) + { + printf(" [%2" PRIu16 "] ", idx); + + memset(name, 0, 9); + memcpy(name, scnhdrs[idx].s_name, 8); + printf("%-8s ", name); + print_section_type(idx); + printf("%08" PRIX32 " %08" PRIX32 " ", + scnhdrs[idx].s_paddr, scnhdrs[idx].s_vaddr); + printf("%08" PRIX32 " %08" PRIX32 "\n", + scnhdrs[idx].s_scnptr, scnhdrs[idx].s_size); + } + + printf("\n"); +} static void usage(int retval) { if (retval == EXIT_FAILURE) { - fprintf(stderr, "Try '%s -h' for more informations.", prg_name); + fprintf(stderr, "Try '%s -h' for more informations.\n", + prg_name); } else { @@ -85,10 +393,100 @@ usage(int retval) static void version(void) { - printf("%s (%s) %s", prg_name, MK_PACKAGE, MK_COMMIT); + printf("%s (%s) %s\n", prg_name, MK_PACKAGE, MK_COMMIT); exit(EXIT_SUCCESS); } +int +main(int argc, char **argv) +{ + int c; + + prg_name = basename(argv[0]); + + while ((c = getopt(argc, argv, "hVHlS")) != -1) + { + switch (c) + { + case 'h': + usage(EXIT_SUCCESS); + break; + case 'V': + version(); + break; + case 'H': + display_file_header = 1; + break; + case 'l': + display_optional_header = 1; + break; + case 'S': + display_sections = 1; + break; + default: + usage(EXIT_FAILURE); + break; + } + } + + if (optind >= argc) + { + usage(EXIT_FAILURE); + } + + if (coff_load_file(argv[optind]) != 0) + { + return (EXIT_FAILURE); + } + + if (display_file_header) + { + print_file_header(); + } + + if (display_optional_header) + { + print_optional_header(); + } + + if (display_sections) + { + print_sections(); + } + + coff_cleanup(); + return (EXIT_SUCCESS); +} + +#if 0 +#include +#include +#include +#include +#include +#ifndef __stupidos__ +# include +#endif +#include + + + + + +/* */ +static const char *prg_name; +static const char *mach = NULL; +static const char *aoutmag = NULL; + +/* */ +static int display_header = 0; +static int display_optional_header = 0; +static int display_sections = 0; +static int display_symbol_table = 0; +static int display_relocs = 0; + + + int main(int argc, char **argv) { @@ -202,7 +600,7 @@ main(int argc, char **argv) { aoutmag = AOUTMAG[idx].str; break; - } + } } printf("A.out header\n"); printf(" Magic: %s\n", aoutmag); @@ -308,3 +706,4 @@ main(int argc, char **argv) return (EXIT_SUCCESS); } +#endif diff --git a/boot/Makefile b/boot/Makefile index 00745f7..c05fafc 100644 --- a/boot/Makefile +++ b/boot/Makefile @@ -1,3 +1,3 @@ -SUBDIRS = bootsect loader efi +SUBDIRS = bootsect efi loader -include $(TOPDIR)/rules.mk +include stpd.subdirs.mk diff --git a/boot/bootsect/Makefile b/boot/bootsect/Makefile index a3dfaa8..adbc33e 100644 --- a/boot/bootsect/Makefile +++ b/boot/bootsect/Makefile @@ -1,4 +1,6 @@ -TARGET = boot_floppy1440.bin \ +include stpd.base.mk + +BINS = boot_floppy1440.bin \ boot_floppy2880.bin \ boot_mbr.bin \ boot_hdd.bin @@ -18,26 +20,30 @@ MBR_SRCS = mbr.asm \ $(addprefix $(COMMON_DIR)/, $(COMMON_SRCS)) .PHONY: all -all: $(TARGET) +all: $(BINS) %.inc: %.inc.in - sh $(TOOLSDIR)/version.sh $< $@ + @$(VERSION_SH) boot_floppy1440.bin: $(FLOPPY_SRCS) - $(AS) floppy.asm $@ + $(MSG_BUILD) + @$(FASM) floppy.asm $@ >/dev/null boot_floppy2880.bin: $(FLOPPY_SRCS) - $(AS) -DFLOPPY_SIZE=FLOPPY_2880 floppy.asm $@ + $(MSG_BUILD) + @$(FASM) -DFLOPPY_SIZE=FLOPPY_2880 floppy.asm $@ >/dev/null boot_mbr.bin: $(MBR_SRCS) - $(AS) mbr.asm $@ + $(MSG_BUILD) + @$(FASM) mbr.asm $@ >/dev/null boot_hdd.bin: $(HDD_SRCS) - $(AS) hdd.asm $@ - -.PHONY: clean -clean: - $(RM) $(TARGET) + $(MSG_BUILD) + @$(FASM) hdd.asm $@ >/dev/null .PHONY: install -install: $(TARGET) +install: $(BINS) + +CLEANFILES = $(BINS) $(COMMON_DIR)/const.inc + +include stpd.clean.mk diff --git a/boot/bootsect/mbr.asm b/boot/bootsect/mbr.asm index 8a2aa16..bec6ebf 100644 --- a/boot/bootsect/mbr.asm +++ b/boot/bootsect/mbr.asm @@ -22,7 +22,10 @@ jmp 0x0:start start: - ; set LBA + sti + mov [uBootDrive], dl + + ; set LBA mov ah, 0x41 mov bx, 0x55AA mov dl, 0x80 @@ -61,6 +64,8 @@ start: hlt jmp $ +uBootDrive db 0 + disk_packet: db 0x10 db 0 diff --git a/boot/efi/Makefile b/boot/efi/Makefile index 0cfef0b..66cdb67 100644 --- a/boot/efi/Makefile +++ b/boot/efi/Makefile @@ -1,5 +1,4 @@ -TARGET = BOOTIA32.EFI - +include stpd.base.mk COMMON_DIR = ../common @@ -15,19 +14,22 @@ BOOTIA32_EFI_SRCS = bootia32.asm \ $(addprefix $(COMMON_DIR)/, $(COMMON_SRCS)) .PHONY: all -all: $(TARGET) +all: BOOTIA32.EFI %.inc: %.inc.in - sh $(TOOLSDIR)/version.sh $< $@ + @$(VERSION_SH) BOOTIA32.EFI: $(BOOTIA32_EFI_SRCS) - $(AS) bootia32.asm $@ - -.PHONY: clean -clean: - $(RM) $(TARGET) + $(MSG_BUILD) + @$(FASM) bootia32.asm $@ >/dev/null .PHONY: install -install: $(TARGET) - @ mkdir -p $(DESTDIR)/EFI/BOOT - install $(TARGET) $(DESTDIR)/EFI/BOOT +install: $(DESTDIR)/EFI/BOOT/BOOTIA32.EFI + +$(DESTDIR)/EFI/BOOT/BOOTIA32.EFI: BOOTIA32.EFI + $(MSG_INSTALL) + @install -D $< $@ + +CLEANFILES = BOOTIA32.EFI $(COMMON_DIR)/const.inc + +include stpd.clean.mk diff --git a/boot/loader/Makefile b/boot/loader/Makefile index f6aeef3..6a46969 100644 --- a/boot/loader/Makefile +++ b/boot/loader/Makefile @@ -1,4 +1,4 @@ -TARGET = stpdldr.sys +include stpd.base.mk COMMON_DIR = ../common SYS_DIR = ../../kernel/sys @@ -22,19 +22,22 @@ LOADER_SRCS = loader.asm \ disk.inc .PHONY: all -all: $(TARGET) - -%.inc: %.inc.in - sh $(TOOLSDIR)/version.sh $< $@ +all: stpdldr.sys stpdldr.sys: $(LOADER_SRCS) - $(AS) loader.asm $@ + $(MSG_BUILD) + @$(FASM) loader.asm $@ >/dev/null -.PHONY: clean -clean: - $(RM) $(TARGET) +%.inc: %.inc.in + @$(VERSION_SH) .PHONY: install -install: $(TARGET) - @ mkdir -p $(DESTDIR) - install $(TARGET) $(DESTDIR) +install: $(DESTDIR)/stpdldr.sys + +$(DESTDIR)/stpdldr.sys: stpdldr.sys + $(MSG_INSTALL) + @install -D $< $@ + +CLEANFILES = stpdldr.sys $(COMMON_DIR)/const.inc + +include stpd.clean.mk diff --git a/compile_flags.txt b/compile_flags.txt new file mode 100644 index 0000000..274c984 --- /dev/null +++ b/compile_flags.txt @@ -0,0 +1,4 @@ +-Iinclude +-DMK_COMMIT="\"XXXX\"" +-DMK_BUGREPORT="\"XXXX\"" +-DMK_PACKAGE="\"build\"" diff --git a/external/Makefile b/external/Makefile index 00321ad..0fad5e5 100644 --- a/external/Makefile +++ b/external/Makefile @@ -1,11 +1 @@ -TOPGOALS = all clean install - -SUBDIRS = - -.PHONY: $(TOPGOALS) -$(TOPGOALS): $(SUBDIRS) - -.PHONY: $(SUBDIRS) -$(SUBDIRS): - @echo "📁 external/$@" - @DESTDIR=$(DESTDIR) $(MAKE) -C $@ $(MAKECMDGOALS) +include stpd.subdirs.mk diff --git a/include/Makefile b/include/Makefile index 25c5742..29d9dbb 100644 --- a/include/Makefile +++ b/include/Makefile @@ -1,4 +1,4 @@ SYSINCS = errno.h -INCS = coff.h elf.h ar.h ranlib.h $(addprefix sys/, $(SYSINCS)) +INCS = ar.h coff.h elf.h fas.h ranlib.h stupidc.h $(addprefix sys/, $(SYSINCS)) -include $(TOPDIR)/rules.mk +include stpd.inc.mk diff --git a/include/fas.h b/include/fas.h index 6081ddb..3b09671 100644 --- a/include/fas.h +++ b/include/fas.h @@ -51,7 +51,6 @@ enum fas_symbol_type FAS_PLT_R_32 }; - typedef struct fas_symbol { uint64_t value; @@ -66,14 +65,14 @@ typedef struct fas_symbol uint32_t psrc_line_off; } FAS_Sym; -struct fas_psrc_line +typedef struct fas_psrc_line { uint32_t from; uint32_t lineno; uint32_t src_off; uint32_t macro_off; uint8_t tokens[]; -}; +} FAS_Psrc_Line; enum fas_code { @@ -82,7 +81,7 @@ enum fas_code FAS_CODE_64 = 64 }; -struct fas_asmdmp +typedef struct fas_asmdmp { uint32_t of_off; uint32_t psrc_line_off; @@ -93,7 +92,7 @@ struct fas_asmdmp uint8_t code; uint8_t virt; uint8_t high; -}; +} FAS_Asmdmp; enum fas_register { diff --git a/include/stupidc.h b/include/stupidc.h new file mode 100644 index 0000000..70c57e2 --- /dev/null +++ b/include/stupidc.h @@ -0,0 +1,62 @@ +#ifndef STUPIDC_H +# define STUPIDC_H 1 + +# include + +# define ARR_BASE_CAP 8 + +# define ARR(type) \ + struct { size_t cap; size_t cnt; type *elems; } + +# define ARR_INIT { 0, 0, NULL } + +# define ARR_GROW(arr) \ + do { \ + if ((arr)->cap < ((arr)->cnt + 1)) \ + { \ + (arr)->cap = ((arr)->cap > ARR_BASE_CAP \ + ? (arr)->cap * 2 : ARR_BASE_CAP); \ + (arr)->elems = realloc((arr)->elems, \ + (arr)->cap * sizeof(*(arr)->elems)); \ + } \ + } while(0) + +# define ARR_APPEND(arr, elem) \ + do { \ + ARR_GROW((arr)); \ + (arr)->elems[(arr)->cnt++] = (elem); \ + } while (0) + +# define ARR_RESET(arr) \ + do { \ + (arr)->cnt = 0; \ + } while (0) + +# define ARR_FREE(arr) \ + do { \ + (arr)->cap = 0; \ + (arr)->cnt = 0; \ + free((arr)->elems); \ + (arr)->elems = NULL; \ + } while(0) + +# define ARR_COUNT(arr) ((arr)->cnt) +# define ARR_EMPTY(arr) ((arr)->cnt == 0) +# define ARR_INDEX(arr, elem) ((elem) - (arr)->elems) +# define ARR_FIRST(arr) ((arr)->elems[0]) +# define ARR_LAST(arr) ((arr)->elems[(arr)->cnt]) + +# define ARR_FOREACH(var, arr) \ + for ((var) = (arr)->elems; \ + (var) < ((arr)->elems + (arr)->cnt); \ + (var)++) + +# define LIST(type) \ + struct { struct type *next; struct type **prev } + +void set_progname(const char *name); +const char *get_progname(void); + +void print_version(void); + +#endif /* !STUPIDC_H */ diff --git a/kernel/Makefile b/kernel/Makefile index e5edead..922b178 100644 --- a/kernel/Makefile +++ b/kernel/Makefile @@ -1,6 +1,4 @@ -AS = fasm -RM = rm -f -INSTALL = install +include stpd.base.mk ASMINCS = sys/bootinfo.inc \ sys/coff.inc \ @@ -11,7 +9,7 @@ ASMINCS = sys/bootinfo.inc \ sys/process.inc \ sys/register.inc -KERNEL = vmstupid.sys +KERNEL = vmstupid MM_SRCS = bootstrap.inc \ mm.inc \ @@ -47,24 +45,32 @@ SRCS = kernel.asm \ $(ASMINCS) .PHONY: all -all: $(KERNEL) +all: $(KERNEL).sys $(KERNEL).sym .PHONY: const.inc const.inc: const.inc.in - sh $(TOOLSDIR)/version.sh $< $@ + @$(VERSION_SH) -$(KERNEL): $(SRCS) - $(AS) kernel.asm $@ +$(KERNEL).sys $(KERNEL).fas &: $(SRCS) + $(MSG_BUILD) + @$(FASM) -s $(KERNEL).fas kernel.asm $(KERNEL).sys >/dev/null -.PHONY: clean -clean: - $(RM) $(KERNEL) +$(KERNEL).sym: $(KERNEL).fas + $(MSG_CREATE) + @$(FAS2SYM) -o $@ $< .PHONY: install -install: $(KERNEL) - @ mkdir -p $(DESTDIR) - install $(KERNEL) $(DESTDIR) - @ mkdir -p $(DESTDIR)$(ASMDIR)/sys - install $(ASMINCS) $(DESTDIR)$(ASMDIR)/sys +install: $(DESTDIR)/$(KERNEL).sys $(SYMSDIR)/$(KERNEL).sym -.PHONY: all clean install +$(DESTDIR)/$(KERNEL).sys: $(KERNEL).sys + $(MSG_INSTALL) + @install -D $< $@ + +$(SYMSDIR)/$(KERNEL).sym: $(KERNEL).sym + $(MSG_INSTALL) + @install -D $< $@ + +CLEANFILES = $(KERNEL).sys $(KERNEL).fas $(KERNEL).sys const.inc + +include stpd.clean.mk +include stpd.inc.mk diff --git a/lib/Makefile b/lib/Makefile index 6a42b90..ec5552a 100644 --- a/lib/Makefile +++ b/lib/Makefile @@ -1,3 +1,3 @@ SUBDIRS = csu crypto lzp c -include $(TOPDIR)/rules.mk +include stpd.subdirs.mk diff --git a/lib/c/Makefile b/lib/c/Makefile index 29ee6ae..7c3ecb8 100644 --- a/lib/c/Makefile +++ b/lib/c/Makefile @@ -14,9 +14,6 @@ $(LIBS): $(OBJS) %.o: %.asm $(AS) $< $@ -$(DESTDIR)$(INCDIR)/%.h: %.h - install -D $< $@ - $(DESTDIR)$(LIBDIR)/%.a: %.a install -D $< $@ @@ -26,3 +23,5 @@ clean: .PHONY: install install: $(INST) + +include stpd.inc.mk diff --git a/lib/crypto/Makefile b/lib/crypto/Makefile index 19941f9..d32bdde 100644 --- a/lib/crypto/Makefile +++ b/lib/crypto/Makefile @@ -8,13 +8,11 @@ INCS = sha2/sha2.h \ dilithium/dilithium.h \ falcon/falcon.h \ keccak/keccak.h -ASMS = sha2/sha2.inc \ +ASMINCS = sha2/sha2.inc \ chacha/chacha.inc \ hchacha/hchacha.inc -INST = $(addprefix $(DESTDIR)$(INCDIR)/, $(INCS)) \ - $(addprefix $(DESTDIR)$(ASMDIR)/, $(ASMS)) \ - $(addprefix $(DESTDIR)$(LIBDIR)/, $(LIBS)) +INST = $(addprefix $(DESTDIR)$(LIBDIR)/, $(LIBS)) .PHONY: all all: $(LIBS) @@ -25,11 +23,6 @@ $(LIBS): $(OBJS) %.o: %.asm $(AS) $< $@ -$(DESTDIR)$(INCDIR)/%.h: %.h - install -D $< $@ - -$(DESTDIR)$(ASMDIR)/%.inc: %.inc - install -D $< $@ $(DESTDIR)$(LIBDIR)/%.a: %.a install -D $< $@ @@ -41,4 +34,4 @@ clean: .PHONY: install install: $(INST) - +include stpd.inc.mk diff --git a/lib/csu/Makefile b/lib/csu/Makefile index 91684fc..ecd0332 100644 --- a/lib/csu/Makefile +++ b/lib/csu/Makefile @@ -14,3 +14,5 @@ clean: $(RM) $(LIBS) install: $(INST) + +include stpd.base.mk diff --git a/lib/lzp/Makefile b/lib/lzp/Makefile index da9aa17..c9eb8aa 100644 --- a/lib/lzp/Makefile +++ b/lib/lzp/Makefile @@ -17,12 +17,6 @@ $(LIBS): $(OBJS) %.o: %.asm $(AS) $< $@ -$(DESTDIR)$(INCDIR)/%.h: %.h - install -D $< $@ - -$(DESTDIR)$(ASMDIR)/%.inc: %.inc - install -D $< $@ - $(DESTDIR)$(LIBDIR)/%.a: %.a install -D $< $@ @@ -33,3 +27,4 @@ clean: .PHONY: install install: $(INST) +include stpd.inc.mk diff --git a/lib/stupidc/progname.c b/lib/stupidc/progname.c new file mode 100644 index 0000000..33ae957 --- /dev/null +++ b/lib/stupidc/progname.c @@ -0,0 +1,30 @@ +#include +#include + +#ifdef _WIN32 +# define PATH_SEP '\\' +#else +# define PATH_SEP '/' +#endif /* _WIN32 */ + +static const char *__progname; + +void +set_progname(const char *progname) +{ + __progname = strrchr(progname, PATH_SEP); + if (__progname == NULL) + { + __progname = progname; + } + else + { + __progname++; + } +} + +const char * +get_progname(void) +{ + return (__progname); +} diff --git a/lib/stupidc/version.c b/lib/stupidc/version.c new file mode 100644 index 0000000..e79734c --- /dev/null +++ b/lib/stupidc/version.c @@ -0,0 +1,20 @@ +#include +#include + +#ifndef MK_PACKAGE +# define MK_PACKAGE "StupidOS" +#endif /* !MK_PACKAGE */ + +#ifndef MK_COMMIT +# define MK_COMMIT "???????" +#endif /* !MK_COMMIT */ + +void +print_version(void) +{ + printf("%s (%s) %s\n", get_progname(), MK_PACKAGE, MK_COMMIT); + printf("Copyright (C) 2025, d0p1\n" + "License BSD-3-Clause: \n" + "This is free software: you are free to change and redistribute it.\n" + "There is NO WARRANTY, to the extent permitterd by law.\n"); +} diff --git a/modules/Makefile b/modules/Makefile index 2f95850..5942cda 100644 --- a/modules/Makefile +++ b/modules/Makefile @@ -1,3 +1,3 @@ SUBDIRS = dummy -include $(TOPDIR)/rules.mk +include stpd.subdirs.mk diff --git a/modules/dummy/Makefile b/modules/dummy/Makefile index 928105c..103b503 100644 --- a/modules/dummy/Makefile +++ b/modules/dummy/Makefile @@ -1,16 +1,20 @@ +include stpd.base.mk + MODULE = dummy.mod -INST = $(addprefix $(DESTDIR)/, $(MODULE)) - -all: - -clean: +all: $(MODULE) $(MODULE): $(MODULE:.mod=.asm) - fasm $^ $@ + $(MSG_BUILD) + @fasm $^ $@ -$(DESTDIR)/%.mod: %.mod - install -D $< $@ +$(DESTDIR)/$(MODULE): $(MODULE) + $(MSG_INSTALL) + @install -D $< $@ .PHONY: install -install: $(INST) +install: $(DESTDIR)/$(MODULE) + +CLEANFILES = $(MODULE) + +include stpd.clean.mk diff --git a/rules.mk b/rules.mk deleted file mode 100644 index b89f772..0000000 --- a/rules.mk +++ /dev/null @@ -1,87 +0,0 @@ -TARGETS = all install clean -.PHONY: $(TARGETS) -$(TARGETS): ; - -_INST = $(addprefix $(DESTDIR)$(INCDIR)/, $(INCS)) \ - $(addprefix $(DESTDIR)$(ASMDIR)/, $(ASMINCS)) \ - $(addprefix $(DESTDIR)$(LIBDIR)/, $(LIB)) - -# ----------------- Subdirs ----------------------- - -ifdef SUBDIRS - -_SUBDIRS:=$(filter-out .WAIT,$(SUBDIRS)) -_CURDIR=$(subst $(TOPDIR),,$(CURDIR)) -ifneq ($(_CURDIR),) -_CURDIR:=$(_CURDIR)/ -endif - -.PHONY: $(_SUBDIRS) -$(_SUBDIRS): - @echo "📁 $(_CURDIR)$@" - @DESTDIR=$(DESTDIR) $(MAKE) -C $@ $(MAKECMDGOALS) - -$(TARGETS): $(SUBDIRS) - -endif - -# --------------- Build rules ------------------ - -%.o: %.asm - $(AS) $< $@ - -# --------------- Lib rules -------------------- - -ifneq ($(LIB),) - -all: $(LIB) - -_cleanlib: - $(RM) $(LIB) - -clean: _cleanlib - -endif - -# --------------- Progs rules ------------------- - -ifneq ($(PROG),) - -all: $(PROG) - - -endif - -# --------------- Install rules ----------------- - -ifneq ($(_INST),) - -install: $(_INST) - -endif - -# headers -$(DESTDIR)$(INCDIR)/%.h: %.h - install -D $< $@ - -$(DESTDIR)$(ASMDIR)/%.inc: %.inc - install -D $< $@ - -# libs -$(DESTDIR)$(LIBDIR)/%.a: %.a - install -D $< $@ - -$(DESTDIR)$(LIBDIR)/%.o: %.o - install -D $< $@ - -# bins -$(DESTDIR)$(BINDIR)/%: % - install -D $< $@ - -# kernel & mods -$(DESTDIR)/%.sys: %.sys - install -D $< $@ - -$(DESTDIR)/%.mod: %.mod - install -D $< $@ - diff --git a/sbin/Makefile b/sbin/Makefile new file mode 100644 index 0000000..0fad5e5 --- /dev/null +++ b/sbin/Makefile @@ -0,0 +1 @@ +include stpd.subdirs.mk diff --git a/sbin/mtree/main.c b/sbin/mtree/main.c new file mode 100644 index 0000000..7fea210 --- /dev/null +++ b/sbin/mtree/main.c @@ -0,0 +1,77 @@ +#include +#include +#include +#include +#include + +#ifndef PATH_MAX +# define PATH_MAX 1024 +#endif /* !PATH_MAX */ + +static char curdir[PATH_MAX] = { 0 }; + +static const char *prg_name = NULL; + +static const char *specfile = NULL; +static const char *basepath = NULL; + +static FILE *specfp = NULL; + +static void +usage(int retval) +{ + if (retval == EXIT_FAILURE) + { + fprintf(stderr, "Try '%s -h' for more informations.\n", + prg_name); + } + else + { + printf("Usage: %s [-ce] [-p path] [-f spec]\n", prg_name); + printf(" -c \tXXX.\n"); + printf(" -e \tXXXX\n"); + printf(" -f spec\tXXXX\n"); + printf(" -p path\tXXXX\n"); + } + exit(retval); +} + +int +main(int argc, char **argv) +{ + int c; + + prg_name = basename(argv[0]); + + while ((c = getopt(argc, argv, "hf:")) != -1) + { + switch (c) + { + case 'h': + usage(EXIT_SUCCESS); + break; + case 'f': + specfile = optarg; + break; + case 'p': + basepath = optarg; + break; + default: + usage(EXIT_FAILURE); + break; + } + } + + if (basepath == NULL) + { + basepath = getcwd(curdir, PATH_MAX); + if (basepath == NULL) + { + return (EXIT_FAILURE); + } + } + + printf("basepath: %s\n", basepath); + + return (EXIT_SUCCESS); +} diff --git a/sbin/mtree/mtree.h b/sbin/mtree/mtree.h new file mode 100644 index 0000000..046468b --- /dev/null +++ b/sbin/mtree/mtree.h @@ -0,0 +1,47 @@ +#ifndef MTREE_H +# define MTREE_H 1 + +# include +# include + +# define NODE_PARENT(n) ((n)->tree.parent) +# define NODE_CHILD_FIRST(n) ((n)->tree.child) +# define NODE_CHILD_ADD(p, c) do { \ + (c)->tree.parent = p; \ + if (((c)->list.next = (p)->tree.child) != NULL) { \ + (p)->tree.child->list.prev = &(c)->list.next; \ + } \ + (p)->tree.child = (c); \ + (c)->list.prev = (p)->tree.child; \ + } while(0); + +enum flags { + FL_TYPE = (1<<0), + FL_MODE = (1<<1), + FL_UID = (1<<2), + FL_GID = (1<<3), +}; + +struct node { + struct { + struct node *parent; + struct node *child; + } tree; + struct { + struct node *next; + struct node **prev; + } list; + + uint32_t flags; + mode_t mode; + uid_t uid; + gid_t gid; + char *name; +}; + +/* node.c */ +struct node *node_new(void); +void node_free(struct *node); +void node_dump(struct *node); + +#endif /* !MTREE_H */ diff --git a/sbin/parted/cmd.c b/sbin/parted/cmd.c new file mode 100644 index 0000000..1437a37 --- /dev/null +++ b/sbin/parted/cmd.c @@ -0,0 +1,120 @@ +#include +#include +#include +#include +#include + +static inline void +cmd_help_print_idx(size_t idx) +{ + printf("\e[1m%s\e[0m", cmds[idx].cmd); + if (cmds[idx].args != NULL) + { + printf(" \e[3m%s\e[0m", cmds[idx].args); + } + printf("\n\t%s\n", cmds[idx].desc); +} + +static int +cmd_help(struct context *ctx, int argc, char **argv) +{ + size_t idx; + + (void)ctx; + (void)argc; + (void)argv; + + for (idx = 0; cmds[idx].cmd != NULL; idx++) + { + if (argc >= 2) + { + if (strcmp(argv[1], cmds[idx].cmd) == 0) + { + cmd_help_print_idx(idx); + return (0); + } + } + else + { + cmd_help_print_idx(idx); + } + } + + if (argc >= 2) + { + printf("\e[31mError:\e[0m Unknown command \"%s\"\n", argv[1]); + return (-1); + } + return (0); +} + +static int +cmd_version(struct context *ctx, int argc, char **argv) +{ + (void)ctx; + (void)argc; + (void)argv; + + print_version(); + + return (0); +} + +static int +cmd_print(struct context *ctx, int argc, char **argv) +{ + long disk_sz; + + (void)argc; + (void)argv; + fseek(ctx->dsk_fp, 0, SEEK_END); + disk_sz = ftell(ctx->dsk_fp); + rewind(ctx->dsk_fp); + printf("Disk %s: %ldB\n", ctx->dsk_fname, disk_sz); + return (0); +} + +static int +cmd_quit(struct context *ctx, int argc, char **argv) +{ + (void)argc; + (void)argv; + + if (ctx->dsk_fp != NULL) + { + fclose(ctx->dsk_fp); + } + exit(EXIT_SUCCESS); + + return (0); +} + +static int +cmd_set(struct context *ctx, int argc, char **argv) +{ + return (0); +} + +static int +cmd_rm(struct context *ctx, int argc, char **argv) +{ + return (0); +} + +static int +cmd_mklabel(struct context *ctx, int argc, char **argv) +{ + return (0); +} + + +const struct cmd cmds[] = { + DEF_CMD(help, "[command]", "Display general help or 'command' help"), + DEF_CMD(version, NULL, "Display version information and copyright message"), + DEF_CMD(print, NULL, "Display partition table"), + DEF_CMD(mklabel, "label-type", "Create a new partition table of 'label-type'. 'label-type' should be one of \"msdos\" or \"gpt\"."), + DEF_CMD(rm, "partition", "Delete 'partition'"), + DEF_CMD(set, "partition flag [state]", "XXX"), + DEF_CMD(quit, NULL, "Exit from fdisk"), + { NULL, NULL, NULL, NULL } +}; diff --git a/sbin/parted/disk.c b/sbin/parted/disk.c new file mode 100644 index 0000000..a226ef3 --- /dev/null +++ b/sbin/parted/disk.c @@ -0,0 +1,13 @@ +#include + +int +disk_init(struct disk *dsk, struct device *dev) +{ + if (dsk == NULL || dev == NULL) + { + return (-1); + } + + memset(dsk, 0, sizeof(struct disk)); + disk->dev = dev; +} diff --git a/sbin/parted/disk.h b/sbin/parted/disk.h new file mode 100644 index 0000000..1379ff5 --- /dev/null +++ b/sbin/parted/disk.h @@ -0,0 +1,4 @@ +#ifndef PARTED_DISK_H +# define PARTED_DISK_H 1 + +#endif diff --git a/sbin/parted/fdisk/cmd.h b/sbin/parted/fdisk/cmd.h new file mode 100644 index 0000000..f3d98c7 --- /dev/null +++ b/sbin/parted/fdisk/cmd.h @@ -0,0 +1,29 @@ +#ifndef FDISK_CMD_H +# define FDISK_CMD_H 1 + +# define FDISK_LINE_MAX 1024 + +struct context { + const char *dsk_fname; + FILE *dsk_fp; + + int script; +}; + +struct cmd { + const char *cmd; + const char *args; + const char *desc; + int (*cb)(struct context *, int, char **); +}; + +# define DEF_CMD(name, args, desc) \ + { #name, args, desc, cmd_##name } + +/* cmd.c */ +extern const struct cmd cmds[]; + +/* repl.c */ +int repl(struct context *ctx); + +#endif /* :FDISK_CMD_H */ diff --git a/sbin/parted/fdisk/device.h b/sbin/parted/fdisk/device.h new file mode 100644 index 0000000..c31400d --- /dev/null +++ b/sbin/parted/fdisk/device.h @@ -0,0 +1,33 @@ +#ifndef FDISK_DEVICE_H +# define FDISK_DEVICE_H 1 + +# include + +# define DEVICE_IS_OPEN(dev) ((dev)->status & (DEV_OPEN)) + +enum device_status { + DEV_OPEN = 1 << 0, + DEV_RDONLY = 1 << 1, +}; + +struct device { + const char *path; + + uint8_t status; + + uint16_t ph_secsz; + uint16_t lg_secsz; + + uint64_t size; + uint64_t ph_secnt; + uint64_t lg_secnt; +}; + +int device_open(struct device *dev, const char *path); +int device_close(struct device *dev); +int device_read(struct device *dev, uint8_t *buff, uint64_t lba, + int count); +int device_write(struct device *dev, const uint8_t *buff, uint64_t lba, + int count); + +#endif /* !FDISK_DEVICE_H */ diff --git a/sbin/parted/fdisk/disk.h b/sbin/parted/fdisk/disk.h new file mode 100644 index 0000000..8683559 --- /dev/null +++ b/sbin/parted/fdisk/disk.h @@ -0,0 +1,37 @@ +#ifndef FDISK_DISK_H +# define FDISK_DISK_H 1 + +struct disk; +struct device; +struct partition; + +struct disk_ops { + int (*probe)(struct disk *dsk); +}; + +# define DEF_DISK_OPS(name) \ + static const struct disk_ops ##name_ops = { ##name_probe } + +struct disk_label { + const char *name; + const struct disk_ops *ops; + + /* */ + struct disk_label *next; + struct disk_label **prev; +}; + +# define DEF_DISK_LABEL(name) \ + static const struct disk_label ##name_label = { \ + #name, &##name_ops, 0, 0} + +struct disk { + struct device *dev; + struct disk_label *label; + struct partition *parts; +}; + +int disk_init(struct disk *dsk); +int disk_cleanup(struct disk *dsk); + +#endif /* !FDISK_DISK_H */ diff --git a/sbin/parted/fdisk/partition.h b/sbin/parted/fdisk/partition.h new file mode 100644 index 0000000..83493eb --- /dev/null +++ b/sbin/parted/fdisk/partition.h @@ -0,0 +1,12 @@ +#ifndef FDISK_PARTITION_H +# define FDISK_PARTITION_H 1 + +enum partition_flags { + PARTITION_BOOTABLE, +}; + +struct partition { + int dummy; +}; + +#endif /* !FDISK_PARTITION_H */ diff --git a/sbin/parted/fdisk/version.h b/sbin/parted/fdisk/version.h new file mode 100644 index 0000000..cc0c3bc --- /dev/null +++ b/sbin/parted/fdisk/version.h @@ -0,0 +1,6 @@ +#ifndef FDISK_VERSION_H +# define FDISK_VERSION_H 1 + +void print_version(void); + +#endif /* !FDISK_VERSION_H */ diff --git a/sbin/parted/fildev.c b/sbin/parted/fildev.c new file mode 100644 index 0000000..f7b2b5e --- /dev/null +++ b/sbin/parted/fildev.c @@ -0,0 +1,119 @@ +#include +#include + +#define DEFAULT_SECSZ 512 + +static FILE *fildev_fp = NULL; + +int +device_open(struct device *dev, const char *path) +{ + long sz; + + if (dev == NULL || path == NULL) + { + return (-1); + } + + dev->path = path; + fildev_fp = fopen(dev->path, "r+b"); + if (fildev_fp == NULL) + { + /* XXX: error msg */ + return (-1); + } + + if (fseek(fildev_fp, 0, SEEK_END) != 0) + { + goto err; + } + + sz = ftell(fildev_fp); + if (sz < 0) + { + goto err; + } + + dev->size = (uint64_t)sz; + dev->ph_secsz = DEFAULT_SECSZ; + dev->ph_secnt = dev->size / dev->ph_secsz; + + dev->status = DEV_OPEN; + + return (0); +err: + fclose(fildev_fp); + return (-1); +} + +int +device_close(struct device *dev) +{ + if (dev == NULL || fildev_fp == NULL) + { + return (-1); + } + + if (DEVICE_IS_OPEN(dev)) + { + fclose(fildev_fp); + fildev_fp = NULL; + dev->status &= ~(DEV_OPEN); + } + + return (0); +} + +int +device_read(struct device *dev, uint8_t *buff, uint64_t lba, + int count) +{ + if (dev == NULL || buff == NULL || count == 0) + { + return (-1); + } + + if (!DEVICE_IS_OPEN(dev)) + { + return (-1); + } + + if (fseek(fildev_fp, dev->ph_secsz * lba, SEEK_SET) != 0) + { + return (-1); + } + + if (fread(buff, dev->ph_secsz, count, fildev_fp) != count) + { + return (-1); + } + + return (0); +} + +int +device_write(struct device *dev, const uint8_t *buff, uint64_t lba, + int count) +{ + if (dev == NULL || fildev_fp == NULL || buff == NULL || count == 0) + { + return (-1); + } + + if (!DEVICE_IS_OPEN(dev)) + { + return (-1); + } + + if (fseek(fildev_fp, dev->ph_secsz * lba, SEEK_SET) != 0) + { + return (-1); + } + + if (fwrite(buff, dev->ph_secsz, count, fildev_fp) != count) + { + return (-1); + } + + return (0); +} diff --git a/sbin/parted/gpt.h b/sbin/parted/gpt.h new file mode 100644 index 0000000..9ff9283 --- /dev/null +++ b/sbin/parted/gpt.h @@ -0,0 +1,28 @@ +#ifndef GPT_H +# define GPT_H 1 + +# define GPT_MAGIC "EFI PART" + +# define GPT_UNUSED_ENTRY { 0x00000000, 0x0000, 0x0000, \ + { 0x00, 0x00, 0x00, 0x00, \ + 0x00, 0x00, 0x00, 0x00 }} + +struct gpt_header { + uint8_t magic[8]; + uint32_t revision; + uint32_t hsize; + uint32_t hcrc32; + uint32_t reserved; + uint64_t curr_LBA; + uint64_t alt_LBA; + uint64_t fuse_LBA; + uint64_t luse_LBA; + uint8_t guid[16]; + uint64_t start_LBA; + uint32_t pentnum; + uint32_t pentsize; + uint32_t pentcrc32; +}; + + +#endif /* !GPT_H */ diff --git a/sbin/parted/guid.h b/sbin/parted/guid.h new file mode 100644 index 0000000..a980cef --- /dev/null +++ b/sbin/parted/guid.h @@ -0,0 +1,16 @@ +#ifndef GUID_H +# define GUID_H 1 + +# include + +typedef struct { + uint32_t d1; + uint16_t d2; + uint16_t d3; + uint16_t d4; + uint8_t d5[6]; +} GUID; + +int guid_equal(GUID *g1, GUID *g2); + +#endif /* !GUID_H */ diff --git a/sbin/parted/label/msdos.c b/sbin/parted/label/msdos.c new file mode 100644 index 0000000..ca1a5c3 --- /dev/null +++ b/sbin/parted/label/msdos.c @@ -0,0 +1,11 @@ +#include + +static int +msdos_probe(struct disk *dsk) +{ + (void)dsk; + return (0); +} + +DEF_DISK_OPS(msdos); +DEF_DISK_LABEL(msdos); diff --git a/sbin/parted/main.c b/sbin/parted/main.c index ac42de4..e37040c 100644 --- a/sbin/parted/main.c +++ b/sbin/parted/main.c @@ -2,10 +2,130 @@ #include #include #include +#include #include #include +#include +#include +#include +#include +#include #include "mbr.h" +const char *prg_name = NULL; + +static struct device dev; +static struct disk disk; + +static const char *partfile[4] = { NULL, NULL, NULL, NULL }; + +static int do_list = 0; +static int do_script = 0; +static int do_import = 0; +static int do_export = 0; + +static void +usage(int retcode) +{ + if (retcode == EXIT_FAILURE) + { + fprintf(stderr, "Try '%s -h' for more information.\n", prg_name); + } + else + { + printf("Usage: %s [-hVlsei] [-p0-3 img] disk\n", prg_name); + printf(" Options:\n"); + printf(" -l\tdump disk information\n"); + printf(" -s\tscript mode\n"); + printf(" -h\tdisplay this help and exit\n"); + printf(" -p0-3 img\tXXX\n"); + printf(" -i\timport\n"); + printf(" -e\textract\n"); + printf(" -V\toutput version information.\n"); + printf("\nReport bugs to <%s>\n", MK_BUGREPORT); + } + + exit(retcode); +} + +static void +version(void) +{ + print_version(); + + exit(EXIT_SUCCESS); +} + +static int +parted(const char *disk_path) +{ + struct device dev; + struct disk dsk; + struct context ctx; + + if (device_open(&dev, disk_path) != 0) + { + return (EXIT_FAILURE); + } + + repl(&ctx); + + device_close(&dev); + return (EXIT_SUCCESS); +} + +int +main(int argc, char **argv) +{ + int c; + + prg_name = basename(argv[0]); + while ((c = getopt(argc, argv, "hVlsp:ei")) != -1) + { + switch (c) + { + case 'h': + usage(EXIT_SUCCESS); + break; + case 'V': + version(); + break; + case 'l': + do_list = 1; + break; + case 's': + do_script = 1; + break; + case 'p': + /* XXX: maybe there is a better way to do this */ + if (optind >= argc || (optarg[0] < '0' && optarg[0] > '3')) + { + usage(EXIT_FAILURE); + } + partfile[optarg[0] - '0'] = argv[optind]; + optind++; + break; + case 'e': + do_export = 0; + break; + case 'i': + do_import = 0; + break; + default: + usage(EXIT_FAILURE); + break; + } + } + + if (optind >= argc) + { + usage(EXIT_FAILURE); + } + + return (parted(argv[optind])); +} + +#if 0 static char *prg_name = NULL; static int dump_info = 0; static const char *diskpath = NULL; @@ -28,7 +148,7 @@ dump_partition_info(Partition part) } else { - printf("no\n"); + printf("no\n"); } printf("\tType: %d\n", part.type); printf("\tLBA Start: %d\n", part.lba_start); @@ -54,28 +174,7 @@ dump_disk(void) } } -static void -usage(int retcode) -{ - if (retcode == EXIT_FAILURE) - { - fprintf(stderr, "Try '%s -h' for more information.\n", prg_name); - } - else - { - printf("Usage: %s [-hVd] disk\n", prg_name); - printf("\t-h\tdisplay this help and exit\n"); - printf("\t-V\toutput version information.\n"); - printf("\t-d\tdump disk information\n"); - printf("\t-p0-3\t\n"); - printf("\t-o out\twrite to file 'out'\n"); - printf("\t-e\textract\n"); - printf("\t-i img\t\n"); - printf("\nReport bugs to <%s>\n", MK_BUGREPORT); - } - exit(retcode); -} static void version(void) @@ -156,3 +255,4 @@ main(int argc, char **argv) return (EXIT_SUCCESS); } +#endif diff --git a/sbin/parted/parted.8 b/sbin/parted/parted.8 new file mode 100644 index 0000000..135fb44 --- /dev/null +++ b/sbin/parted/parted.8 @@ -0,0 +1,13 @@ +.Dd $Mdocdate$ +.Dt PARTED 8 +.Os +.Sh NAME +.Nm parted +.Nd a partition utility +.Sh SYNOPSIS +.Nm parted +.Op Fl d +.Op Fl p Ar 0-3 +.Op Fl o Ar file +.Op Ar +.Sh DESCRIPTION diff --git a/sbin/parted/parted.h b/sbin/parted/parted.h new file mode 100644 index 0000000..5b9b138 --- /dev/null +++ b/sbin/parted/parted.h @@ -0,0 +1,26 @@ +#ifndef PARTED_H +# define PARTED_H 1 + +# include + +# define PARTED_LINE_MAX 1024 + +# define PARTED_DEFAULT_SECSZ 512 + +enum parted_unit { + PARTED_KiB = 1024, + PARTED_MiB = 1024 * 1024, + PARTED_GiB = 1024 * 1024 * 1024, + + PARTED_KB = 1000, + PARTED_MB = 1000 * 1000, + PARTED_GB = 1000 * 1000 * 1000, +}; + +/* copyright.c */ +extern const char *copyright; + +/* main.c */ +extern const char *prg_name; + +#endif /* !PARTED_H */ diff --git a/sbin/parted/repl.c b/sbin/parted/repl.c new file mode 100644 index 0000000..74230de --- /dev/null +++ b/sbin/parted/repl.c @@ -0,0 +1,123 @@ +#include +#include +#include +#include + +#define BUFFSZ 128 +#define MAXARGS 6 + +static char * +readline(const char *prompt) +{ + size_t linsz = 0; + size_t buffsz; + char *line = NULL; + char buffer[BUFFSZ]; + + printf(prompt); + while (fgets(buffer, BUFFSZ, stdin) != NULL) + { + buffsz = strlen(buffer); + + line = realloc(line, linsz + buffsz + 1); + if (line == NULL) + { + return (NULL); + } + + memcpy(line + linsz, buffer, buffsz); + linsz += buffsz; + line[linsz] = '\0'; + if (line[linsz - 1] == '\n') + { + line[linsz - 1] = '\0'; + return (line); + } + } + + free(line); + return (NULL); +} + +static int +parse_cmd(struct context *ctx, char *line) +{ + char *argv[MAXARGS] = { NULL }; + int argc; + size_t idx; + char *tmp; + + argc = 0; + tmp = strtok(line, " \t"); + while (tmp != NULL && argc < MAXARGS) + { + argv[argc++] = tmp; + tmp = strtok(NULL, " \t"); + } + + for (idx = 0; cmds[idx].cmd != NULL; idx++) + { + if (strcmp(argv[0], cmds[idx].cmd) == 0) + { + if (cmds[idx].cb != NULL) + { + return (cmds[idx].cb(ctx, argc, argv)); + } + + printf("not implemented\n"); + return (-1); + } + } + + fprintf(stderr, "\e[31mError:\e[0m unknown command '%s'\n", argv[0]); + return (-1); +} + +int +repl_ask(const char *str) +{ + int c = '\n'; + + do + { + if (c == '\n') + { + printf("%s [y/n] ", str); + } + c = fgetc(stdin); + + if (c == 'Y' || c == 'y') + { + putchar('\n'); + return (1); + } + else if (c == 'N' || c == 'n') + { + putchar('\n'); + return (0); + } + } + while (c != EOF); + + return (-1); +} + +int +repl(struct context *ctx) +{ + char *line; + + while ((line = readline("(fdisk) ")) != NULL) + { + if (line[0] == '\0') + { + free(line); + continue; + } + + parse_cmd(ctx, line); + free(line); + } + + return (0); +} diff --git a/sbin/parted/version.c b/sbin/parted/version.c new file mode 100644 index 0000000..286d4be --- /dev/null +++ b/sbin/parted/version.c @@ -0,0 +1,24 @@ +#include + +#ifndef MK_PACKAGE +# define MK_PACKAGE "ext" +#endif /* !MK_PACKAGE */ +#ifndef MK_COMMIT +# define MK_COMMIT "????" +#endif /* !MK_COMMIT */ + +extern const char *prg_name; + +static const char *copyright = \ + "Copyright (c) 2025, d0p1\n" \ + "License BSD-3-Clause: " \ + "\n" \ + "This is free software: you are free to change and redistribute it.\n" \ + "There is NO WARRANTY, to the extent permitterd by law.\n"; + +void +print_version(void) +{ + printf("%s (%s) %s\n", prg_name, MK_PACKAGE, MK_COMMIT); + printf(copyright); +} diff --git a/share/mk/stpd.base.mk b/share/mk/stpd.base.mk new file mode 100644 index 0000000..3f992e3 --- /dev/null +++ b/share/mk/stpd.base.mk @@ -0,0 +1,79 @@ +ifndef _STPD_BASE_MK_ +_STPD_BASE_MK_:=1 + +ifndef TOPDIR +$(error "TOPDIR is undefined") +endif + +MK_BUGREPORT := \"https://git.cute.engineering/d0p1/StupidOS/issues\" +MK_COMMIT := \"$(shell git rev-parse --short HEAD)\" +MK_PACKAGE := \"StupidOS\" + +BASE_CPPFLAGS = -DMK_COMMIT="$(MK_COMMIT)" \ + -DMK_BUGREPORT="$(MK_BUGREPORT)" \ + -DMK_PACKAGE="$(MK_PACKAGE)" + +TARGETS = all clean includes install + +BINDIR ?= /bin +LIBDIR ?= /usr/lib +INCDIR ?= /usr/include +ASMDIR ?= /usr/asm +MANDIR ?= /usr/share/man +DOCDIR ?= /usr/share/doc + +# +------------------------------------------------------------------+ +# | Tools | +# +------------------------------------------------------------------+ +ifndef TOOLSDIR +$(error "TOOLSDIR is undefined") +endif + +FASM = fasm +CC = $(TOOLSDIR)/bin/tcc +AR = ar +FAS2SYM = $(TOOLSDIR)/bin/fas2sym + +define VERSION_SH = +$(MSG_CREATE) +@sh $(TOPDIR)/tools/version.sh $< $@ +endef + +# +------------------------------------------------------------------+ +# | Host | +# +------------------------------------------------------------------+ +HOST_CC = gcc +HOST_AR = ar +HOST_LDFLAGS += -L$(TOOLSDIR)/lib +HOST_CFLAGS += +HOST_CPPFLAGS += $(BASE_CPPFLAGS) -I $(TOPDIR)/include + +# +------------------------------------------------------------------+ +# | Verbose | +# +------------------------------------------------------------------+ +MSG ?= @echo ' ' +MSG_BUILD ?= $(MSG) '👷‍♂️ build ' $@ +MSG_CREATE ?= $(MSG) '🪄 create ' $@ +MSG_COMPILE ?= $(MSG) '⚙️ compile ' $@ +MSG_LINK ?= $(MSG) '🔗 link ' $@ +MSG_EXECUTE ?= $(MSG) '▶️ execute ' $@ +MSG_FORMAT ?= $(MSG) '✏️ format ' $@ +MSG_INSTALL ?= $(MSG) '📦 install ' $(subst $(TOPDIR)/,,$@) +MSG_REMOVE ?= $(MSG) '🗑️ remove ' $@ + +# +------------------------------------------------------------------+ +# | rules | +# +------------------------------------------------------------------+ + +%.o: %.asm + $(MSG_COMPILE) + @$(FASM) $< $@ >/dev/null + +%.lo: %.c + $(MSG_COMPILE) + @$(HOST_CC) -c -o $@ $< $(HOST_CPPFLAGS) $(HOST_CFLAGS) + + +$(TARGETS): + +endif diff --git a/share/mk/stpd.clean.mk b/share/mk/stpd.clean.mk new file mode 100644 index 0000000..cb32e11 --- /dev/null +++ b/share/mk/stpd.clean.mk @@ -0,0 +1,12 @@ +ifndef _STPD_CLEAN_MK_ +_STPD_CLEAN_MK_=1 + +.PHONY: clean +clean: +ifeq ($(strip $(CLEANFILES)),) + @true +else + rm -f $(CLEANFILES) +endif + +endif diff --git a/share/mk/stpd.hostlib.mk b/share/mk/stpd.hostlib.mk new file mode 100644 index 0000000..e1a3cfa --- /dev/null +++ b/share/mk/stpd.hostlib.mk @@ -0,0 +1,27 @@ +include stpd.base.mk + +ifdef HOSTLIB + +ifndef OBJS +OBJS=$(SRCS:.c=.lo) +endif + +_HOSTLIBINST = $(addprefix $(TOOLSDIR)/lib/,$(HOSTLIB)) + +$(HOSTLIB): $(OBJS) + $(MSG_BUILD) + @$(HOST_AR) rcs $@ $< + +all: $(HOSTLIB) + +install: $(_HOSTLIBINST) + +$(_HOSTLIBINST): $(HOSTLIB) + $(MSG_INSTALL) + @install -D $< $@ + +CLEANFILES += $(OBJS) $(HOSTLIB) + +include stpd.clean.mk + +endif diff --git a/share/mk/stpd.hostprog.mk b/share/mk/stpd.hostprog.mk new file mode 100644 index 0000000..7581c80 --- /dev/null +++ b/share/mk/stpd.hostprog.mk @@ -0,0 +1,31 @@ +include stpd.base.mk + +ifdef HOSTPROG + +ifndef SRCS +SRCS=$(HOSTPROG).c +endif + +ifndef OBJS +OBJS=$(SRCS:.c=.lo) +endif + +_HOSTPROGINST = $(addprefix $(TOOLSDIR)/bin/,$(HOSTPROG)) + +$(HOSTPROG): $(OBJS) + $(MSG_LINK) + @$(HOST_CC) -o $@ $^ $(HOST_LDFLAGS) $(LDADD) + +all: $(HOSTPROG) + +install: $(_HOSTPROGINST) + +$(_HOSTPROGINST): $(HOSTPROG) + $(MSG_INSTALL) + @install -D $< $@ + +CLEANFILES += $(OBJS) $(HOSTPROG) + +include stpd.clean.mk + +endif diff --git a/share/mk/stpd.inc.mk b/share/mk/stpd.inc.mk new file mode 100644 index 0000000..2246063 --- /dev/null +++ b/share/mk/stpd.inc.mk @@ -0,0 +1,17 @@ +include stpd.base.mk + +define includes-rule + +$1/$2: $2 + $$(MSG_INSTALL) + @install -D $2 $1/$2 + +endef + +_INCLUDES:=$(addprefix $(DESTDIR)$(INCDIR)/, $(INCS)) \ + $(addprefix $(DESTDIR)$(ASMDIR)/, $(ASMINCS)) + +includes: $(_INCLUDES) + +$(eval $(foreach X,$(INCS),$(call includes-rule,$(DESTDIR)$(INCDIR),$X))) +$(eval $(foreach X,$(ASMINCS),$(call includes-rule,$(DESTDIR)$(ASMDIR),$X))) diff --git a/share/mk/stpd.subdirs.mk b/share/mk/stpd.subdirs.mk new file mode 100644 index 0000000..5c335a9 --- /dev/null +++ b/share/mk/stpd.subdirs.mk @@ -0,0 +1,33 @@ +include stpd.base.mk + +ifdef SUBDIRS + +_SUBDIRS=$(filter-out .WAIT,$(SUBDIRS)) +_CURDIR=$(subst $(TOPDIR),,$(CURDIR)) +ifneq ($(_CURDIR),) +_CURDIR:=$(_CURDIR)/ +endif + +define subdir-rule + +.PHONY: $1-$2 +$1-$2: + @echo "📁 $(_CURDIR)$2" + @DESTDIR=$(DESTDIR) $$(MAKE) -C $2 $1 + +endef + +define subdir-target + +.PHONY: subdir-$1 +subdir-$1: $(foreach X,$(SUBDIRS),$(if $(filter-out $(X),.WAIT),$1-$X,.WAIT)) + +$1: subdir-$1 + +endef + +$(eval $(foreach T,$(TARGETS),$(foreach X,$(_SUBDIRS),$(call subdir-rule,$T,$X)))) +$(eval $(foreach T,$(TARGETS),$(call subdir-target,$T))) + +endif + diff --git a/tests/Makefile b/tests/Makefile index 4118235..5284c5d 100644 --- a/tests/Makefile +++ b/tests/Makefile @@ -1,4 +1,4 @@ -TOPGOALS = all clean install +include stpd.base.mk -.PHONY: $(TOPGOALS) -$(TOPGOALS): +all: + @echo TODO diff --git a/tools/Makefile b/tools/Makefile index 80d8a39..2ceb456 100644 --- a/tools/Makefile +++ b/tools/Makefile @@ -1,40 +1,4 @@ -TARGET = ld$(EXEXT) parted$(EXEXT) readcoff$(EXEXT) \ - elf2coff$(EXEXT) ar$(EXEXT) ranlib$(EXEXT) \ - fasdump$(EXEXT) fas2sym$(EXEXT) +SUBDIRS = libstupidc .WAIT ar elf2coff fas2sym fasdump +SUBDIRS += fdisk ld mtree ranlib readcoff -FAS2SYM_SRCS = main.c fas.c elf.c buffer.c -FAS2SYM_OBJS = $(addprefix ../bin/fas2sym/, $(FAS2SYM_SRCS:.c=.o)) - -.PHONY: all -all: $(TARGET) - -ld$(EXEXT): ../bin/ld/main.c - $(TOOL_CC) -o $@ $^ $(CFLAGS) $(LDFLAGS) - -readcoff$(EXEXT): ../bin/readcoff/main.c - $(TOOL_CC) -o $@ $^ $(CFLAGS) $(LDFLAGS) - -elf2coff$(EXEXT): ../bin/elf2coff/main.c - $(TOOL_CC) -o $@ $^ $(CFLAGS) $(LDFLAGS) - -parted$(EXEXT): ../sbin/parted/main.c - $(TOOL_CC) -o $@ $^ $(CFLAGS) $(LDFLAGS) - -ranlib$(EXEXT): ../bin/ranlib/main.c ../bin/ar/archive.c - $(TOOL_CC) -o $@ $^ $(CFLAGS) $(LDFLAGS) - -ar$(EXEXT): ../bin/ar/main.c - $(TOOL_CC) -o $@ $^ $(CFLAGS) $(LDFLAGS) - -fasdump$(EXEXT): ../bin/fasdump/main.c - $(TOOL_CC) -o $@ $^ $(CFLAGS) $(LDFLAGS) - -fas2sym$(EXEXT): $(FAS2SYM_OBJS) - $(TOOL_CC) -o $@ $^ $(CFLAGS) $(LDFLAGS) - -.PHONY: install -install: $(TARGET) - -.PHONY: clean -clean: - $(RM) $(TARGET) +include stpd.subdirs.mk diff --git a/tools/ar/Makefile b/tools/ar/Makefile new file mode 100644 index 0000000..4520f53 --- /dev/null +++ b/tools/ar/Makefile @@ -0,0 +1,5 @@ +VPATH = $(TOPDIR)/bin/ar +HOSTPROG = ar +SRCS = main.c + +include stpd.hostprog.mk diff --git a/tools/elf2coff/Makefile b/tools/elf2coff/Makefile new file mode 100644 index 0000000..8100c52 --- /dev/null +++ b/tools/elf2coff/Makefile @@ -0,0 +1,5 @@ +VPATH = $(TOPDIR)/bin/elf2coff +HOSTPROG = elf2coff +SRCS = main.c + +include stpd.hostprog.mk diff --git a/tools/fas2sym/Makefile b/tools/fas2sym/Makefile new file mode 100644 index 0000000..f241025 --- /dev/null +++ b/tools/fas2sym/Makefile @@ -0,0 +1,5 @@ +VPATH = $(TOPDIR)/bin/fas2sym +HOSTPROG = fas2sym +SRCS = main.c fas.c elf.c buffer.c + +include stpd.hostprog.mk diff --git a/tools/fasdump/Makefile b/tools/fasdump/Makefile new file mode 100644 index 0000000..d76dab2 --- /dev/null +++ b/tools/fasdump/Makefile @@ -0,0 +1,5 @@ +VPATH = $(TOPDIR)/bin/fasdump +HOSTPROG = fasdump +SRCS = main.c + +include stpd.hostprog.mk diff --git a/tools/fdisk/Makefile b/tools/fdisk/Makefile new file mode 100644 index 0000000..8f5bdb4 --- /dev/null +++ b/tools/fdisk/Makefile @@ -0,0 +1,6 @@ +VPATH = $(TOPDIR)/sbin/parted +HOSTPROG = fdisk +HOST_CPPFLAGS += -I$(TOPDIR)/sbin/parted +SRCS = main.c repl.c cmd.c version.c fildev.c + +include stpd.hostprog.mk diff --git a/tools/ld/Makefile b/tools/ld/Makefile new file mode 100644 index 0000000..150143c --- /dev/null +++ b/tools/ld/Makefile @@ -0,0 +1,5 @@ +VPATH = $(TOPDIR)/bin/ld +HOSTPROG = ld +SRCS = main.c + +include stpd.hostprog.mk diff --git a/tools/libstupidc/Makefile b/tools/libstupidc/Makefile new file mode 100644 index 0000000..6e8cab9 --- /dev/null +++ b/tools/libstupidc/Makefile @@ -0,0 +1,6 @@ +VPATH = $(TOPDIR)/lib/stupidc + +HOSTLIB = libstupidc.a +SRCS = progname.c version.c + +include stpd.hostlib.mk diff --git a/tools/mtree/Makefile b/tools/mtree/Makefile new file mode 100644 index 0000000..89626e6 --- /dev/null +++ b/tools/mtree/Makefile @@ -0,0 +1,5 @@ +VPATH = $(TOPDIR)/sbin/mtree +HOSTPROG = mtree +SRCS = main.c + +include stpd.hostprog.mk diff --git a/tools/ranlib/Makefile b/tools/ranlib/Makefile new file mode 100644 index 0000000..446be93 --- /dev/null +++ b/tools/ranlib/Makefile @@ -0,0 +1,5 @@ +VPATH = $(TOPDIR)/bin/ranlib $(TOPDIR)/bin/ar +HOSTPROG = ranlib +SRCS = main.c archive.c + +include stpd.hostprog.mk diff --git a/tools/readcoff/Makefile b/tools/readcoff/Makefile new file mode 100644 index 0000000..428bbc9 --- /dev/null +++ b/tools/readcoff/Makefile @@ -0,0 +1,5 @@ +VPATH = $(TOPDIR)/bin/readcoff +HOSTPROG = readcoff +SRCS = main.c + +include stpd.hostprog.mk