车载之-自定义系统服务

news/2025/2/15 15:18:47/

源码梳理

  • SystemServer的启动,SystemServer是由Zygote启动的。
   /*** The main entry point from zygote.*/public static void main(String[] args) {new SystemServer().run();}
  • 继续看run()方法,看关键代码,开启服务。
    startBootstrapServices主要是针对底层相关的服务;
    startCoreServices主要针对用户相关的服务;
    startOtherServices主要针对应用相关的服务,而对于我们应用的开发,百分之99都是修改此方法。
  private void run() {
...// Start services.try {traceBeginAndSlog("StartServices");startBootstrapServices();startCoreServices();startOtherServices();SystemServerInitThreadPool.shutdown();} catch (Throwable ex) {Slog.e("System", "******************************************");Slog.e("System", "************ Failure starting system services", ex);throw ex;} finally {traceEnd();}...}
  • 我们关注一下服务 的启动形式,我们进入startBootstrapServices方法内,我们发现规律,基本上服务都是由mSystemServiceManager.startService这个方法启动的。
 // Wait for installd to finish starting up so that it has a chance to// create critical directories such as /data/user with the appropriate// permissions.  We need this to complete before we initialize other services.traceBeginAndSlog("StartInstaller");Installer installer = mSystemServiceManager.startService(Installer.class);traceEnd();// In some cases after launching an app we need to access device identifiers,// therefore register the device identifier policy before the activity manager.traceBeginAndSlog("DeviceIdentifiersPolicyService");mSystemServiceManager.startService(DeviceIdentifiersPolicyService.class);traceEnd();// Uri Grants Manager.traceBeginAndSlog("UriGrantsManagerService");mSystemServiceManager.startService(UriGrantsManagerService.Lifecycle.class);traceEnd();
  • 并且启动的所有服务都是集成自SystemService这个类,例如:Installer,DeviceIdentifiersPolicyService,UriGrantsManagerService.Lifecycle等,其可以监听系统的启动流程
    其对于我们比较重要的方法有,onStart与onBootPhase方法。
    onStart在启动时回;
    onBootPhase在启动过程中回调,其携带的参数时SystemService中的常量,比如PHASE_WAIT_FOR_DEFAULT_DISPLAY,PHASE_LOCK_SETTINGS_READY,PHASE_SYSTEM_SERVICES_READY等。
    收到PHASE_ACTIVITY_MANAGER_READY消息,就可以做发送广播等操作。
    收到PHASE_THIRD_PARTY_APPS_CAN_START消息,其表示其启动第三方引用。
    收到PHASE_BOOT_COMPLETED表示应用程序与用户可以进行交互了。
//com.android.server.SystemService/*** Called when the dependencies listed in the @Service class-annotation are available* and after the chosen start phase.* When this method returns, the service should be published.*/public abstract void onStart();/*** Called on each phase of the boot process. Phases before the service's start phase* (as defined in the @Service annotation) are never received.** @param phase The current boot phase.*/public void onBootPhase(int phase) {}
  • 还有设计比较巧妙的地方是,Java只支持单继承,而如果ActivityManagerService是需要进程间通讯的,需要集成Binder,这样就不能集成SystemService,所以其增加了内部类LifeCycle来创建ActivityManagerService,从而持有其实例。
    public static final class Lifecycle extends SystemService {private final ActivityManagerService mService;private static ActivityTaskManagerService sAtm;public Lifecycle(Context context) {super(context);mService = new ActivityManagerService(context, sAtm);}public static ActivityManagerService startService(SystemServiceManager ssm, ActivityTaskManagerService atm) {sAtm = atm;return ssm.startService(ActivityManagerService.Lifecycle.class).getService();}@Overridepublic void onStart() {mService.start();}@Overridepublic void onBootPhase(int phase) {mService.mBootPhase = phase;if (phase == PHASE_SYSTEM_SERVICES_READY) {mService.mBatteryStatsService.systemServicesReady();mService.mServices.systemServicesReady();} else if (phase == PHASE_ACTIVITY_MANAGER_READY) {mService.startBroadcastObservers();} else if (phase == PHASE_THIRD_PARTY_APPS_CAN_START) {mService.mPackageWatchdog.onPackagesReady();}}@Overridepublic void onCleanupUser(int userId) {mService.mBatteryStatsService.onCleanupUser(userId);}public ActivityManagerService getService() {return mService;}}
  • 服务创建后需要将服务注册到ServiceManager中,调用ServiceManager.addService()方法进行注册。
public void setSystemProcess() {try {ServiceManager.addService(Context.ACTIVITY_SERVICE, this, /* allowIsolated= */ true,DUMP_FLAG_PRIORITY_CRITICAL | DUMP_FLAG_PRIORITY_NORMAL | DUMP_FLAG_PROTO);ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats);ServiceManager.addService("meminfo", new MemBinder(this), /* allowIsolated= */ false,DUMP_FLAG_PRIORITY_HIGH);ServiceManager.addService("gfxinfo", new GraphicsBinder(this));ServiceManager.addService("dbinfo", new DbBinder(this));if (MONITOR_CPU_USAGE) {ServiceManager.addService("cpuinfo", new CpuBinder(this),/* allowIsolated= */ false, DUMP_FLAG_PRIORITY_CRITICAL);}ServiceManager.addService("permission", new PermissionController(this));ServiceManager.addService("processinfo", new ProcessInfoService(this));ApplicationInfo info = mContext.getPackageManager().getApplicationInfo("android", STOCK_PM_FLAGS | MATCH_SYSTEM_ONLY);mSystemThread.installSystemApplicationInfo(info, getClass().getClassLoader());synchronized (this) {ProcessRecord app = mProcessList.newProcessRecordLocked(info, info.processName,false,0,new HostingRecord("system"));app.setPersistent(true);app.pid = MY_PID;app.getWindowProcessController().setPid(MY_PID);app.maxAdj = ProcessList.SYSTEM_ADJ;app.makeActive(mSystemThread.getApplicationThread(), mProcessStats);mPidsSelfLocked.put(app);mProcessList.updateLruProcessLocked(app, false, null);updateOomAdjLocked(OomAdjuster.OOM_ADJ_REASON_NONE);}} catch (PackageManager.NameNotFoundException e) {throw new RuntimeException("Unable to find android system package", e);}// Start watching app ops after we and the package manager are up and running.mAppOpsService.startWatchingMode(AppOpsManager.OP_RUN_IN_BACKGROUND, null,new IAppOpsCallback.Stub() {@Override public void opChanged(int op, int uid, String packageName) {if (op == AppOpsManager.OP_RUN_IN_BACKGROUND && packageName != null) {if (mAppOpsService.checkOperation(op, uid, packageName)!= AppOpsManager.MODE_ALLOWED) {runInBackgroundDisabled(uid);}}}});}

实践

  • 创建AIDL接口
/frameworks/base/core/java/android/app/IToolManager.aidl
//android.app
interfadce IToolManager{String handler();
}
  • 服务端
//frameworks/base/services/core/java/com/android/server/tool/ToolManagerService.java
package com.android.server.tool;import android.app.IToolManager;
import android.os.RemoteException;/*** 服务端   AMS PMS WMS*/
public class ToolManagerService extends IToolManager.Stub {@Overridepublic String request(String msg) throws RemoteException {return "ToolManagerService接收数据:"+msg;}
  • 客户端
//frameworks/base/core/java/android/app/ToolManager.java
package android.app;import android.annotation.SystemService;
import android.compat.annotation.UnsupportedAppUsage;
import android.content.Context;
import android.os.IBinder;
import android.os.RemoteException;
import android.util.Singleton;
import android.os.ServiceManager;
import android.annotation.Nullable;/*** 客户端*/
@SystemService(Context.TOOL_SERVICE)
public class ToolManager {/*** @hide*/public ToolManager() {}/*** @hide*/public static IToolManager getServerice(){return I_TOOL_MANAGER_SINGLETON.get();}@UnsupportedAppUsageprivate static final Singleton<IToolManager> I_TOOL_MANAGER_SINGLETON =new Singleton<IToolManager>() {@Overrideprotected IToolManager create() {final IBinder b= ServiceManager.getService(Context.TOOL_SERVICE);final IToolManager im=IToolManager.Stub.asInterface(b);return im;}};@Nullablepublic String handle(@Nullable String msg){try{return getServerice().request(msg);}catch (RemoteException e){throw e.rethrowFromSystemServer();}}
}
  • 添加常量
/frameworks/base/core/java/android/context/Context.java
添加 public static final String TOOL_SERVICE = "tool";
  • 注册Binder
frameworks/base/services/java/com/android/server/SystemServer.java
//在startOtherServices方法中ServiceManager.addService(Context.TOOL_SERVICE,new ToolManagerService());

SystemServiceRegistry用于给客户端获取服务的类,有一个static块 执行了registerService用于注册.

frameworks/base/core/java/android/app/SystemServiceRegistry.javaregisterService(Context.TOOL_SERVICE, ToolManager.class,new CachedServiceFetcher<ToolManager>() {@Overridepublic ToolManager createService(ContextImpl ctx) {return new ToolManager();}});
  • 修改SeLinux安全权限
    system/sepolicy/prebuilts/api/32.0/private/
    与 system/sepolicy/private/ 目录下,
    分别修改以下三个文件
  1. service_contexts
    #配置自定义服务selinux角色
    chen u:object_r:tool_service:s0
    用户:角色:类型:安全级别

  2. service.te
    #配置自定义服务类型的权限
    type tool_service, app_api_service, ephemeral_app_api_service, system_server_service,
    service_manager_type;

  3. untrusted_app_all.te
    #允许所有app使用自定义服务
    allow untrusted_app_all tool_service:service_manager find;

  • 更新编译
  1. 更新api
    make update-api
  2. 编译
    m
  3. 运行模拟器
    emulator

http://www.ppmy.cn/news/42714.html

相关文章

Spring-Retry

Spring-Retry 引入Maven依赖 <dependency><groupId>org.springframework.retry</groupId><artifactId>spring-retry</artifactId></dependency><dependency><groupId>org.aspectj</groupId><artifactId>aspectjw…

技术+商业“双轮”驱动,量旋科技加速推进全方位的量子计算解决方案

【中国&#xff0c;深圳】4月14日&#xff0c;在第三个“世界量子日”&#xff0c;以“‘双轮’驱动 加速未来”为主题的量旋科技2023战略发布会在线上举办。 本次发布会&#xff0c;量旋科技全线升级了三大业务线产品&#xff1a;其中重点布局的超导量子计算体系产品&#xf…

优先级队列

目录 前言&#xff1a; 1、PriorityQueue的特性 .2 PriorityQueue常用接口介绍 Ⅰ、PriorityQueue常见的构造方法 Ⅱ、常用的方法 Ⅲ、PriorityQueue的扩容方式&#xff1a; 3、应用 前言&#xff1a; 普通的队列是一种先进先出的数据结构&#xff0c;元素在队列尾追加&…

Ajax简介、axios异步提交

一、Ajax简介 Ajax全称为&#xff1a;“Asynchronous JavaScript and XML”&#xff08;异步JavaScript 和 XML&#xff09; 使用ajax&#xff0c;可以无刷新状态更新页面&#xff0c;并且实现异步提交&#xff0c;提升了用户体验。Ajax其实质是利用浏览器提供的一个特殊的对象…

redis中的持久化操作AOF与RDB区别

通过阅读Redis官网&#xff1a; 持久性&#xff1a;是指将数据写入持久存储&#xff0c;例如固态磁盘 &#xff08;SSD&#xff09; 包括&#xff1a; RDB&#xff08;Redis数据库&#xff09;&#xff1a;RDB持久性按指定的时间间隔执行数据集的时间点快照AOF &#xff08;…

掌握这些“学习方法和工具”,让你事半功倍!

在中国这个高竞争的社会环境下&#xff0c;学习成为了每个人都需要掌握的技能。然而&#xff0c;学习并不仅仅是读书和听课&#xff0c;更是需要一系列高效的方法和习惯来提高效率。本文将介绍一些实用的学习经验和方法&#xff0c;以及推荐一些国内好的学习工具和平台&#xf…

Apollo配置中心使用篇

Apollo配置中心使用篇常见配置中心对比Apollo核心概念Apollo核心特性Apollo架构设计各模块介绍服务端设计客户端设计Apollo与Spring集成的底层原理Apollo安装安装apollo-portalconfig service和admin service部署多网卡问题解决修改Portal环境配置调整ApolloPortal配置Apollo权…

设备是如何实现延时关机的

文章目录1. 引言2. 延时关机的实现方式2.1 自建定时服务实现2.2 RocketMQ中间件实现2.2.1 生成端demo2.2.2 消费端demo3. 结尾1. 引言 在设备联动中&#xff0c;有些场景需要保持设备继续工作一段时间再关机。比如在厨房场景下&#xff0c;存在燃气灶和烟机的联动场景&#xf…