This guide covers creating a Linux kernel package for postmarketOS, a critical step in porting the operating system to a new device. The kernel package defines which hardware features are available and how the device boots.
You must choose between two kernel packaging approaches:
Downstream (vendor) kernel: The original kernel provided by the device manufacturer, typically with heavy modifications for Android. This path is fastest for initial device bringup and is common for devices in the testing category.
Mainline kernel: A kernel close to the official upstream Linux kernel source, maintained by the postmarketOS community for specific System-on-Chip (SoC) families. This path is preferred for long-term maintenance and devices in the community and main categories.
Select the appropriate section below and follow the workflow for your chosen approach. Both paths ultimately require kernel configuration adjustments covered in the Kernel configuration section at the end of this page.
Downstream kernels are based on manufacturer-provided source code, often modified for Android devices. This approach requires finding and configuring existing sources, but is typically quicker to get working initially.
Step 1: Locate the kernel source
Identify the exact kernel source that matches your device.
On GitHub: Search for repositories named android_kernel_vendor_codename where vendor is the manufacturer and codename is your device's internal name. The organization that maintains the ROM for your device (usually LineageOS) is a good starting point.
Some SoCs use a shared kernel across multiple devices, typically named android_kernel_vendor_soccodename. Check the same GitHub organization that hosts the device-specific repositories.
From manufacturers: Some companies provide open-source repositories on their websites:
Important: If you locate the kernel on a manufacturer's website, mirror it to GitHub or another persistent public location. Manufacturer links disappear frequently, making your port unmaintainable. Do not create your own fork with patches applied; instead, apply patches during the build process through the APKBUILD.
If public sources are unavailable, contact the manufacturer requesting source code distribution. The GPL license requires that distributed kernels include source availability.
Replace LineageOS with your kernel's GitHub user/organization, and _repository with the actual repository name. Set _commit to the full commit hash you want to build (found on the GitHub repository page).
This translates to version 4.9.292-rc1. Update the pkgver variable in the APKBUILD accordingly. Omit EXTRAVERSION if empty.
Never modify pkgrel. This variable tracks rebuild iterations without version changes.
Locate the defconfig:
The defconfig file contains your device's kernel configuration. Search the kernel source at arch/arm/configs/ or arch/arm64/configs/ for a file matching your device's codename or model number.
In LineageOS/CyanogenMod kernels, look for filenames prefixed with lineage_ or cyanogenmod_.
If a build.config exists in the repository root, check it for a DEFCONFIG= line.
For android_device_vendor_codename repositories, check BoardConfig.mk for a TARGET_KERNEL_CONFIG variable.
If the defconfig is not in the source and you have root access to the device, extract it from the running system:
(If /proc/config.gz does not exist, this approach will not work.)
Copy the defconfig file to the kernel package directory and rename it to config-vendor-codename.arch, where arch is armv7 or aarch64 (from your device package).
In the APKBUILD, update the comment at the top:
# Kernel config based on: lineage_msm8916_defconfig
Step 3: Generate checksums
Download the kernel source and generate checksums:
This command downloads the kernel tarball (cached for future use) and computes SHA256 hashes for all source files. If the download fails, verify your source URL and commit hash.
Checksums verify source file integrity only. After running kconfig edit, checksums are regenerated automatically.
Step 4: Configure the kernel
Vendor kernels typically lack kernel configuration options required by postmarketOS. Proceed to the Kernel configuration section below to adjust these settings.
WARNING: Do not edit the config file directly. Manual edits do not propagate dependency updates and are silently ignored.
Step 5: Build and troubleshoot
Attempt to build the kernel:
$ pmbootstrapbuildlinux-''vendor''-''codename''
The build will likely fail with compilation errors because postmarketOS uses newer GCC and build tools than the kernel was originally compiled with.
Finding errors:
Check the pmbootstrap log at /home/user/.local/var/pmbootstrap/log.txt. Search for "error" or "fail" to locate the problem. Common errors include:
In file included from arch/arm/mach-msm/perf_trace_counters.h:127:0:
include/trace/define_trace.h:79:43: fatal error: ./perf_trace_counters.h: No such file or directory
or linker errors at the end of the build:
drivers/built-in.o: In function `.LANCHOR1':
msm_iommu_sec.c:(.data+0x9298): undefined reference to `kgsl_iommu_sync_lock'
Makefile:877: recipe for target '.tmp_vmlinux1' failed
Repeat until the build succeeds. Track which patches are applied—you will reference them if the kernel is later updated.
If you see a warning about mismatched checksums, you modified non-APKBUILD files without regenerating checksums. Run pmbootstrap checksum ... again.
Mainline Kernel Workflow
Mainline kernels are based on or very close to the official upstream Linux kernel. The postmarketOS community maintains shared kernel packages for specific SoCs, allowing multiple devices to use the same kernel source while supporting device-specific configuration through Device Trees.
Step 1: Check SoC support status
Determine how well the mainline Linux kernel supports your device's SoC.
Check the supported SoCs list:
Navigate to the list of supported SoCs on the postmarketOS wiki. This page shows the status of features (GPU, audio, suspend, etc.) for each SoC.
If your SoC is listed:
Note which features are working and which are not.
Visit the SoC's wiki page for detailed porting notes and kernel source recommendations.
If your SoC is not listed:
Search the upstream Linux kernel source (available at GitHub) for your SoC's codename under arch/arm/boot/dts/ or arch/arm64/boot/dts/.
The presence of a Device Tree Source (.dts) file for your SoC or a similar one is a positive indicator that mainlining is feasible.
Step 2: Find the shared kernel package
Each mainlined SoC has a single shared kernel package used by all devices on that SoC. The package name follows the pattern:
Check your SoC's wiki page—the shared kernel package name is typically listed near the top.
Search the pmaports.git repository under device/community/ or device/main/ for the pattern above.
Examine an existing device package using the same SoC and check its APKBUILD to find the shared kernel package name.
Step 3: Create your device's kernel package
Your device needs its own kernel package (not shared). This allows device-specific configuration (particularly the Device Tree) without modifying the shared kernel.
(Alternatively, manually copy the shared kernel package's APKBUILD and config files to your device directory.)
Edit the APKBUILD:
Update these variables:
pkgname="linux-''vendor''-''codename''"pkgdesc="Linux kernel for ''Device Model''"
Keep the source= array unchanged—it should point to the same upstream or community-maintained kernel source as the shared package.
Step 4: Add your device's Device Tree
The Device Tree (DTB) is the primary way to tell the kernel about your specific hardware: GPIO mappings, interrupt controllers, peripheral addresses, etc.
Locate the DTS file:
Search the kernel source under arch/arm/boot/dts/ or arch/arm64/boot/dts/ for a file matching your device's codename or a closely related SoC variant.
If your device's DTS does not exist, you must write one—this is a complex process beyond the scope of this guide. See the Mainlining Guide for detailed instructions.
Ensure the DTS is compiled:
Open the APKBUILD's build() function and verify that the kernel build process includes your .dts file. Most mainline kernels automatically compile all .dts files in the correct directory, so you may not need changes.
If required, add a patch to the kernel's Makefile or create a device-specific build configuration.
Install the resulting DTB:
In the package() function, ensure the compiled .dtb file (or combined dtb.img) is installed to the boot partition:
Examine how similar existing device packages handle this.
Step 5: Configure the kernel (optional)
You may need to enable or disable specific kernel options for your device. Proceed to the Kernel configuration section below.
Step 6: Build the kernel
Build your device's kernel package:
$ pmbootstrapbuildlinux-''vendor''-''codename''
If you have correctly referenced the shared upstream source and your Device Tree is in place, the build should succeed. If not, check the pmbootstrap log for specific errors.
Kernel configuration
Both downstream and mainline workflows require adjusting kernel configuration options to meet postmarketOS requirements. This section applies to both approaches.
WARNING: Do not edit the config file directly (e.g., config-vendor-codename.arch). Manual edits do not correctly update dependencies and are silently ignored.
postmarketOS maintains a list of required kernel configuration options in kconfigcheck.toml. If your kernel does not meet these requirements, you will see warnings and errors:
WARNING: config-vendor-codename.arch: CONFIG_DEVTMPFS should be set (category:default)ERROR: kconfig check failed! More info: https://postmarketos.org/kconfig
Copy this list to a text editor—you will address each item in the next step.
To check all kernels (including those normally skipped), use the -f flag:
This command:
1. Extracts the kernel source and applies all patches from the APKBUILD.
2. Launches an interactive configuration editor.
3. Saves the updated config back to your pmaports directory.
4. Automatically regenerates checksums.
Because checksums are regenerated automatically, do not run pmbootstrap checksum after editing.
Choosing an editor:
Two interfaces are available:
menuconfig (default): The classic ncurses terminal UI.
nconfig: An alternative interface with improved search. Use the -n flag:
For options not listed, press / to search. Type the option name without the CONFIG_ prefix:
Search for DEVTMPFS, not CONFIG_DEVTMPFS
In nconfig, the search is scoped to the current submenu; press Escape to exit search and navigate to other menu sections.
WARNING: Some options are hidden until their dependencies are satisfied. If a search result shows an option as unavailable, enable its dependencies first, then search again.
Step 3: Verify and repeat
After saving and exiting the editor, re-run the config check:
When exiting the editor, confirm that you want to save. If you exit without saving, the config file will not be updated and you will need to start over.
Key Concepts
This section defines important terms used throughout this guide.
APKBUILD: The build script for a postmarketOS/Alpine Linux package. It specifies the package name, version, source URL, build commands, and installation steps. See APKBUILD Reference for details.
defconfig: A kernel configuration file that defines which drivers and features are enabled in the compiled kernel. Often device-specific, provided by the device manufacturer.
Device Tree (DTB/DTS): A hardware description format used by modern kernels. The DTS (Device Tree Source) is a human-readable text file; the DTB (Device Tree Blob) is its compiled binary form. The kernel reads the DTB at boot to learn about your specific hardware.
Mainline kernel: The official Linux kernel source maintained at github.com/torvalds/linux, or a close derivative thereof.
Shared kernel package: A single kernel package used by multiple devices with the same SoC. Device-specific configuration is handled through Device Trees rather than separate kernel sources.
SoC (System-on-Chip): An integrated circuit containing the CPU, GPU, memory controllers, and other core components. Examples: Qualcomm Snapdragon 410 (MSM8916), Allwinner A64.
Vendor kernel: A kernel provided by the device manufacturer, typically heavily modified for Android and the specific device model.
See Also
Mainlining — Overview of mainlining and supported SoCs