gila/docs/DEVELOPMENT.MD
August f0177d2d4d
Some checks failed
Continuous Integration / Check (push) Failing after 3m23s
Continuous Integration / Clippy (push) Failing after 2m12s
Memory investigations
2026-03-16 21:27:47 +00:00

7.3 KiB

Developer Resources

Design Goals & Philosophy

General design goals are outlined in DESIGN.md. Security-relevant design details can be found in SECURITY.md.

Navigating

  • kernel/src/: Kernel-specific code.
    • arch/: Architecture specific features like the display, serial, and interrupts. Each architecture is a subfolder, containing a file or module for each feature.
    • boot/: Handles bootloader-managed data structures. Gila uses Limine. Other bootloaders are NOT supported.
    • constants.rs: Constants referenced elsewhere in the kernel.
    • log.rs: Logging structures, macros, and singletons for logging to serial or the display.
    • interrupt/: Interrupt handlers with platform-agnostic APIs.
    • main.rs: The entry point that gets called by the bootloader.
    • memory.rs: Types relating to memory regions and allocation.
    • panic.rs: The panic handler and associated functionality.
    • process.rs: Process types and functions.
    • syscall_runner.rs: Chooses a system call by its ID and defers actual syscall execution to code in /libgila/src/.
  • libgila/src/: Shared between the kernel and any binaries built for it. Contains any definitions, structures, and types that will cross the boundary between userspace and kernelspace, including those sent over IPC.
    • arch/: Architecture specific functionality like system call register storing/loading.
    • syscall.rs: System call types common to apps and the kernel.

Building and running

Building a bootable kernel is easy. All you need to do is run cargo build -p kernel, and a valid, bootable Limine executable will be generated. However, it cannot be booted without installing it in a bootable Limine filesystem, and it cannot do anything useful without an initramfs containing system servers, such as the init server and device drivers.

Note

The ISO build system will be removed once Gila reaches a stable version, and instead, bootable image creation will be handled by the system software distribution.

This project uses cargo-make to handle building ISOs and managing files not associated with Cargo. You need to install it before you can build an ISO automatically. To do so, you can run cargo install cargo-make. In addition, you will also need:

  • rustup command installed
  • limine command installed
  • xorriso command installed
  • qemu-system-{your target architecture} command installed (for running)

Then run cargo make to invoke the Makefile.toml.

  • cargo make clean_all: Cleans all built binaries, libraries, initramfs files, and ISOs.
  • cargo make lib: Builds libgila, the library that the kernel and user code are linked against.
  • cargo make kernel: Builds the kernel ELF file.
  • cargo make initramfs: Build the init archive.
  • cargo make iso: Builds the bootable ISO with Limine installed.
  • cargo make run: Builds the ISO and boots it in QEMU.
  • cargo make debug: Launch the kernel in QEMU with debugging enabled, and start and connect GDB.

You do not need to clean any files after making changes. The lib, kernel, and iso tasks will automatically be rerun if their input files change.

Configuration

  • Variable LIMINEDIR: Location of binary files for limine. Default is /usr/share/limine.
  • Variable TARGET: rustc target triple to compile for. Default is x86_64-unknown-none. Options are listed in the targets section.
  • Argument -p: Rust build profile to use. Default is dev. Options are dev and release.

Note

The -p {profile} argument must go between cargo make and the task argument.

Targets

Gila currently supports aims to support four different CPU architectures:

  • x86_64
  • aarch64
  • riscv64
  • loongarch64

It currently only builds on x86_64, and will continue to only support it until I can implement support for important features in other architectures.

All these architectures are supported by Limine, and the appropriate backends are present in the Makefile to compile and build bootable images for each. While Limine (the bootloader) and rustc also support IA32 (also referred to as i686), the Limine boot protocol cannot work on a 32-bit architecture, as it relies heavily on 64-bit pointers. Compilation will fail if a build for an unsupported target is attempted.

EFI boot is presently supported, at least on x86_64. No features depend on EFI, and as such, the uefi feature can be safely disabled when booting through BIOS.

Kernel Parameters

Kernel parameters are passed as part of the cmdline through limine.conf. The parameters are passed as a space-delimited list of keys and values. Keys begin with a hyphen (-), and keys are separated from their values with equals signs (=). Keys can have a set of multiple values, separated by a comma (,). Gila does not currently support parameter values with spaces. That would require an actual parser.

List of current extant kernel parameters:

  • -loglevel: Can be a number or string corresponding to a log level. Only one value supported. Current options are Disabled, Trace, Info, Warning, Error, and Critical. This parameter is case insensitive.
  • -logdev: A sequence of one or more values representing devices to log to. Current options are display and serial. This parameter is case insensitive.
  • -initramfs: A valid path to a module to serve as the initramfs (containing the init binary). Only one value supported. This parameter is case sensitive.

The default behavior for each parameter, when not supplied, is:

-loglevel=Info -initramfs=/boot/initramfs.tar.lzma

The .lzma extension is removed from the default initramfs name when compression is disabled. It must also be changed in limine.conf or else Limine will not load it.

Writing Programs for Gila

Gila's system calls will soon be fully defined in libgila. The library is developed in tandem with, and is used within, the kernel. As such, it is treated as part of the kernel. Programs built against the wrong version of libgila will not work due to mismatched definitions.

As Gila is merely a kernel, and its userspace will heavily depend on whatever servers and drivers are included alongside it, no standard library for any language will ever be issued as part of the kernel's software package. Instead, this will be deferred to the system software developer who designs and integrates the userspace.

To compile software for Gila, simply write your program as if it were a no_std binary for the kernel's processor architecture. By linking against libgila, the program may access things like system calls, error types, and IPC data formats.

Contributing

Contribution policies are outlined in CONTRIBUTING.md.