Compiling a custom Samsung Android Kernel, and living to tell the tale.
Many security enthusiasts and sysadmins are familiar with the process in which one custom compiles a Linux Kernel and then installs it in our favorite distro. This can have different purposes: Security hardening, feature customization or including debugging symbols, to name a few.
However, when it comes to Android Kernels (which are heavily based on the original Linux Kernel), especially for phone models that are not from Google, one starts entering into a territory in which things are not instantly obvious and that can’t be done by following an online step-by-step tutorial.
Today, and for my next Medium Series, I’m going to try my best to change that. Remove the veil that obscures this whole infosec niche, and make it available for anyone who’s interested.
A small disclaimer: This guide is more or less specific to the Samsung S7 (SM-G930F) however, it can be applied to other Samsung models with few to no modifications.
Preparing the environment
Get yourself an Ubuntu x64 iso. I particularly prefer Xubuntu, since I prefer the look & feel however, any other flavor should be okay. At the moment Xubuntu 18.04 (Bionic Beaver) is the latest long term support distribution, which you can download from This Link.
Create a Xubuntu 18 VM using your preferred hypervisor. Make sure it has at least:
- 4 GB of RAM
- 40 GB of disk space
- 2 processor cores
This will speed up the process of compiling the kernel and will ensure that you won’t run out of space in the middle of compiling the kernel.
Once your VM is up and running, drop into a root shell and execute:
apt-get -y update
apt-get -y upgrade
apt-get -y dist-upgrade
apt-get -y install git ccache automake lzop bison gperf build-essential zip curl zlib1g-dev zlib1g-dev:i386 g++-multilib python-networkx libxml2-utils bzip2 libbz2-dev libbz2-1.0 libghc-bzlib-dev squashfs-tools pngcrush schedtool dpkg-dev liblz4-tool make optipng heimdall-flash adb
Now, we need to download the Kernel source and the android cross-compiler, which will enable us to produce AARCH64 code from a regular x86 VM.
Go to the folder in which you want to download the source and execute:
git clone https://github.com/djb77/samsung-kernel.git — branch G93XX-ALL
Make sure that the branch applies to the phone you are intending to modify.
Then, potentially on the same folder which contains the folder that holds the source code, execute:
git clone https://android.googlesource.com/platform/prebuilts/gcc/linux-x86/aarch64/aarch64-linux-android-4.9
At this point, we should have everything we need in order to compile the kernel.
Building the Kernel
First, we need to set up a few environmental variables. Go to the folder that contains the android-cross-compiler, presumably it’s called aarch64-linux-android-4.9, and run the following:
A few important caveats regarding these environmental variables:
- In the today rare case that the architecture of your device is not arm64, change the variables “ARCH” and “SUBARCH” accordingly. You can see a list of options inside the “arch” folder on the kernel source.
- Check that the folder to which the variable “CROSS_COMPILE” is pointing (after appending the version), actually exists. Otherwise the process will fail.
- The “ANDROID_MAJOR_VERSION” variable is set to “o” because we are compiling android Oreo (8.x). This will change over time, so make sure it’s adjusted accordingly.
Then we need to select our target configuration: List the contents of the folder “arch/<arch>/configs” and select the one that corresponds to your target device. In my case, it’s “exynos8890-herolte_defconfig” and I’m using arm64 as target architecture, so this is my output:
Once you have selected your target config, check how many cores your phone has (check the device’s documentation) and then run the following:
make -j(number of cores)
Remember to replace “exynos8890-herolte_defconfig” with your target defconfig file.
The process shouldn’t take much time (5 to 10 minutes), and after compiling, your kernel should be in the arch/<arch>/boot folder, named Image and Image.gz.