Android, Linux-ARM and TLS register emulation

If you are an Android integration/porting guy and you don’t know what TLS is or why you should care about it while porting Android on a new Linux Kernel, then you have just landed on the right page.

What is TLS or Thread Local Storage?

In a multi-threaded application, where all threads in a process share the same address space, there often arises the need to maintain data that is unique to a thread. Use of errno, in a C code, is a classic example of using this type of data which is local to a given thread. TLS or Thread Local Storage, as you can probably figure out from its name now, is a concept used for Threading abstraction. It is a fast and efficient way to store per-thread local data. Offset of thread’s local data is accessible via the TLS register(h/w or s/w block) which points to Thread Control Block of respective thread. Check this PDF for more information.

Yesteryears High end ARM cores viz. ARM9 and even some of ARM11 cores do not have this TLS Register physically available. Operating Systems (Linux from here onwards) need to emulate it in software. New generation ARM cores viz. Cortex-Ax onwards, however, do have this TLS register available (CP15).

Why do I being an Android porting/integration guy, need to care about all this?

Android(till Froyo? I guess) had this unique bug (or feature?) where in, it assumes that TLS register is emulated by the Kernel(Linux) and thus expect Linux to trap it. It worked well for ARM cores who were already emulating TLS register in software.

With the rise of ARM Cortex-Ax cores, people started reporting all sort of errors related to Android mounting or random Android service crashes. It turned out that the error was due to hard dependency of Android on TLS register emulation. Since Cortex-Ax devices do have TLS register available and Linux was not trapping it, that made Android really really mad.

By that time there was no known way to make Android user-space TLS register aware, people started patching Linux to make it compatible with the emulated TLS register. Here is the relevant TLS patch for 2.6.32 and patch for 2.6.37 ARM kernel.

With Gingerbread i.e. v2.3, Android introduced a build config variable ARCH_ARM_HAVE_TLS_REGISTER which (you need to set it to true during build time) will make Android user-space TLS register aware and you don’t need to patch your Linux anymore.

So now you know what else to look for if your Android port is crashing on an unsupported Kernel version.

P.S.
I’m yet to figure out what ARCH_ARM_HAVE_TLS_REGISTER ends up doing. A quick grep of this variable in AOSP came out with results in bionic/ and frameworks/base/opengl/ projects.

Contributed by :- Amit Pundir

One thought on “Android, Linux-ARM and TLS register emulation

  1. Ben Keane says:

    Thankyou soo much for this information!! Keep up the great work!

Leave a comment