|
| 1 | +# Nuke built-in rules and variables. |
| 2 | +MAKEFLAGS += -rR |
| 3 | +.SUFFIXES: |
| 4 | + |
| 5 | +# This is the name that our final executable will have. |
| 6 | +# Change as needed. |
| 7 | +override OUTPUT := kernel |
| 8 | + |
| 9 | +# Install prefix; /usr/local is a good, standard default pick. |
| 10 | +PREFIX := /usr/local |
| 11 | + |
| 12 | +# User controllable C compiler command. |
| 13 | +CC := cc |
| 14 | + |
| 15 | +# User controllable C flags. |
| 16 | +CFLAGS := -g -O2 -pipe |
| 17 | + |
| 18 | +# User controllable C preprocessor flags. We set none by default. |
| 19 | +CPPFLAGS := |
| 20 | + |
| 21 | +# User controllable nasm flags. |
| 22 | +NASMFLAGS := -F dwarf -g |
| 23 | + |
| 24 | +# User controllable linker flags. We set none by default. |
| 25 | +LDFLAGS := -g |
| 26 | + |
| 27 | +# Ensure the dependencies have been obtained. |
| 28 | +ifneq ($(shell ( test '$(MAKECMDGOALS)' = clean || test '$(MAKECMDGOALS)' = distclean ); echo $$?),0) |
| 29 | + ifeq ($(shell ( ! test -d freestnd-c-hdrs || ! test -d src/cc-runtime || ! test -f src/limine.h ); echo $$?),0) |
| 30 | + $(error Please run the ./get-deps script first) |
| 31 | + endif |
| 32 | +endif |
| 33 | + |
| 34 | +# Check if CC is Clang. |
| 35 | +override CC_IS_CLANG := $(shell ! $(CC) --version 2>/dev/null | grep 'clang' >/dev/null 2>&1; echo $$?) |
| 36 | + |
| 37 | +# If the C compiler is Clang, set the target as needed. |
| 38 | +ifeq ($(CC_IS_CLANG),1) |
| 39 | + override CC += \ |
| 40 | + -target x86_64-unknown-none |
| 41 | +endif |
| 42 | + |
| 43 | +# Internal C flags that should not be changed by the user. |
| 44 | +override CFLAGS += \ |
| 45 | + -Wall \ |
| 46 | + -Wextra \ |
| 47 | + -std=gnu11 \ |
| 48 | + -nostdinc \ |
| 49 | + -ffreestanding \ |
| 50 | + -fno-stack-protector \ |
| 51 | + -fno-stack-check \ |
| 52 | + -fno-PIC \ |
| 53 | + -ffunction-sections \ |
| 54 | + -fdata-sections \ |
| 55 | + -m64 \ |
| 56 | + -march=x86-64 \ |
| 57 | + -mno-80387 \ |
| 58 | + -mno-mmx \ |
| 59 | + -mno-sse \ |
| 60 | + -mno-sse2 \ |
| 61 | + -mno-red-zone \ |
| 62 | + -mcmodel=kernel |
| 63 | + |
| 64 | +# Internal C preprocessor flags that should not be changed by the user. |
| 65 | +override CPPFLAGS := \ |
| 66 | + -I src \ |
| 67 | + -isystem freestnd-c-hdrs \ |
| 68 | + $(CPPFLAGS) \ |
| 69 | + -DLIMINE_API_REVISION=3 \ |
| 70 | + -MMD \ |
| 71 | + -MP |
| 72 | + |
| 73 | +# Internal nasm flags that should not be changed by the user. |
| 74 | +override NASMFLAGS += \ |
| 75 | + -Wall \ |
| 76 | + -f elf64 |
| 77 | + |
| 78 | +# Internal linker flags that should not be changed by the user. |
| 79 | +override LDFLAGS += \ |
| 80 | + -Wl,-m,elf_x86_64 \ |
| 81 | + -Wl,--build-id=none \ |
| 82 | + -nostdlib \ |
| 83 | + -static \ |
| 84 | + -z max-page-size=0x1000 \ |
| 85 | + -Wl,--gc-sections \ |
| 86 | + -T linker.ld |
| 87 | + |
| 88 | +# Use "find" to glob all *.c, *.S, and *.asm files in the tree and obtain the |
| 89 | +# object and header dependency file names. |
| 90 | +override SRCFILES := $(shell cd src && find -L * -type f | LC_ALL=C sort) |
| 91 | +override CFILES := $(filter %.c,$(SRCFILES)) |
| 92 | +override ASFILES := $(filter %.S,$(SRCFILES)) |
| 93 | +override NASMFILES := $(filter %.asm,$(SRCFILES)) |
| 94 | +override OBJ := $(addprefix obj/,$(CFILES:.c=.c.o) $(ASFILES:.S=.S.o) $(NASMFILES:.asm=.asm.o)) |
| 95 | +override HEADER_DEPS := $(addprefix obj/,$(CFILES:.c=.c.d) $(ASFILES:.S=.S.d)) |
| 96 | + |
| 97 | +# Default target. This must come first, before header dependencies. |
| 98 | +.PHONY: all |
| 99 | +all: bin/$(OUTPUT) |
| 100 | + |
| 101 | +# Include header dependencies. |
| 102 | +-include $(HEADER_DEPS) |
| 103 | + |
| 104 | +# Link rules for the final executable. |
| 105 | +bin/$(OUTPUT): GNUmakefile linker.ld $(OBJ) |
| 106 | + mkdir -p "$$(dirname $@)" |
| 107 | + $(CC) $(CFLAGS) $(LDFLAGS) $(OBJ) -o $@ |
| 108 | + |
| 109 | +# Compilation rules for *.c files. |
| 110 | +obj/%.c.o: src/%.c GNUmakefile |
| 111 | + mkdir -p "$$(dirname $@)" |
| 112 | + $(CC) $(CFLAGS) $(CPPFLAGS) -c $< -o $@ |
| 113 | + |
| 114 | +# Compilation rules for *.S files. |
| 115 | +obj/%.S.o: src/%.S GNUmakefile |
| 116 | + mkdir -p "$$(dirname $@)" |
| 117 | + $(CC) $(CFLAGS) $(CPPFLAGS) -c $< -o $@ |
| 118 | + |
| 119 | +# Compilation rules for *.asm (nasm) files. |
| 120 | +obj/%.asm.o: src/%.asm GNUmakefile |
| 121 | + mkdir -p "$$(dirname $@)" |
| 122 | + nasm $(NASMFLAGS) $< -o $@ |
| 123 | + |
| 124 | +# Remove object files and the final executable. |
| 125 | +.PHONY: clean |
| 126 | +clean: |
| 127 | + rm -rf bin obj |
| 128 | + |
| 129 | +# Remove everything built and generated including downloaded dependencies. |
| 130 | +.PHONY: distclean |
| 131 | +distclean: clean |
| 132 | + rm -rf freestnd-c-hdrs src/cc-runtime src/limine.h |
| 133 | + |
| 134 | +# Install the final built executable to its final on-root location. |
| 135 | +.PHONY: install |
| 136 | +install: all |
| 137 | + install -d "$(DESTDIR)$(PREFIX)/share/$(OUTPUT)" |
| 138 | + install -m 644 bin/$(OUTPUT) "$(DESTDIR)$(PREFIX)/share/$(OUTPUT)/" |
| 139 | + |
| 140 | +# Try to undo whatever the "install" target did. |
| 141 | +.PHONY: uninstall |
| 142 | +uninstall: |
| 143 | + rm -f "$(DESTDIR)$(PREFIX)/share/$(OUTPUT)/$(OUTPUT)" |
| 144 | + -rmdir "$(DESTDIR)$(PREFIX)/share/$(OUTPUT)" |
0 commit comments