mirror of
https://github.com/taigrr/gopher-os
synced 2025-01-18 04:43:13 -08:00
The go compiler exposes a fully qualified symbol for kernel.Kmain that also includes the full package name (github.com/.../kernel.Kmain). Since nasm cannot work with external symbols that include slashes we use objcopy to create an alias symbol "kernel.Kmain" that points to the symbol generated by the go compiler. To use the "--add-symbol" argument we need to use objcopy 2.6+. The makefile was modified to include an additional pre-compile check for the installed objcopy version.
110 lines
3.6 KiB
Makefile
110 lines
3.6 KiB
Makefile
OS = $(shell uname -s)
|
|
ARCH := x86
|
|
BUILD_DIR := build
|
|
BUILD_ABS_DIR := $(CURDIR)/$(BUILD_DIR)
|
|
|
|
kernel_target :=$(BUILD_DIR)/kernel-$(ARCH).bin
|
|
iso_target := $(BUILD_DIR)/kernel-$(ARCH).iso
|
|
|
|
ifeq ($(OS), Linux)
|
|
export SHELL := /bin/bash -o pipefail
|
|
|
|
LD := ld
|
|
AS := nasm
|
|
|
|
GOOS := linux
|
|
GOARCH := 386
|
|
|
|
LD_FLAGS := -n -melf_i386 -T arch/$(ARCH)/script/linker.ld -static --no-ld-generated-unwind-info
|
|
AS_FLAGS := -g -f elf32 -F dwarf -I arch/$(ARCH)/asm/
|
|
|
|
MIN_OBJCOPY_VERSION := 2.26.0
|
|
HAVE_VALID_OBJCOPY := $(shell objcopy -V | head -1 | awk -F ' ' '{print "$(MIN_OBJCOPY_VERSION)\n" $$NF}' | sort -ct. -k1,1n -k2,2n && echo "y")
|
|
|
|
asm_src_files := $(wildcard arch/$(ARCH)/asm/*.s)
|
|
asm_obj_files := $(patsubst arch/$(ARCH)/asm/%.s, $(BUILD_DIR)/arch/$(ARCH)/asm/%.o, $(asm_src_files))
|
|
|
|
.PHONY: kernel iso clean binutils_version_check
|
|
|
|
kernel: binutils_version_check $(kernel_target)
|
|
|
|
$(kernel_target): $(asm_obj_files) go.o
|
|
@echo "[$(LD)] linking kernel-$(ARCH).bin"
|
|
@$(LD) $(LD_FLAGS) -o $(kernel_target) $(asm_obj_files) $(BUILD_DIR)/go.o
|
|
|
|
go.o:
|
|
@mkdir -p $(BUILD_DIR)
|
|
|
|
@echo "[go] compiling go sources into a standalone .o file"
|
|
@GOARCH=386 GOOS=linux go build -n 2>&1 | sed \
|
|
-e "1s|^|set -e\n|" \
|
|
-e "1s|^|export GOOS=linux\n|" \
|
|
-e "1s|^|export GOARCH=386\n|" \
|
|
-e "1s|^|WORK='$(BUILD_ABS_DIR)'\n|" \
|
|
-e "1s|^|alias pack='go tool pack'\n|" \
|
|
-e "/^mv/d" \
|
|
-e "s|-extld|-tmpdir='$(BUILD_ABS_DIR)' -linkmode=external -extldflags='-nostdlib' -extld|g" \
|
|
| sh 2>&1 | sed -e "s/^/ | /g"
|
|
|
|
@# build/go.o is a elf32 object file but all go symbols are unexported. Our
|
|
@# asm entrypoint code needs to know the address to 'main.main' so we use
|
|
@# objcopy to make that symbol exportable. Since nasm does not support externs
|
|
@# with slashes we create a global symbol alias for kernel.Kmain
|
|
@echo "[objcopy] creating global symbol alias 'kernel.Kmain' for 'github.com/achilleasa/gopher-os/kernel.Kmain' in go.o"
|
|
@objcopy \
|
|
--add-symbol kernel.Kmain=.text:0x`nm $(BUILD_DIR)/go.o | grep "kernel.Kmain" | cut -d' ' -f1` \
|
|
$(BUILD_DIR)/go.o $(BUILD_DIR)/go.o
|
|
|
|
binutils_version_check:
|
|
@echo "[binutils] checking that installed objcopy version is >= $(MIN_OBJCOPY_VERSION)"
|
|
@if [ "$(HAVE_VALID_OBJCOPY)" != "y" ]; then echo "[binutils] error: a more up to date binutils installation is required" ; exit 1 ; fi
|
|
|
|
$(BUILD_DIR)/arch/$(ARCH)/asm/%.o: arch/$(ARCH)/asm/%.s
|
|
@mkdir -p $(shell dirname $@)
|
|
@echo "[$(AS)] $<"
|
|
@$(AS) $(AS_FLAGS) $< -o $@
|
|
|
|
iso: $(iso_target)
|
|
|
|
$(iso_target): $(kernel_target)
|
|
@echo "[grub] building ISO kernel-$(ARCH).iso"
|
|
|
|
@mkdir -p $(BUILD_DIR)/isofiles/boot/grub
|
|
@cp $(kernel_target) $(BUILD_DIR)/isofiles/boot/kernel.bin
|
|
@cp arch/$(ARCH)/script/grub.cfg $(BUILD_DIR)/isofiles/boot/grub
|
|
@grub-mkrescue -o $(iso_target) $(BUILD_DIR)/isofiles 2>&1 | sed -e "s/^/ | /g"
|
|
@rm -r $(BUILD_DIR)/isofiles
|
|
|
|
else
|
|
VAGRANT_SRC_FOLDER = /home/vagrant/workspace/src/github.com/achilleasa/gopher-os
|
|
|
|
.PHONY: kernel iso vagrant-up vagrant-down vagrant-ssh run gdb clean
|
|
|
|
kernel:
|
|
vagrant ssh -c 'cd $(VAGRANT_SRC_FOLDER); make kernel'
|
|
|
|
iso:
|
|
vagrant ssh -c 'cd $(VAGRANT_SRC_FOLDER); make iso'
|
|
|
|
run: iso
|
|
qemu-system-i386 -cdrom $(iso_target)
|
|
|
|
gdb: iso
|
|
qemu-system-i386 -s -S -cdrom $(iso_target) &
|
|
sleep 1
|
|
gdb \
|
|
-ex "add-auto-load-safe-path $(pwd)" \
|
|
-ex "file $(kernel_target)" \
|
|
-ex "set disassembly-flavor intel" \
|
|
-ex 'set arch i386:intel' \
|
|
-ex 'target remote localhost:1234' \
|
|
-ex 'layout asm' \
|
|
-ex 'b _rt0_entry' \
|
|
-ex 'continue' \
|
|
-ex 'disass'
|
|
@killall qemu-system-i386 || true
|
|
endif
|
|
|
|
clean:
|
|
@test -d $(BUILD_DIR) && rm -rf $(BUILD_DIR) || true
|