In this document, I will show you how to set up a build environment and perform regular builds of LineageOS 14.1 (Android 7.1.2) for Huawei Ascend Y550 devices. These are the steps I took, the problems I ran into and the solutions that worked for me.
My goal in writing this tutorial is to preserve these instructions for myself and anyone interested in keeping the Y550 ‘alive’ in the sense of being safe to use from a software point of view.
Most of the information and instructions found in this tutorial were previously written by others. I will provide links to sources whenever possible. The primary source of inspiration for this document is the official build instruction document for the Huawei Honor 4/4X CHE1 (codename cherry
) device, written by the LineageOS developers. Thanks to pndwal for proofreading and providing feedback on this tutorial.
You might ask: why even bother keeping a smartphone released in 2014 up to date while there are so many other newer and faster devices out there? I have two answers to this question. Personally, I don’t like to dispense with a device that still works just because it’s old or slow. Also, getting to know the operating system and how to build it is a great personal challenge with a victory every now and then.
If you haven’t already, install Ubuntu. Choose “minimal” configuration as you won’t need anything more than the basic system utilities. If you’re using a virtual machine, make sure you install openssh-server
to reach it from your local terminal.
sudo apt update;
sudo apt install -y openssh-server;
First, update the system’s package lists and upgrade to latest. Then install the following packages:
sudo apt update && sudo apt upgrade -y;
sudo apt install -y bc bison build-essential ccache curl flex \
g++-multilib gcc-multilib git gnupg gperf imagemagick \
lib32ncurses5-dev lib32readline-dev lib32z1-dev liblz4-tool \
libncurses5 libncurses5-dev libsdl1.2-dev libssl-dev libxml2 \
libxml2-utils lzop pngcrush rsync schedtool squashfs-tools \
libxslt1-dev openjdk-8-jdk android-tools-adb android-tools-fastboot \
python
The following directories will have to be created:
mkdir -p ~/bin;
mkdir -p ~/android/lineage;
The first will be home to repo
, an important command that we’ll use to update and manage all the different projects contained in our custom ROM.
The second will hold all the source code and related files.
The following command downloads the repo
script and makes it executable:
curl https://storage.googleapis.com/git-repo-downloads/repo > ~/bin/repo;
chmod a+x ~/bin/repo;
To make sure the ~/bin
directory is in your ${PATH}
environment variable, open ~/.profile
and add the following code, if it’s not already there:
# set PATH so it includes user's private bin if it exists
if [ -d "$HOME/bin" ] ; then
PATH="$HOME/bin:$PATH"
fi
If you added it just now, run source ~/.profile
to update your environment.
Even if you will never push your edits out into the world, git
and repo
demand to know who you are. So, provide your name and emailaddress:
git config --global user.name "Firstname Lastname";
git config --global user.email your@emailaddress.com;
Next, move to and initialize the source directory. Answer yes
at the prompt to enable colors in repo
’s output. Then download the sources:
cd ~/android/lineage;
repo init -u https://github.com/LineageOS/android.git -b cm-14.1;
repo sync --force-sync;
This will take a long time, depending on your internet connection and system specs.
repo
keeps track of all the different projects that are combined into an image. It parses XML
-files in a hidden folder inside the top directory: ~/android/lineage/.repo
. These files are called manifests.
Create a subfolder called local_manifests
in the .repo
directory. Add a new XML
-file with any name you want. Mine is called fwiep.xml
:
<?xml version="1.0" encoding="UTF-8"?>
<manifest>
<remote name="githubfwiep" fetch="https://github.com/fwiep" />
<project
path="device/cyanogen/msm8916-common"
name="LineageOS/android_device_cyanogen_msm8916-common"
remote="github"
revision="cm-14.1" />
<project
path="device/huawei/msm8916-common"
name="android_device_huawei_msm8916-common"
remote="githubfwiep"
revision="cm-14.1" />
<project
path="device/huawei/y550"
name="android_device_huawei_y550"
remote="githubfwiep"
revision="cm-14.1" />
<project
path="device/qcom/common"
name="LineageOS/android_device_qcom_common"
remote="github"
revision="cm-14.1" />
<project
path="vendor/huawei"
name="proprietary_vendor_huawei"
remote="githubfwiep"
revision="cm-14.1" />
<project
path="kernel/huawei/msm8916"
name="android_kernel_huawei_msm8916"
remote="githubfwiep"
revision="cm-14.1" />
<project
path="kernel/huawei/y550-vid"
name="android_kernel_huawei_y550"
remote="githubfwiep"
revision="los-14.1" />
</manifest>
Now, perform another synchronization:
repo sync --force-sync;
To make the source code and the resulting image compatible with our Y550 devices, the cherry
-specific code must be edited. Luckily for you, these edits have already been made. They are contained in the projects with the remote="githubfwiep"
attribute, above. If you want, you can review the commits on github.
Now, things get complicated. Unfortunately, not all firmware needed to run a smartphone or tablet is open source. The manufacturers keep some of it secret, closed source. They make the hardware dependant on those pieces. That means we can not use the device without them.
When I first forked the Lineage-repositories for this project, I added the vendor-specific files to my repository. It may not be completely legal to provide the files like this, but it saves you and me quite a few headaches.
So by now you should have all the necessary files on disk. The following steps are the ones I performed to get them in the first place. Please skip to CCache
if you’re not interested.
Luckily, there is a way to extract the closed source pieces of code from a device already running the same branch of LineageOS. If that is not an option, there is a way to extract the files from an installable zip
-file, too. For the latest of such a zip
-file, see post #74 or the thread index on XDA.
cd ~/android/lineage;
source build/envsetup.sh;
breakfast y550;
This command will make the necessary folders in /vendor
to hold all the vendor-specific files, and also download a few more projects and source code. Now, connect your Y550 with recent LineageOS 14.1 via USB and extract the proprietary files from it:
cd device/huawei/y550;
./extract-files.sh;
Alternatively, you could extract the files from an installable zip
-file, as stated above (please follow the LineageOS-instructions first):
cd device/huawei/y550;
./extract-files.sh ~/android/system_dump/;
All source code has to be translated to a format that the central processor of the device (CPU) can understand. This is called compilation. To speed up the building process, you can enable the compiler cache or ccache
for short. If you build for the same device repeatedly, files that didn’t change since the last build (and have already been compiled) are copied over to the new build instead of being compiled again. This can save an enormous amount of time.
Execute the following command once to set the desired cache size:
ccache -M 50G;
Then, execute the following command, setting the USE_CCACHE
environment variable in your current session. Append this same command to your ~/.bashrc
, so it will be automatically executed when your shell session begins:
export USE_CCACHE=1;
Finally, we’re going to set up the application that directs and controls the building process: jack; not to be confused with the JACK Audio Connection Kit (JACK).
For me, this was the most difficult part of setting up my build system. Jack is very picky about the amount of memory it gets; more is better. Much more is much better.
These are the settings that worked for me. I put them in a file called ~/.jack-settings
:
# Server settings
SERVER_HOST=127.0.0.1
SERVER_PORT_SERVICE=8076
SERVER_PORT_ADMIN=8077
# Internal, do not touch
SETTING_VERSION=4
JACK_SERVER_VM_ARGUMENTS="-Dfile.encoding=UTF-8 -XX:+TieredCompilation -Xmx4096m"
Then add another environment variable to your session and ~/.bashrc
:
export ANDROID_JACK_VM_ARGS="-Dfile.encoding=UTF-8 -XX:+TieredCompilation -Xmx4096m";
After an Ubuntu update in june 2021, the build process ended abruptly while complaining about being unable to connect securely to the jack-server. Luckily, StackOverflow held an answer to this question: remove TLSv1
and TLSv1.1
from jdk.tls.disabledAlgorithms
in /etc/java-8-openjdk/security/java.security
. Don’t forget to kill and restart the jack-server; see below.
Now it’s time to build our first image! It may take some time or even crash because of a memory shortage. Be patient and observant. Read the messages on the screen and try to make sense of them. Most developers provide helpful hints to solve common issues. Sometimes it’s a missing package, sometimes it’s a jack
-memory-setting.
The command to do this is further explained in the next section, “How to build regular (monthly) updates”. It is:
cd ~/android/lineage;
source build/envsetup.sh;
LANG=C brunch y550 2>&1 | tee $( date +'%Y-%m-%d_%H-%M-%S' )-build.log;
If this fails because of a memory issue (jack
) and you know what to do about it, don’t forget to kill and restart the jack-server after the fix:
croot;
./prebuilts/sdk/tools/jack-admin kill-server;
./prebuilts/sdk/tools/jack-admin start-server;
On the fifth of each month, Google releases security patches for all of their supported devices. Alongside those, the source code for these fixes is released to the open source community. The LineageOS developers integrate them into their sources. Luckily for Y550 users, Android 7.1.2 is still supported, though there are not many fixes these days (june 2021). But when there are, it’s well worth the wait.
To integrate the monthly security updates into the custom ROM, follow these steps. It takes about 30 minutes on my quad-core with 8 GByte of RAM.
cd ~/android/lineage;
source build/envsetup.sh;
croot;
repo sync --force-sync;
grep -o -P '(?<=PLATFORM_SECURITY_PATCH := ).*' build/core/version_defaults.mk;
I’ll explain each of these commands:
cd ~/android/lineage
- navigate to the top folder containing the LineageOS sources.source build/envsetup.sh
- execute the setup script to set environment variables and add functions to the current shell session.croot
- return to the top folder, resolve any relative paths or symbolic links to an absolute path.repo sync --force-sync
- perform the actual update.
repo
- call the repo
application to perform the synchronization.sync
- command to actually synchronize.--force-sync
- ignore any local changes while updating. This overwrites any edits you might have made to the projects’ sources. All projects are checked for updates at their origins (mostly on GitHub). If available, these updates are downloaded and integrated into the local repositories.grep -o -P '(?<=PLATFORM_SECURITY_PATCH := ).*' ...
- extract the security patch level of the source code.
grep
- utility to search a string inside other text(-files).-o
- option to only return the matched characters, not the whole line.-P
- option to enable Perl compatible regular expressions.(?<=PLATFORM_SECURITY_PATCH := ).*
- regular expression to extract the current patch level.
(?<=...)
- look for the characters between (
and )
, but don’t consider them as part of the output match.PLATFORM_SECURITY_PATCH :=
- literal text to find the line containing the current patch level..*
- regular expression to match any character (.
) zero or more times (*
) until the end of the line.If the new patch level is equal to the one found under “Bump Security String to…” on the LineageOS changelog, start the actual build:
LANG=C brunch y550 2>&1 | tee $( date +'%Y-%m-%d_%H-%M-%S' )-build.log
I’ll explain each component of this command:
LANG=C
sets the locale of the following command to a generic one. I needed this because of a mid-build crash of a component called flex
.brunch
is a shell function being included from the vendor/cm/build/envsetup.sh
script.y550
is the build target of our device.2>&1
redirects all error output (file descriptor 2
) to standard output (file descriptor 1
). This way, we get ALL output instead of only the ‘normal’ output.|
- sends the output of the previous command to the next.tee
- call the programm tee
which not only sends its input to standard output (the terminal), but also writes it to the given file.$( date +'%Y-%m-%d_%H-%M-%S' )-build.log
- open a subshell and call the date
utility, which returns the current date and time in the specified format. Effectively, this creates a unique filename for each build.Note: On my machine, I have to make as much free RAM as possible for the build to succeed. I have to log out of my graphical desktop and switch to the text console (Ctrl+Alt+F4). After the build, I switch back to the graphical login console (Ctrl+Alt+F1).
If you want, you can sign the build with your PGP key so others can verify it has come from you and has not been tampered with. Remember to enter your build date in the ZIP
-filename. Use tab-completion to help you out:
cd ~/android/lineage/out/target/product/y550;
ZIPFILE="lineage-14.1-20210608-UNOFFICIAL-y550.zip";
mv "${ZIPFILE}.md5sum" "${ZIPFILE}.md5";
gpg --armor --detach-sign --output "${ZIPFILE}.md5.asc" "${ZIPFILE}.md5"
To verify your signature, use this command:
gpg --verify "${ZIPFILE}.md5.asc" "${ZIPFILE}.md5"
Final step is uploading the ZIP
, MD5
and ASC
files to a filehoster, and post the update on the XDA forum.
git
is a version control system. By using it, you keep track of all changes to a file. You can always go back and look at a previous version. Most open source projects use git as their base system. It allows you to have your own copy of all source files along with their histories. Git projects (repositories or repos for short) can be linked. This way you can include files from another project and keep them up to date automagically. Android and LineageOS make heavy use of this feature.
cherry
is the codename for the Huawei Honor 4/4X (CHE1 series w/- Qualcomm Snapdragon soc only) - Unified. This device is officially supported by the LineageOS developers. The Y550 uses very similar hardware, so the Honor 4/4X CHE1 is the perfect ‘sponsor’ to base a Y550 custom ROM on. Almost all of the cherry
-instructions apply to the Y550, as well.
TeamWin Recovery Project or TWRP is a custom recovery for Android devices. It is basically a mini operating system that exists alongside the original or custom ROM to facilitate flashing ROMs and mods, and recovery of OS when needed. Think of it as a dual-boot system. By booting to this custom recovery ‘OS’, you can partition your device, flash custom ROMs and much more. For the Huawei Y550 there is a specific image download.