Friday, 14 February 2020

Android(AOSP) System Service in Details

Hi Guys!!! Hope All is well.
Today i am going to discuss Android(AOSP) System Service in details. I have written many post on Android framework But this part was left. 

What is service ?
As per Android Developer docs
https://developer.android.com/guide/components/services 

  • A Service is an application component that can perform long-running operations in the background and does not provide a user interface.
  • Another application component can start a service and it will continue to run in the background even if the user switches to another application.
  • Additionally, a component can bind to a service to interact with it and even perform interprocess communication (IPC).
  • For example, a service might handle network transactions, play music, perform file I/O, or interact with a content provider, all from the background.
Service Facts Vs. Myth
Most confusion about the Service class actually revolves around what it is not:

  • A Service is not a separate process.
  • The Service object itself does not imply it is running in its own process; unless otherwise specified,
  • By default it runs in the same process as the application it is part of.
  • A Service is not a thread. It is not a means to do work off of the main thread (to avoid Application Not Responding errors).
For more detail go the Android developer docs.
https://developer.android.com/guide/components/services
Now coming to main Point Android System service

Android system services
Functionality exposed by application framework APIs to communicates with system services to access the underlying hardware. There are two groups of services (Generic and Multimedia)

  • system services such as window manager and notification manager and
  • media System services involved in playing and recording media.
These are the services that provide application interfaces as part of the Android framework.
Besides these services, there are also native services supporting these system services, such as

  • SurfaceFlinger
  • netd
  • logcatd
  • rild and
  • so on.
Many of them are very similar to Linux daemons that you may find in a Linux distribution
AOSP System Service Architecture


To create a custom system service in android following steps are required

  1. Create service in the framework
  2. Register service in SystemServer
  3. Create an .aidl interface of the service in the framework
  4. Register .aidl interface in the build system
  5. Create a manager for the service in the framework
  6. Register the service manager in ContextImpl
  7. Register name of service manager in Context (abstract class)
After performing the above steps we need to build the new SDK for using the features of service through the service manager.
1. Create service in the framework
First We need to create a service in below directory /frameworks/base/services/java/com/android/server/
where other system services are placed.
example code:
/*MySystemService.java */
2. Register service in SystemServer
We need to register our service in /frameworks/base/services/java/com/android/server/SystemServer.java
where other system services are registered. Below is the method
private void startOtherServices() {}

try {
    Slog.i(TAG, "Starting MySystemService");
    ServiceManager.addService("my", new MySystemService(context));
    Slog.i(TAG, "MySystemService Started");
    } catch (Throwable e) {
    Slog.e(TAG, "Failure starting MySystemService Service", e);
  }
3. Create an .aidl interface of the service in the framework 
A system service can expose a set of functions that can be accessed by other process/application,by exposing them in .aidl file.
To expose the functions of our MySystemService we need to declare them in .aidl file in any
existing directory or any new directory in the framework
So we need to create IMyService.aidl in directory
/frameworks/base/core/java/android/os/ 
/* IMySystemService */

/*
* aidl file :
* frameworks/base/core/java/android/os/IMySystemService.aidl
* This file contains definitions of functions which are
* exposed by service.
*/
package android.os;
/**{@hide}*/
interface IMySystemService {
    void setData(int val);
}
4. Register .aidl interface in the build system
We need to register our service’s aidl interface in frameworks/base/Android.mk
Note: here we don’t have to add the entry of any aidl files for parcelables
if we use any in our IMyService.aidl.
/* Android.mk */

/*
* open frameworks/base/Android.mk and add line in red 
 * color mentioned below which contains the location of
 * our .aidl file.
*/
…
    core/java/android/os/IPowerManager.aidl \
    core/java/android/os/IMyService.aidl \
    core/java/android/os/IRemoteCallback.aidl \
    …
5. Create a manager for the service in the framework
 To provide single instance of our service manager we need to register our service manager in /frameworks/base/core/java/android/app/ContextImpl.java and so to optimized and simple we will see with singleton. Below is the sample code for a Singleton manager class:


Now, 3rd party apps can call getMyService().setData(); method.
6. Register the service manager in ContextImpl
Now applications will be able to get the instance of our service manager with the MyProxy.getMyProxy(),
But to make it a singleton class we need to register it in ContextImpl so that applications can get an instance of service manger like Context.getSystemService(“service_name”);
so we need to write following code in /frameworks/base/core/java/android/app/ContextImpl.java file in the static block:


/**
 * In /frameworks/base/core/java/android/app/ContextImpl.java
 * inside the static block we need to register our SystemService
 */
registerService(MY_SERVICE , new SystemService() {
public Object createService(ContextImpl ctx) {
    return MyProxy.getMyProxy();
/**
 * Or we can create new object of it, if MyProxy is not a singleton class.
 * see other registered Services for example.
 */
}});

7. Register name of our service manager in Context (abstract class)
Now we need to add the entry of MY_SERVICE as a constant in file
/** inside /frameworks/base/core/java/android/content/Context.java. */
/**
 * Use with {@link #getSystemService} to retrieve a
 * {@link android.os.MyProxy} for using MyService
 *
 * @see #getSystemService
 * @hide
 */
public static final String MY_SERVICE = "mySystemService";
After all the above steps we just need to build our custom image(build AOSP code)
to get our system service working like other system service.
To use this system service We have to use Android System App. 
If we want to distribute this SystemService just like other Android System service We have to build
SDK and then share this SDK to other third party developer just like Google do.
we can use the service manager in applications like:
MyProxy dm= (MyProxy) getApplicatioContext().getSystemService(Context.MY_SERVICE);
Thanks
Saurabh Sharma
Happy Coding !!!

2 comments:

  1. I tried your tutorial. It's working. But what if I want to access to FilesDir in SystemService.
    with context.getFilesDir() it does return me null.

    ReplyDelete
  2. Can anyone share working files as mentioned above, as I am getting various issues from Android.mk and context file

    ReplyDelete

Build a Custom Kernel Module for Android

Hi Guys!!!Hope you are doing well !!!. Today I will describe how you can write a custom kernel module(Hello world) for Android and load it a...