This is an old revision of the document!


QEMU setup for kernel development

In this section we present a step-by-step guide of setting up a kernel development environment using qemu-system-aarch64. This emulator is very widely used, enables easy kernel debugging, and is extremely efficient. However, it is not a replacement for a hardware testing environment. If you want to develop a device driver and not say, an iptables plugin, you should probably be looking for a development board. Similarly, this emulator does away with most of the ARM boot process, meaning that you're not going to be able to test out the bootloaders studied during the first two sessions. This solution is strictly for kernel development.

The Linux kernel

This step is very straightforward. Just clone the Linux repo (with depth=1 to squash the commit history) and compile it for the arm64 target. Optionally, you can enable the generation of debug symbols & gdb helper scripts; the config options are CONFIG_DEBUG_INFO_DWARF5 and CONFIG_GDB_SCRIPTS, found under Kernel hacking → Compile-time checks and compiler options.

# clone the repo
~$ git clone --depth=1 https://github.com/torvalds/linux.git
 
# generate a default config & compile
# NOTE: the default target will also compile the modules
linux$ make ARCH=arm64 CROSS_COMPILE=aarch64-linux-gnu- defconfig
linux$ make ARCH=arm64 CROSS_COMPILE=aarch64-linux-gnu- -j $(nproc)

When navigating the source code of any project, it's useful to be able to jump to definitions / references of a particular symbol. This functionality is provided by a language server (e.g.: clangd. If your editor implements a Language Server Protocol (LSP) client, you should be able to interact with the language server whose job is to index the source code.

Unfortunately, the server does not have any foolproof method of inferring the structure of the project. For example, it has no idea whether you are using the arm64 or the x86 definition of a function. Luckily for us, the Linux build system contains a script that's able to generate a file names compile_commands.json. This file contains all compiler invocations used during the boot and can deduce include paths, compiled source, macro definitions, etc. The language server will automatically load it and generate indices for the compiled source code.

Note that this script only forks for the Linux kernel. If you want to generate compile_commands.json for other projects, consider using Bear. This is a tool that hooks the exec() family of library calls via LD_PRELOAD hooking in order to extract the command arguments.

Bootstrapping the rootfs

In this example setup we're going to be using debootstrap to generate a root filesystem based on Debian.

~$ mkdir rootfs
~$ sudo debootstrap --arch arm64 stable rootfs/ \
                     http://ftp.hosteurope.de/mirror/ftp.debian.org/debian/
ass/cursuri/04/theory/00.1723201950.txt.gz · Last modified: 2024/08/09 14:12 by radu.mantu
CC Attribution-Share Alike 3.0 Unported
www.chimeric.de Valid CSS Driven by DokuWiki do yourself a favour and use a real browser - get firefox!! Recent changes RSS feed Valid XHTML 1.0