Google is committed to advancing racial equity for Black communities. See how.

AIDL Overview

The Android Interface Definition Language (AIDL) is a tool that lets users abstract away IPC communication. Given an interface (specified in a .aidl file), various build systems use the aidl binary to construct C++ or Java bindings so that this interface can be used across processes, regardless of the runtime or bitness there.

AIDL can be used between any process in Android: between platform components or between apps. However, it is never used as an API for apps. AIDL may be used to implement an SDK API in the platform, for instance, but the SDK API surface never contains AIDL APIs directly. For documentation about how to use AIDL between apps directly, see corresponding Android developers documentation. When AIDL is used between platform components that are updated separately, such as APEXes (starting in Android 10) or HALs (starting in Android R), the versioning system known as Stable AIDL must be used.


Here is an example AIDL interface:

    package my.package;

    import my.package.Baz; // defined elsewhere

    interface IFoo {
        void doFoo(Baz baz); // synchronous method
        oneway void doFoo(int a); // async method

Android 10 and higher support parcelable declarations. For example:

    package my.package;

    import my.package.Boo;

    parcelable Baz {
        @utf8InCpp String name = "baz";
        Boo boo;

Android R and higher support enum declarations. For example:

    package my.package;

    enum Boo {
        A = 1 * 4,
        B = 3,

A server process registers an interface and serves calls to it, and a client process makes calls to those interfaces. In many cases, a process acts as both a client and a server since it may be referencing multiple interfaces. For more details about the various runtimes available to use these interfaces, see AIDL backends. These type declarations are exactly like a class declaration in a given language, but they work across processes.

How it works

AIDL uses the binder kernel driver to make calls. When you make a call, a method identifier and all of the objects are packed onto a buffer and copied to a remote process where a binder thread waits to read the data. Once a binder thread receives data for a transaction, the thread looks up a native stub object in the local process, and this class unpacks the data and makes a call on a local interface object. This local interface object is the one a server process creates and registers. When calls are made in the same process and the same backend, no proxy objects exist, and so calls are direct without any packing or unpacking.

Interacting with services on the device

Android comes with a few commands to allow interacting with services on the device. Try:

    adb shell dumpsys --help # listing and dumping services
    adb shell service --help # sending commands to services for testing