Skip to content

Android Linux kernel additions

Google made some changes to the Linux kernel that haven't been mainstreamed. There was an attempt by placing some drivers on staging, but those were removed on 2.6.33 due to lack of maintainers.

I will use as an example the Android Linux port for Freescale's MX51, which at the time of this writing can be accessed from their public git repository, specifically the imx_2.6.35_10.10.01 branch.

 

The binder

Background

OpenBinder was introduces at BeOS, continued at PalmSource and parts of it open sourced into Linux. It's an attempt to introduce object oriented design to operating system design. OpenBinder provides object oriented representations for processes, shared memory, files etc.

It contains a Binder Shell as an example of VM for OpenBinder that lets you write Binder code in its particular language. It's a POSIX compatible shell (like bash) that sits on top of the Binder framework giving a much richer environment than you would get from a shell designed for traditional operating system services.

OpenBinder is similar to COM or CORBA, and it can be used to design graphics, user interface, and multimedia frameworks.

More background on this Introduction to OpenBinder

The original spec for the Linux port is here, although the current code is no longer compatible.

Configuration

ANDROID_BINDER_IPC

Files

drivers/staging/android/binder.c

drivers/staging/android/binder.h

 

ashmem – Android Shared Memory

Similar to POSIX shm, with different behavior and a simpler file-based API, it can be used to share memory between processes.

The advantage of ashmem over traditional Linux shared memory is that it provides a means for the kernel to reclaim these shared memory blocks if they are not currently in use.

If a process then tries to access a shared memory block the kernel has freed, it will receive an error, and will then need to reallocate the block and reload the data.

To use this, programs open /dev/ashmem, use mmap() on it, and can perform one or more of the following ioctls:

ASHMEM_SET_NAME

ASHMEM_GET_NAME

ASHMEM_SET_SIZE

ASHMEM_GET_SIZE

ASHMEM_SET_PROT_MASK

ASHMEM_GET_PROT_MASK

ASHMEM_PIN

ASHMEM_UNPIN

ASHMEM_GET_PIN_STATUS

ASHMEM_PURGE_ALL_CACHES

Ashmem has reference counting so that if many processes use the same area the area will not be removed until all processes has released it, the memory is also virtual and not physically contiguous. If physically contiguous memory is needed like for hardware reasons pmem (see below) can be used, but it has no reference counting.

To use ashmem to allocate a shared memory region:

int fd = ashmem_create_region("SharedRegionName", size); if(fd == 0) {

  data = mmap(NULL, size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);

  if(data != MAP_FAILED)

  {

    /* It works do your stuff*/

  }

}

The only way for another process to use this shared memory area is to use mmap with the same file descriptor (fd).

To share the file descriptor we can use the Binder introduced above, as explained here.

Configuration

ASHMEM

Files

include/linux/ashmem.h

mm/ashmem.c

 

pmem – Process Memory Allocator

Used to manage large (1-16+MB) physically contiguous regions of memory shared between userspace and kernel drivers (dsp, gpu,etc). It needs UID based statistics tracking exported to /proc/uid_stat.

Configuration

ANDROID_PMEM

UID_STAT

Files

drivers/misc/pmem.c

drivers/misc/uid_stat.c

include/linux/android_pmem.h

 

Logger – System Logging Facility

Adds three device nodes under /dev/log/, events, main and radio. The paths for open, read and write on these are optimized. A read will return one event or block if not opened in non blocking mode. Writing automatically saves pid, tgid and timestamp, with level, tag and message provided by the application.

Supported ioctls include:

LOGGER_GET_LOG_BUF_SIZE: returns the size of the entire log buffer

LOGGER_GET_LOG_LEN: returns the amount of data in the log

LOGGER_GET_NEXT_ENTRY_LEN: returns size of next log entry

LOGGER_FLUSH_LOG: clears the log of data

Android user space comes with a logcat application to read the log, either from the local filesystem or using adb logcat.

There is also a system property so that applications emit their stdout and/or stderr to the log.

Configuration

ANDROID_LOGGER

Files

drivers/staging/android/logger.c

drivers/staging/android/logger.h

 

Wake Locks

A wake lock prevents the kernel from getting into low power states. Wake locks can be held from both kernel and user space.

From kernel space:

#include <linux/wakelock.h>

wake_lock_init(struct wakelock *lock, int type, const char *name);

void wake_lock(struct wake_lock *lock);

void wake_unlock(struct wake_lock *lock);

void wake_lock_timeout(struct wake_lock *lock, long timeout);

void wake_lock_destroy(struct wake_lock *lock);

int wake_lock_active(struct wake_lock *lock);

long has_wake_lock(int type);

From user space:

echo "name" > /sys/power/wake_lock

echo "name" > /sys/power/wake_unlock

A wake lock can be of two types:

WAKE_LOCK_IDLE: The system will not enter idle mode, making the device more responsive.

WAKE_LOCK_SUSPEND: The system will not suspend.

cat /proc/wakelocks will list all waitlocks.

Configuration

WAKELOCK

WAKELOCK_STAT: Report wake lock stats in /proc/wakelocks

USER_WAKELOCK: User-space wake lock api.

Files

include/linux/wakelock.h

kernel/power/userwakelock.c

kernel/power/wakelock.c

 

Early suspend

Early suspend is an extension to the standard Linux power management stages. This is not suspending the device, but some of its components like LCD, touch sensor and maybe accelerometer. We could name "Late resume" the stage that resumes these devices. The kernel calls early suspend handlers when the user requested sleep state changes.

Configuration

EARLYSUSPEND

It can be configured in three modes:

NO_USER_SPACE_SCREEN_ACCESS_CONTROL

CONSOLE_EARLYSUSPEND: Register early suspend handler to perform a console switch to when user-space should stop drawing to the screen and a switch back when it should resume.

FB_EARLYSUSPEND: Register early suspend handler that notifies and waits for user-space through sysfs when user-space should stop drawing to the screen and notifies user-space when it should resume.

Files

include/linux/earlysuspend.h

kernel/power/consoleearlysuspend.c

kernel/power/fbearlysuspend.c

These patches were submitted to mainline and rejected. Some of the history.

 

OOM handling – The Android Out Of Memory killer

Kills processes as available memory becomes low.

The lowmemorykiller driver lets user-space specify a set of memory thresholds where processes with a range of oom_adj values will get killed. Specify the minimum oom_adj values in /sys/module/lowmemorykiller/parameters/adj and the number of free pages in /sys/module/lowmemorykiller/parameters/minfree. Both files take a comma separated list of numbers in ascending order.

For example, write "0,8" to /sys/module/lowmemorykiller/parameters/adj and "1024,4096" to /sys/module/lowmemorykiller/parameters/minfree to kill processes with a oom_adj value of 8 or higher when the free memory drops below 4096 pages and kill processes with a oom_adj value of 0 or higher when the free memory drops below 1024 pages.

The driver considers memory used for caches to be free, but if a large percentage of the cached memory is locked this can be very inaccurate and processes may not get killed until the normal oom killer is triggered.

In an Android system, init.rc initializes both adj and minfree. Processes can set their oom_adj to place them in the correct class for their current operation.

These oom_adj levels end up being based on the process lifecycle defined here.

Configuration

ANDROID_LOW_MEMORY_KILLER

Files

drivers/staging/android/lowmemorykiller.c

A handy article regarding the standard Linux OOM killer.

 

Android alarm

This is the kernel implementation to support Android's AlarmManager. It lets user space tell the kernel when it would like to wake up, allowing the kernel to schedule that appropriately and come back (holding a wake lock) when the time has expired regardless of the sleep state of the CPU.

Configuration

RTC_INTF_ALARM

Files

drivers/rtc/alarm.c

include/linux/android_alarm.h

 

Android paranoid network security

According to the Android security architecture, each application is given its own uid and gid at install time. Data files are kept under /data/data/<app-name>/…, and are read-writable only by that application process.

When Dalvik (actually, the 'zygote' process') loads an application, it changes to the uid and gid for the application, so that the process is running in the correct security context.

The paranoid network security mode restricts access to some networking features depending on the group of the calling process.

The list of groups that are allowed access to networking features are on the following list of #defines, GID and capability:

AID_NET_BT_ADMIN 3001 Can create an RFCOMM, SCO, or L2CAPP Bluetooth socket
AID_NET_BT 3002 Can create a Bluetooth socket
AID_INET 3003 Can create IPv4 or IPv6 socket
AID_NET_RAW 3004 Can create raw sockets.
AID_NET_ADMIN 3005 Allow CAP_NET_ADMIN permissions for process.

Configuration

None

Files

include/linux/android_aid.h

 

Android timed output/GPIO

This exposes a user space interface for timed GPIOs. It is used in the vibrator code.

Configuration

ANDROID_TIMED_GPIO

ANDROID_TIMED_OUTPUT

Files

drivers/staging/android/timed_gpio.c

drivers/staging/android/timed_gpio.h

drivers/staging/android/timed_output.c

drivers/staging/android/timed_output.h

 

Android RAM console

This allows saving the kernel printk messages to a buffer in RAM, so that after a kernel panic they can be viewed in the next kernel invocation, by accessing /proc/last_kmsg.

Configuration

ANDROID_RAM_CONSOLE: Android RAM buffer console

ANDROID_RAM_CONSOLE_ENABLE_VERBOSE: Enable verbose console messages on Android RAM console

ANDROID_RAM_CONSOLE_ERROR_CORRECTION: Android RAM Console Enable error correction

    ANDROID_RAM_CONSOLE_ERROR_CORRECTION_DATA_SIZE: Android RAM Console Data data size

    ANDROID_RAM_CONSOLE_ERROR_CORRECTION_ECC_SIZE: Android RAM Console ECC size

    ANDROID_RAM_CONSOLE_ERROR_CORRECTION_SYMBOL_SIZE: Android RAM Console Symbol size

    ANDROID_RAM_CONSOLE_ERROR_CORRECTION_POLYNOMIAL: Android RAM Console Polynomial

ANDROID_RAM_CONSOLE_EARLY_INIT: Start Android RAM console early

ANDROID_RAM_CONSOLE_EARLY_ADDR: Android RAM console virtual address

ANDROID_RAM_CONSOLE_EARLY_SIZE: Android RAM console buffer size

Files

drivers/staging/android/ram_console.c

 

Other Android differences

Goldfish

The Android emulator runs a virtual CPU that Google calls Goldfish. Goldfish executes ARM926T instructions and has hooks for input and output — such as reading key presses from or displaying video output in the emulator.

YAFFS2

Flash memory file system.YAFFS2 was already freely available for Linux. However, it is not part of the standard Linux kernel, and so Google added it to Android.

Bluetooth

These changes fix apparent bugs related to Bluetooth headsets, and add Bluetooth debugging and access control functions.

Scheduler

The Android kernel also contains slight changes to the CPU process scheduler and time-keeping algorithms. Why???

Android Debug Bridge

A protocol that runs over a USB link between a hardware device running Android and a developer writing applications on a desktop PC. 

 

Overview of changes

Finally, an overview of changes from Greg Kroah-Hartman's "Android: A Case Study of an Embedded Linux Project".

drivers:

  • dcc_tty – arm tty driver (2007)
  • reset key driver (2008)
  • gpio input drivers (2008)
  • timed gpio driver (2008)
  • synaptics i2c touchscreen driver (2007) (added multitouch in July 2009)
  • ledtrig-sleep debug driver (2008)
  • apanic debug flash driver (2009) writes panic info to flash to catch it later
  • kernel debugger core (2008)
  • pmem driver (2008)
  • uid status (2009) collects per-user network statistics through a proc file
  • Bluetooth TI wl127x rfkill power control via GPIO (2009)
  • Loads of MMC changes (SDIO support, "paranoid mode, new host driver)
  • nvidia Tegra MDT NAND controller (2008)
  • RTC Alarm driver (2008)
  • Logger (2008)
  • ram console (2008)
  • Switch subsystem? (2008)
  • GPIO switch (2008)
  • USB Gadget subsystem rewrite (2008)
  • tegra USB gadget driver (2010)
  • tegra framebuffer driver (2010)
  • bluetooth fixes and extensions (2009)
  • disable /dev/mem

Security model:

  • Binder (2007)
  • "secure" networking (2008)

filesystem:

  • YAFFS2
  • FAT Volume ID ioctl (2008)
  • no inotify event under some situations
  • Partition uevents (2009)
  • special proc file type

networking:

  • PPP on L2TP Access Controller (2009)
  • PPP on PPTP Network server (2009)
  • sysfs files for networking controls (2008)

core:

  • low memory killer (2008)
  • wakelocks (2008)
  • "early" suspend (2008)
  • ashmem (anonymous shared memory) (2008)
  • panic timeout
  • cgroup/cset changes (2009)
  • futex speedup due to broken userspace code (2009)
  • min_free_order_shift sysctl for swapless systems (2009)

 

References

Porting Android to a new device

Android Kernel Features 

Android kernel configuration

Post a Comment

Your email is never published nor shared. Required fields are marked *
*
*