Merge pull request #16 from johndoe6345789/copilot/remove-makefile-support

Migrate to pure CMake build system by removing all Makefiles
This commit is contained in:
2025-12-28 21:09:30 +00:00
committed by GitHub
14 changed files with 169 additions and 507 deletions

View File

@@ -25,6 +25,7 @@ jobs:
sudo apt-get update
sudo apt-get install -y \
build-essential \
cmake \
nasm \
qemu-system-x86 \
ovmf \
@@ -32,19 +33,21 @@ jobs:
xorriso \
imagemagick
- name: Build bootloader
- name: Configure CMake
run: |
cd bootloader
make
mkdir -p build
cd build
cmake ..
- name: Build kernel
- name: Build bootloader and kernel
run: |
cd kernel
make
cd build
cmake --build .
- name: Create bootable image
run: |
make image
cd build
cmake --build . --target image
- name: Start QEMU and capture screenshot
run: |
@@ -56,19 +59,22 @@ jobs:
XVFB_PID=$!
sleep 2
# Verify disk image exists (created by 'make image')
if [ ! -f build/metalos.img ]; then
echo "Error: build/metalos.img not found!"
# Verify disk image exists (created by cmake build)
if [ ! -f build/build/metalos.img ]; then
echo "Error: build/build/metalos.img not found!"
exit 1
fi
# Create directory for logs
mkdir -p build/logs
# Start QEMU in the background with a timeout
timeout 30s qemu-system-x86_64 \
-bios /usr/share/OVMF/OVMF_CODE.fd \
-drive format=raw,file=build/metalos.img \
-drive format=raw,file=build/build/metalos.img \
-m 512M \
-display gtk \
-serial file:build/serial.log \
-serial file:build/logs/serial.log \
-no-reboot &
QEMU_PID=$!
@@ -77,7 +83,7 @@ jobs:
# Take screenshot using ImageMagick (optional - don't fail if this doesn't work)
# Using subshell to prevent 'set -e' from affecting this optional step
{ import -window root build/qemu-screenshot.png; } || echo "Screenshot capture failed (non-fatal)"
{ import -window root build/logs/qemu-screenshot.png; } || echo "Screenshot capture failed (non-fatal)"
# Gracefully stop QEMU (don't fail if already stopped)
kill $QEMU_PID 2>/dev/null || true
@@ -91,9 +97,9 @@ jobs:
- name: Show serial output
if: always()
run: |
if [ -f build/serial.log ]; then
if [ -f build/logs/serial.log ]; then
echo "=== QEMU Serial Output ==="
cat build/serial.log
cat build/logs/serial.log
else
echo "No serial output captured"
fi
@@ -103,7 +109,7 @@ jobs:
uses: actions/upload-artifact@v4
with:
name: qemu-screenshot
path: build/qemu-screenshot.png
path: build/logs/qemu-screenshot.png
if-no-files-found: warn
- name: Upload serial log
@@ -111,7 +117,7 @@ jobs:
uses: actions/upload-artifact@v4
with:
name: serial-log
path: build/serial.log
path: build/logs/serial.log
if-no-files-found: warn
- name: Upload built disk image
@@ -119,5 +125,5 @@ jobs:
uses: actions/upload-artifact@v4
with:
name: metalos-disk-image
path: build/metalos.img
path: build/build/metalos.img
if-no-files-found: warn

View File

@@ -24,25 +24,28 @@ jobs:
sudo apt-get update
sudo apt-get install -y \
build-essential \
cmake \
nasm \
qemu-system-x86 \
ovmf \
mtools \
xorriso
- name: Build bootloader
- name: Configure CMake
run: |
cd bootloader
make
mkdir -p build
cd build
cmake ..
- name: Build kernel
- name: Build bootloader and kernel
run: |
cd kernel
make
cd build
cmake --build .
- name: Create bootable image
run: |
make image
cd build
cmake --build . --target image
- name: Prepare release directory
run: |
@@ -51,29 +54,29 @@ jobs:
mkdir -p release
# Copy the bootable disk image (required)
if [ -f build/metalos.img ]; then
cp build/metalos.img release/
if [ -f build/build/metalos.img ]; then
cp build/build/metalos.img release/
echo "✓ Copied metalos.img"
else
echo "Error: build/metalos.img not found!"
echo "Error: build/build/metalos.img not found!"
exit 1
fi
# Copy bootloader if it exists (required)
if [ -f bootloader/bootx64.efi ]; then
cp bootloader/bootx64.efi release/
if [ -f build/bootloader/bootx64.efi ]; then
cp build/bootloader/bootx64.efi release/
echo "✓ Copied bootx64.efi"
else
echo "Error: bootloader/bootx64.efi not found!"
echo "Error: build/bootloader/bootx64.efi not found!"
exit 1
fi
# Copy kernel if it exists (required)
if [ -f kernel/metalos.bin ]; then
cp kernel/metalos.bin release/
if [ -f build/kernel/metalos.bin ]; then
cp build/kernel/metalos.bin release/
echo "✓ Copied metalos.bin"
else
echo "Error: kernel/metalos.bin not found!"
echo "Error: build/kernel/metalos.bin not found!"
exit 1
fi

View File

@@ -22,17 +22,23 @@ jobs:
set -e # Exit on any error
sudo apt-get update
sudo apt-get install -y build-essential
sudo apt-get install -y build-essential cmake
- name: Configure CMake
run: |
mkdir -p build
cd build
cmake ..
- name: Build unit tests
run: |
cd tests
make all
cd build
cmake --build .
- name: Run unit tests
run: |
cd tests
make test
cd build
ctest --output-on-failure
- name: Test summary
if: always()

2
.gitignore vendored
View File

@@ -18,6 +18,8 @@
# Build directories
build/
build-*/
cmake-build/
cmake-build-*/
bootloader/build/
kernel/build/
_codeql_build_dir/

View File

@@ -53,9 +53,9 @@ endif()
# Custom target to create bootable image
find_program(MFORMAT mformat)
find_program(MCOPY mcopy)
find_program(MDD mdd)
find_program(MMD mmd)
if(MFORMAT AND MCOPY)
if(MFORMAT AND MCOPY AND MMD)
add_custom_target(image
COMMAND ${CMAKE_COMMAND} -E make_directory ${CMAKE_BINARY_DIR}/build/iso/EFI/BOOT
COMMAND ${CMAKE_COMMAND} -E copy
@@ -65,10 +65,10 @@ if(MFORMAT AND MCOPY)
${CMAKE_BINARY_DIR}/kernel/metalos.bin
${CMAKE_BINARY_DIR}/build/iso/
COMMAND ${CMAKE_COMMAND} -E echo "Creating disk image..."
COMMAND dd if=/dev/zero of=${CMAKE_BINARY_DIR}/build/metalos.img bs=1M count=64 2>/dev/null
COMMAND dd if=/dev/zero of=${CMAKE_BINARY_DIR}/build/metalos.img bs=1M count=64
COMMAND ${MFORMAT} -i ${CMAKE_BINARY_DIR}/build/metalos.img -F -v METALOS ::
COMMAND ${MDD} -i ${CMAKE_BINARY_DIR}/build/metalos.img ::/EFI
COMMAND ${MDD} -i ${CMAKE_BINARY_DIR}/build/metalos.img ::/EFI/BOOT
COMMAND ${MMD} -i ${CMAKE_BINARY_DIR}/build/metalos.img ::/EFI
COMMAND ${MMD} -i ${CMAKE_BINARY_DIR}/build/metalos.img ::/EFI/BOOT
COMMAND ${MCOPY} -i ${CMAKE_BINARY_DIR}/build/metalos.img
${CMAKE_BINARY_DIR}/build/iso/EFI/BOOT/bootx64.efi ::/EFI/BOOT/
COMMAND ${MCOPY} -i ${CMAKE_BINARY_DIR}/build/metalos.img
@@ -143,6 +143,20 @@ if(QEMU)
COMMENT "Running MetalOS in QEMU with GDB server (port 1234)"
VERBATIM
)
add_custom_target(qemu-uefi-test
COMMAND ${CMAKE_COMMAND} -E echo "Testing QEMU UEFI boot (no OS image)..."
COMMAND ${CMAKE_COMMAND} -E echo "Using OVMF firmware: ${OVMF_FIRMWARE}"
COMMAND ${CMAKE_COMMAND} -E echo "This will boot to UEFI shell in nographic mode."
COMMAND ${CMAKE_COMMAND} -E echo "You should see UEFI boot messages. Press Ctrl-A then X to exit QEMU."
COMMAND ${QEMU}
-drive if=pflash,format=raw,readonly=on,file=${OVMF_FIRMWARE}
-m 512M
-nographic
-net none
COMMENT "Testing QEMU UEFI setup without OS image"
VERBATIM
)
else()
message(WARNING "OVMF firmware not found - QEMU targets will not be available")
endif()

View File

@@ -152,9 +152,19 @@ Closes #42
Every PR should be tested in QEMU:
```bash
make clean
make all
make qemu
mkdir build && cd build
cmake ..
cmake --build .
cmake --build . --target qemu
```
Or if you already have a build directory:
```bash
cd build
cmake --build . --target clean
cmake --build .
cmake --build . --target qemu
```
Verify:

144
Makefile
View File

@@ -1,144 +0,0 @@
# MetalOS Main Makefile
# Builds bootloader, kernel, and creates bootable image
.PHONY: all bootloader kernel image qemu qemu-debug qemu-gdb qemu-uefi-test test clean distclean
all: bootloader kernel
# Run unit tests
test:
@echo "Running unit tests..."
@cd tests && $(MAKE) test
bootloader:
@echo "Building bootloader..."
@cd bootloader && $(MAKE) || echo "Warning: Bootloader build failed (expected during Phase 1 development)"
kernel:
@echo "Building kernel..."
@cd kernel && $(MAKE) || echo "Warning: Kernel build failed (expected during Phase 1 development)"
# Create bootable disk image for UEFI/QEMU
image: bootloader kernel
@chmod +x scripts/create_image.sh
@./scripts/create_image.sh
# Run in QEMU with UEFI firmware (OVMF)
# Automatically detects OVMF path and display mode
# Set QEMU_DISPLAY=gtk or QEMU_DISPLAY=sdl to use graphical mode
QEMU_DISPLAY ?= none
qemu: image
@echo "Starting QEMU with UEFI firmware..."
@bash -c ' \
if [ -f /usr/share/OVMF/OVMF_CODE.fd ]; then \
OVMF="/usr/share/OVMF/OVMF_CODE.fd"; \
elif [ -f /usr/share/ovmf/OVMF.fd ]; then \
OVMF="/usr/share/ovmf/OVMF.fd"; \
elif [ -f /usr/share/edk2-ovmf/x64/OVMF_CODE.fd ]; then \
OVMF="/usr/share/edk2-ovmf/x64/OVMF_CODE.fd"; \
elif [ -f /usr/share/qemu/ovmf-x86_64.bin ]; then \
OVMF="/usr/share/qemu/ovmf-x86_64.bin"; \
else \
echo "Error: OVMF UEFI firmware not found!"; \
echo "Install with:"; \
echo " Ubuntu/Debian: sudo apt-get install ovmf"; \
echo " Arch Linux: sudo pacman -S edk2-ovmf"; \
echo " Fedora: sudo dnf install edk2-ovmf"; \
exit 1; \
fi; \
echo "Using OVMF firmware: $$OVMF"; \
echo "Display mode: $(QEMU_DISPLAY) (set QEMU_DISPLAY=gtk for graphical)"; \
qemu-system-x86_64 \
-drive if=pflash,format=raw,readonly=on,file=$$OVMF \
-drive format=raw,file=build/metalos.img \
-m 512M \
-serial stdio \
-display $(QEMU_DISPLAY) \
-net none \
'
qemu-debug: image
@echo "Starting QEMU with debug output..."
@bash -c ' \
if [ -f /usr/share/OVMF/OVMF_CODE.fd ]; then \
OVMF="/usr/share/OVMF/OVMF_CODE.fd"; \
elif [ -f /usr/share/ovmf/OVMF.fd ]; then \
OVMF="/usr/share/ovmf/OVMF.fd"; \
elif [ -f /usr/share/edk2-ovmf/x64/OVMF_CODE.fd ]; then \
OVMF="/usr/share/edk2-ovmf/x64/OVMF_CODE.fd"; \
else \
echo "Error: OVMF UEFI firmware not found!"; \
exit 1; \
fi; \
qemu-system-x86_64 \
-drive if=pflash,format=raw,readonly=on,file=$$OVMF \
-drive format=raw,file=build/metalos.img \
-m 512M \
-serial stdio \
-display $(QEMU_DISPLAY) \
-net none \
-d int,cpu_reset \
'
qemu-gdb: image
@echo "Starting QEMU with GDB server on port 1234..."
@bash -c ' \
if [ -f /usr/share/OVMF/OVMF_CODE.fd ]; then \
OVMF="/usr/share/OVMF/OVMF_CODE.fd"; \
elif [ -f /usr/share/ovmf/OVMF.fd ]; then \
OVMF="/usr/share/ovmf/OVMF.fd"; \
elif [ -f /usr/share/edk2-ovmf/x64/OVMF_CODE.fd ]; then \
OVMF="/usr/share/edk2-ovmf/x64/OVMF_CODE.fd"; \
else \
echo "Error: OVMF UEFI firmware not found!"; \
exit 1; \
fi; \
echo "QEMU will wait for GDB connection on localhost:1234"; \
echo "In another terminal, run: gdb kernel/metalos.bin"; \
echo "Then in GDB: target remote localhost:1234"; \
qemu-system-x86_64 \
-drive if=pflash,format=raw,readonly=on,file=$$OVMF \
-drive format=raw,file=build/metalos.img \
-m 512M \
-serial stdio \
-display $(QEMU_DISPLAY) \
-net none \
-s -S \
'
# Quick UEFI test - boots to UEFI shell without OS (for verifying QEMU+OVMF setup)
qemu-uefi-test:
@echo "Testing QEMU UEFI boot (no OS image)..."
@bash -c ' \
if [ -f /usr/share/OVMF/OVMF_CODE.fd ]; then \
OVMF="/usr/share/OVMF/OVMF_CODE.fd"; \
elif [ -f /usr/share/ovmf/OVMF.fd ]; then \
OVMF="/usr/share/ovmf/OVMF.fd"; \
elif [ -f /usr/share/edk2-ovmf/x64/OVMF_CODE.fd ]; then \
OVMF="/usr/share/edk2-ovmf/x64/OVMF_CODE.fd"; \
else \
echo "Error: OVMF UEFI firmware not found!"; \
exit 1; \
fi; \
echo "Using OVMF firmware: $$OVMF"; \
echo "This will boot to UEFI shell in nographic mode."; \
echo "You should see UEFI boot messages. Press Ctrl-A then X to exit QEMU."; \
qemu-system-x86_64 \
-drive if=pflash,format=raw,readonly=on,file=$$OVMF \
-m 512M \
-nographic \
-net none \
'
clean:
@echo "Cleaning build artifacts..."
@cd bootloader && $(MAKE) clean
@cd kernel && $(MAKE) clean
@cd tests && $(MAKE) clean
@rm -rf build
distclean: clean
@echo "Deep clean..."
@find . -name "*.o" -delete
@find . -name "*.d" -delete

View File

@@ -67,18 +67,18 @@ See [docs/ROADMAP.md](docs/ROADMAP.md) for detailed phase breakdown.
## Building
MetalOS supports **multiple build systems** - choose what works best for you!
MetalOS uses **CMake** as its build system for a modern, cross-platform build experience.
### Quick Start (Make - Traditional)
### Quick Start (CMake)
```bash
make all # Build bootloader, kernel, and userspace
make test # Run unit tests
make qemu # Test in QEMU with UEFI firmware
make clean # Clean build artifacts
mkdir build && cd build
cmake ..
cmake --build .
cmake --build . --target qemu
```
### CMake + Ninja (Fast Modern Build)
### Using Ninja (Faster Builds)
```bash
mkdir build && cd build
@@ -103,19 +103,15 @@ The easiest way to build MetalOS with all dependencies:
```bash
./scripts/docker-build.sh # Build Docker image
./scripts/docker-run.sh scripts/setup-deps.sh # Setup dependencies
./scripts/docker-run.sh make all # Build everything
./scripts/docker-run.sh make qemu # Test in QEMU
./scripts/docker-run.sh cmake --build build # Build everything
```
**See [docs/BUILD_SYSTEMS.md](docs/BUILD_SYSTEMS.md) for detailed comparison and usage of all build systems.**
**QEMU UEFI Testing**:
```bash
make qemu # Boot in QEMU with UEFI (headless)
make qemu QEMU_DISPLAY=gtk # Boot with graphical display
make qemu-debug # Boot with debug output
make qemu-gdb # Boot with GDB debugging
make qemu-uefi-test # Test UEFI firmware setup
cmake --build . --target qemu # Boot in QEMU with UEFI (headless)
cmake --build . --target qemu-debug # Boot with debug output
cmake --build . --target qemu-gdb # Boot with GDB debugging
cmake --build . --target qemu-uefi-test # Test UEFI firmware setup
```
See [docs/BUILD.md](docs/BUILD.md) for detailed build instructions and [docs/TESTING.md](docs/TESTING.md) for testing guide.

View File

@@ -1,55 +0,0 @@
# MetalOS Bootloader Makefile
# Builds UEFI bootloader (bootx64.efi)
# Cross-compiler setup
CC = gcc
LD = ld
OBJCOPY = objcopy
# Directories
SRC_DIR = src
INC_DIR = include
BUILD_DIR = build
# Compiler flags for UEFI
CFLAGS = -Wall -Wextra -Werror \
-ffreestanding -fno-stack-protector -fno-stack-check \
-fshort-wchar -mno-red-zone \
-I$(INC_DIR) \
-DEFI_FUNCTION_WRAPPER
# Linker flags for UEFI
LDFLAGS = -shared -Bsymbolic -nostdlib \
-znocombreloc -T uefi.lds
# Source files
SOURCES = $(wildcard $(SRC_DIR)/*.c)
OBJECTS = $(patsubst $(SRC_DIR)/%.c,$(BUILD_DIR)/%.o,$(SOURCES))
# Output
TARGET = bootx64.efi
.PHONY: all clean
all: $(BUILD_DIR) $(TARGET)
$(BUILD_DIR):
mkdir -p $(BUILD_DIR)
# Compile C files
$(BUILD_DIR)/%.o: $(SRC_DIR)/%.c
$(CC) $(CFLAGS) -c $< -o $@
# Link and create EFI binary
$(TARGET): $(OBJECTS)
$(LD) $(LDFLAGS) $(OBJECTS) -o $(BUILD_DIR)/bootx64.so
$(OBJCOPY) -j .text -j .sdata -j .data -j .dynamic \
-j .dynsym -j .rel -j .rela -j .reloc \
--target=efi-app-x86_64 \
$(BUILD_DIR)/bootx64.so $@
clean:
rm -rf $(BUILD_DIR) $(TARGET)
# Note: This is a simplified Makefile
# A real implementation would use gnu-efi or proper UEFI SDK

View File

@@ -21,10 +21,12 @@ The easiest way to build MetalOS is using Docker, which provides a pre-configure
./scripts/docker-run.sh scripts/setup-deps.sh
# 3. Build MetalOS
./scripts/docker-run.sh make all
mkdir build && cd build
cmake ..
cmake --build .
# 4. Test in QEMU (headless mode)
./scripts/docker-run.sh make qemu
cmake --build . --target qemu
# 5. Optional: Interactive shell in container
./scripts/docker-run.sh /bin/bash
@@ -33,7 +35,7 @@ The easiest way to build MetalOS is using Docker, which provides a pre-configure
### What's Included in Docker
The Docker image includes:
- **Build tools**: GCC, NASM, Make, CMake, Meson
- **Build tools**: GCC, NASM, CMake, Meson
- **QEMU**: For testing with UEFI firmware
- **OVMF**: UEFI firmware for QEMU
- **Dependency management**: Scripts to download AMD firmware, Mesa RADV, QT6
@@ -127,11 +129,15 @@ This produces `kernel/metalos.bin` - the kernel binary.
## Creating Bootable Image
```bash
# From repository root
make image
# From repository root, if you haven't already
mkdir build && cd build
cmake ..
# Create the bootable image
cmake --build . --target image
```
This creates `build/metalos.img` - a bootable disk image containing:
This creates the bootable disk image at `<build-directory>/build/metalos.img` (e.g., `build/build/metalos.img` if your build directory is named `build/`). The image contains:
- EFI System Partition with bootloader
- Kernel binary
- Any required data files
@@ -146,41 +152,33 @@ Ensure QEMU and OVMF are installed:
```bash
# Ubuntu/Debian
sudo apt-get install qemu-system-x86 ovmf mtools
sudo apt-get install qemu-system-x86 ovmf mtools cmake
# Arch Linux
sudo pacman -S qemu-full edk2-ovmf mtools
sudo pacman -S qemu-full edk2-ovmf mtools cmake
# Fedora
sudo dnf install qemu-system-x86 edk2-ovmf mtools
sudo dnf install qemu-system-x86 edk2-ovmf mtools cmake
```
### Boot MetalOS in QEMU
```bash
make qemu
cd build
cmake --build . --target qemu
```
This will:
1. Build bootloader and kernel (or use placeholders if build fails)
1. Build bootloader and kernel
2. Create a bootable FAT32 disk image with UEFI boot structure
3. Launch QEMU with OVMF UEFI firmware in headless mode
4. Boot the system (will drop to UEFI shell until bootloader is complete)
**Display Options**: By default, QEMU runs in headless mode (no graphics). To use graphical display:
```bash
# Use GTK display (if available)
make qemu QEMU_DISPLAY=gtk
# Use SDL display (if available)
make qemu QEMU_DISPLAY=sdl
```
4. Boot the system
### Boot with Debug Output
```bash
make qemu-debug
cd build
cmake --build . --target qemu-debug
```
This includes CPU interrupt and reset debugging output.
@@ -191,7 +189,8 @@ For debugging with GDB:
```bash
# Terminal 1 - Start QEMU with GDB server
make qemu-gdb
cd build
cmake --build . --target qemu-gdb
# Terminal 2 - Connect GDB
gdb kernel/metalos.bin
@@ -206,7 +205,8 @@ QEMU will wait for GDB connection before starting execution.
To verify QEMU and OVMF are properly installed without needing a bootable OS image:
```bash
make qemu-uefi-test
cd build
cmake --build . --target qemu-uefi-test
```
This boots directly to the UEFI shell, confirming your QEMU+OVMF setup works correctly.
@@ -292,10 +292,14 @@ ENABLE_SERIAL ?= 1
```bash
# Clean all build artifacts
make clean
cd build
cmake --build . --target clean
# Clean everything including dependencies
make distclean
# Or remove the build directory entirely
cd ..
rm -rf build
mkdir build && cd build
cmake ..
```
## Troubleshooting

View File

@@ -1,21 +1,15 @@
# MetalOS Build Systems Guide
MetalOS supports multiple build systems to accommodate different developer preferences and workflows.
MetalOS uses **CMake** as its primary build system, which can be used with different build backends for different workflows.
## Quick Start
### Using Make (Traditional)
```bash
make all # Build everything
make qemu # Test in QEMU
make clean # Clean build artifacts
```
### Using CMake + Make
### Using CMake (Default)
```bash
mkdir build && cd build
cmake ..
cmake --build .
cmake --build . --target qemu # Test in QEMU
```
### Using CMake + Ninja (Fastest)
@@ -23,6 +17,7 @@ cmake --build .
mkdir build && cd build
cmake -G Ninja ..
ninja
ninja qemu # Test in QEMU
```
### Using Conan + CMake
@@ -35,89 +30,38 @@ cmake --build .
## Build System Comparison
| Build System | Speed | Features | Best For |
|--------------|-------|----------|----------|
| **Make** | Medium | Simple, traditional | Quick builds, CI/CD |
| **CMake** | Medium | Cross-platform, modern | Complex projects, IDEs |
| Build Backend | Speed | Features | Best For |
|---------------|-------|----------|----------|
| **Make** (default) | Medium | Cross-platform, standard | General use, CI/CD |
| **Ninja** | Fast | Parallel builds | Development, large projects |
| **Conan** | Medium | Dependency management | Projects with external deps |
## Detailed Usage
### 1. Make (Traditional Build System)
### 1. CMake (Primary Build System)
The original build system using GNU Make.
CMake is the primary build system for MetalOS, providing cross-platform support and modern features.
#### Build Commands
```bash
# Build all components
make all
# Build individually
make bootloader
make kernel
make test
# Create bootable image
make image
# Run in QEMU
make qemu # Headless mode
make qemu QEMU_DISPLAY=gtk # With GUI
make qemu-debug # With debug output
make qemu-gdb # With GDB server
# Clean
make clean # Clean build artifacts
make distclean # Deep clean
```
#### Advantages
- ✅ Simple and straightforward
- ✅ No additional dependencies
- ✅ Works on all Unix-like systems
- ✅ Easy to understand and modify
#### Disadvantages
- ❌ Not cross-platform (Windows requires special setup)
- ❌ Can be slower for large projects
- ❌ Limited dependency tracking
---
### 2. CMake (Modern Build Generator)
CMake generates build files for various build systems (Make, Ninja, Visual Studio, etc.).
#### Build Commands
```bash
# Configure (generates build files)
# Configure and build
mkdir build && cd build
cmake ..
# Configure with specific generator
cmake -G "Unix Makefiles" ..
cmake -G Ninja ..
cmake -G "Visual Studio 17 2022" .. # Windows
# Configure with options
cmake -DBUILD_BOOTLOADER=ON -DBUILD_KERNEL=ON -DBUILD_TESTS=ON ..
cmake -DCMAKE_BUILD_TYPE=Debug ..
cmake -DCMAKE_BUILD_TYPE=Release ..
# Build
cmake --build .
cmake --build . --parallel 8 # Use 8 parallel jobs
# Build specific targets
cmake --build . --target bootloader_efi
cmake --build . --target kernel_bin
cmake --build . --target image
# Run custom targets
cmake --build . --target qemu
cmake --build . --target qemu-debug
cmake --build . --target qemu-gdb
# Create bootable image
cmake --build . --target image
# Run in QEMU
cmake --build . --target qemu # Headless mode
cmake --build . --target qemu-debug # With debug output
cmake --build . --target qemu-gdb # With GDB server
cmake --build . --target qemu-uefi-test # Test UEFI setup
# Test
ctest
@@ -133,6 +77,23 @@ cmake --build . --target clean
rm -rf build # Complete clean
```
#### Advantages
- ✅ Cross-platform (Windows, Linux, macOS)
- ✅ IDE integration (CLion, VSCode, Visual Studio)
- ✅ Modern dependency management
- ✅ Better parallel build support
- ✅ Generates compile_commands.json for IDEs
#### Disadvantages
- ❌ Requires cmake installation
- ❌ Slightly more complex setup
---
### 2. Ninja (Fast Build Backend)
Ninja is a fast build backend that can be used with CMake for faster incremental builds.
#### Advantages
- ✅ Cross-platform (Windows, Linux, macOS)
- ✅ IDE integration (CLion, Visual Studio, VS Code)

View File

@@ -63,9 +63,11 @@ add_executable(kernel_elf $<TARGET_OBJECTS:kernel_obj> ${KERNEL_ASM_OBJECTS})
set_target_properties(kernel_elf PROPERTIES
OUTPUT_NAME metalos.elf
LINKER_LANGUAGE C
POSITION_INDEPENDENT_CODE OFF
)
target_link_options(kernel_elf PRIVATE
-nostdlib
-no-pie
-T ${CMAKE_CURRENT_SOURCE_DIR}/linker.ld
)

View File

@@ -1,79 +0,0 @@
# MetalOS Kernel Makefile
# Cross-compiler (x86_64 bare metal)
CC = x86_64-elf-gcc
AS = nasm
LD = x86_64-elf-ld
OBJCOPY = x86_64-elf-objcopy
# Check if cross-compiler exists, fallback to regular gcc
ifeq ($(shell which $(CC) 2>/dev/null),)
CC = gcc
LD = ld
OBJCOPY = objcopy
endif
# Directories
SRC_DIR = src
INC_DIR = include
BUILD_DIR = build
# Compiler flags
CFLAGS = -Wall -Wextra -Werror \
-ffreestanding -fno-stack-protector \
-mno-red-zone -mcmodel=large \
-I$(INC_DIR) \
-O2
# Assembler flags
ASFLAGS = -f elf64
# Linker flags
LDFLAGS = -nostdlib -T linker.ld
# Source files
C_SOURCES = $(shell find $(SRC_DIR) -name '*.c')
ASM_SOURCES = $(shell find $(SRC_DIR) -name '*.asm')
# Object files
C_OBJECTS = $(patsubst $(SRC_DIR)/%.c,$(BUILD_DIR)/%.o,$(C_SOURCES))
ASM_OBJECTS = $(patsubst $(SRC_DIR)/%.asm,$(BUILD_DIR)/%.o,$(ASM_SOURCES))
OBJECTS = $(C_OBJECTS) $(ASM_OBJECTS)
# Output
TARGET = metalos.bin
.PHONY: all clean
all: $(BUILD_DIR) $(TARGET)
$(BUILD_DIR):
mkdir -p $(BUILD_DIR)
mkdir -p $(BUILD_DIR)/core
mkdir -p $(BUILD_DIR)/hal
mkdir -p $(BUILD_DIR)/drivers
mkdir -p $(BUILD_DIR)/syscall
# Compile C files
$(BUILD_DIR)/%.o: $(SRC_DIR)/%.c
@mkdir -p $(dir $@)
$(CC) $(CFLAGS) -c $< -o $@
# Assemble ASM files
$(BUILD_DIR)/%.o: $(SRC_DIR)/%.asm
@mkdir -p $(dir $@)
$(AS) $(ASFLAGS) $< -o $@
# Link kernel
$(TARGET): $(OBJECTS)
$(LD) $(LDFLAGS) $(OBJECTS) -o $@
clean:
rm -rf $(BUILD_DIR) $(TARGET)
# Print variables for debugging
info:
@echo "C Sources: $(C_SOURCES)"
@echo "ASM Sources: $(ASM_SOURCES)"
@echo "Objects: $(OBJECTS)"
@echo "Compiler: $(CC)"

View File

@@ -1,64 +0,0 @@
# MetalOS Test Suite Makefile
CC = gcc
CFLAGS = -Wall -Wextra -std=c11 -I../tests/include -I../kernel/include -I../bootloader/include
LDFLAGS =
# Test source files
TEST_SOURCES = $(wildcard unit/*.c)
TEST_BINARIES = $(TEST_SOURCES:.c=)
# Default target
.PHONY: all
all: $(TEST_BINARIES)
# Build each test binary
unit/%: unit/%.c include/test_framework.h
@echo "Building test: $@"
$(CC) $(CFLAGS) $< -o $@ $(LDFLAGS)
# Run all tests
.PHONY: test
test: all
@echo ""
@echo "╔════════════════════════════════════════════╗"
@echo "║ Running MetalOS Test Suite ║"
@echo "╚════════════════════════════════════════════╝"
@echo ""
@for test in $(TEST_BINARIES); do \
./$$test || exit 1; \
done
@echo ""
@echo "╔════════════════════════════════════════════╗"
@echo "║ All Test Suites Passed ✓ ║"
@echo "╚════════════════════════════════════════════╝"
@echo ""
# Run tests with verbose output
.PHONY: test-verbose
test-verbose: all
@for test in $(TEST_BINARIES); do \
echo "Running $$test..."; \
./$$test -v; \
echo ""; \
done
# Clean test binaries
.PHONY: clean
clean:
@echo "Cleaning test binaries..."
@rm -f $(TEST_BINARIES)
@rm -f unit/*.o
@echo "Clean complete"
# Help target
.PHONY: help
help:
@echo "MetalOS Test Suite Makefile"
@echo ""
@echo "Targets:"
@echo " all - Build all test binaries"
@echo " test - Build and run all tests"
@echo " test-verbose - Run tests with verbose output"
@echo " clean - Remove test binaries"
@echo " help - Show this help message"