Skip to content

Compilation and Build

Relevant source files

The following files were used as context for generating this wiki page:

This page provides detailed technical instructions for compiling eCapture from source. eCapture utilizes a complex build system that coordinates Go for the userspace control plane and C for the eBPF kernel programs. It supports both CO-RE (Compile Once – Run Everywhere) and non-CO-RE builds to ensure compatibility across a wide range of Linux kernel versions and architectures, including Android GKI.

Build Architecture Overview

The build process is managed by a multi-layered Makefile system that handles dependency checking, eBPF bytecode generation, asset embedding, and final binary linking.

Build Flow Diagram

The following diagram illustrates the data flow from source code to the final ecapture binary.

"eCapture Build Pipeline"

Sources: Makefile:6-7, Makefile:162-165, Makefile:189-193

Required Toolchain

To build eCapture, the following tools must be installed on the host system:

ToolVersion RequirementPurpose
Golang>= 1.24Compiling the userspace control plane functions.mk:28-34.
Clang>= 14 (Recommended)Compiling C code into eBPF bytecode functions.mk:17-21.
LLVMMatches Clang versionRequired for llc and llvm-strip variables.mk:14.
libelf-devN/ARequired for eBPF program loading.
libpcapSubmoduleStatic linking for pcapng output support Makefile:177-187.
go-bindataManaged via GoEmbeds .o files into Go source Makefile:164.

Environment Initialization

The project provides a script to automate the setup on Ubuntu systems: builder/init_env.sh. This script installs the necessary compilers, links the correct tool versions (e.g., clang-14 to clang), and prepares the Linux kernel headers builder/init_env.sh:72-88.

CO-RE vs. Non-CO-RE Builds

eCapture supports two primary eBPF compilation strategies.

1. CO-RE (Compile Once – Run Everywhere)

  • Mechanism: Uses BPF Type Format (BTF) to handle kernel structure offsets dynamically at runtime.
  • Requirement: Target kernel must be compiled with CONFIG_DEBUG_INFO_BTF=y.
  • Build Command: make or make ebpf Makefile:6.
  • Implementation: Relies on vmlinux.h generated from the host or provided in kern/bpf/$(ARCH)/vmlinux.h variables.mk:163.

2. Non-CO-RE

  • Mechanism: Compiles the eBPF program against specific kernel headers for the target environment.
  • Requirement: Requires kernel headers for the specific kernel version where eCapture will run.
  • Build Command: make nocore Makefile:10.
  • Use Case: Older kernels (e.g., < 5.4) or environments without BTF support.

Sources: Makefile:133-160, variables.mk:184

Common Makefile Targets

The Makefile defines several key targets for different deployment scenarios:

  • make env: Displays the current build environment variables, including detected tool versions and paths Makefile:20-63.
  • make all: The default target. Builds both CO-RE and non-CO-RE bytecode and links them into a single binary Makefile:6.
  • make nocore: Builds only the non-CO-RE version Makefile:10.
  • make clean: Removes all generated artifacts, including bytecode, assets, and the final binary Makefile:109-115.
  • make android: A shortcut (via ANDROID=1) to build for the Android platform, which typically implies non-CO-RE and specific BoringSSL hooks Makefile:95, variables.mk:65-68.

Cross-Compilation

eCapture supports cross-compilation between x86_64 (amd64) and aarch64 (arm64).

Arm64 (Linux)

To build for arm64 on an x86_64 host:

bash
CROSS_ARCH=arm64 make

The build system uses aarch64-linux-gnu- as the compiler prefix and sets GOARCH=arm64 variables.mk:123-127.

Android

Android builds require the ANDROID=1 flag. This adjusts the target OS and includes specific Android BoringSSL probes variables.mk:65-68.

bash
ANDROID=1 CROSS_ARCH=arm64 make nocore

Sources: Makefile:92-95, variables.mk:111-131

Docker Build Environment

For a reproducible build environment, a Dockerfile is provided in builder/Dockerfile. It uses a multi-stage build:

  1. ecapture_builder: An Ubuntu 22.04 image that installs the full toolchain (Clang 14, Go 1.24, kernel sources) and compiles the project builder/Dockerfile:1-32.
  2. ecapture: A minimal Alpine-based final image containing only the compiled binary builder/Dockerfile:35-38.

"Docker Build Stage Mapping"

Sources: builder/Dockerfile:1-38

Implementation Details: Asset Embedding

eCapture uses go-bindata to embed eBPF bytecode directly into the Go binary. This ensures that the tool is a single, portable executable.

  1. The eBPF C code in kern/ is compiled to .o files in bytecode/ Makefile:118-127.
  2. The assets target runs go-bindata on bytecode/*.o Makefile:164.
  3. The generated assets/ebpf_probe.go file contains the hex-encoded bytecode, which is then compiled into the final binary Makefile:165.

Sources: Makefile:162-174

Compilation and Build has loaded