Android Health实现

原文:https://source.android.com/devices/tech/health/implementation

healthd的所有代码都已重构为health@2.0-impllibhealthservice,然后修改HAL实现为health@2.0。这两个库通过health@2.0-service静态链接,使其能够完成之前healthd的工作(如运行healthd_mainloop和执行轮询)。在初始化时,health@2.0-serviceIHealth的接口实现注册到hwservicemanager。使用Android 8.x vendor镜像和Android 9 Framework升级设备时,vendor镜像可能不提供health@2.0服务。这是由弃用计划强制执行的 。

要解决此问题:

  1. healthd注册IHealthhwservicemanager(尽管是一个系统守护进程)。IHealth添加到系统manifest中,实例名为“backup”。
  2. Framework和storaged通过hwbinder(而不是binder)与healthd进行通信。
  3. Framework代码和storaged更改为获取“default”实例(如果可用),然后“backup”。
    • C++端代码使用定义在libhealthhalutils中的逻辑。
    • Java端代码使用定义在HealthServiceWrapper中的逻辑。
  4. IHealth/default广泛可用且Android 8.1 vendor镜像被弃用之后,IHealth/backuphealthd才被弃用。有关更多详细信息,请参阅弃用health@1.0

healthd的特定板构建变量

BOARD_PERIODIC_CHORES_INTERVAL_*是用于构建 healthd的特定板的变量。作为system/vendor构建拆分的一部分,无法为系统模块定义特定板的值 。在health@2.0中,供应商可以覆盖healthd_mode_ops->init中这两个值(通过删除依赖于health@2.0-service.<device>libhealthservice 并重新实现此功能)。

静态实现库

与其他HAL实现库不同,health@2.0-impl实现库是一个静态库,其中包含health@2.0-service, charger, recovery和遗留的healthd链接。

如上所述health@2.0.impl实现IHealth,旨在包装libbatterymonitorlibhealthd.BOARD。这些health@2.0-impl的用户不得直接使用BatteryMonitorlibhealthd中的功能 ; 相反,应该由实现IHealth接口的Health类调用。为进一步概括,healthd_common代码也包含在health@2.0-impl中。new 的healthd_common包含health@2.0-service, chargerhealthd之间的其余的公共代码,并且取代BatteryMonitor调用IHealth方法。

Health2.0服务实现

为设备实现health@2.0服务时,如果默认实现为:

  • 设备充足,直接使用android.hardware.health@2.0-service
  • 对于设备来说还不够,创建 android.hardware.health@2.0-service.(device)可执行文件并包含:
#include <health2/service.h>
int main() { return health_service_main(); }

然后:

  • 如果 libhealthd特定板:
    • 存在,链接到它。
    • 不存在,提供healthd_board_inithealthd_board_battery_update函数的空实现。
  • 如果特定板的BOARD_PERIODIC_CHORES_INTERVAL_*变量:
    • 已定义,创建特定设备HealthServiceCommon.cpp(复制自hardware/interfaces/health/2.0/utils/libhealthservice)并在healthd_mode_service_2_0_init中客制化。
    • 未定义,静态链接到libhealthservice
  • 如果设备:
    • 需要实现getStorageInfogetDiskStatsAPI,则在get_storage_infoget_disk_stats函数中提供实现。
    • 不用实现这些API,则静态链接到libstoragehealthdefault
  • 更新必要的SELinux权限。

有关详细信息,请参阅 hardware/interfaces/health/2.0/README.md

Health客户端

health@2.0有以下客户端:

  • chargerlibbatterymonitor和和healthd_common代码的用法包含在health@2.0-impl中。

  • recoverylibbatterymonitor的链接包含在health@2.0-impl中。所有BatteryMonitor的调用都被Health实现类的调用所取代 。

  • BatteryManagerBatteryManager.queryProperty(int id)是唯一的一个IBatteryPropertiesRegistrar.getProperty的客户端,其由 healthd提供并直接读/sys/class/power_supply

    出于安全考虑,应用不允许直接调用Health HAL。在Android 9中,binder服务 IBatteryPropertiesRegistrar是由BatteryService提供而不是 healthd,并且BatteryService委派通过Health的HAL调用来检索所请求的信息。

  • BatteryService。在Android 9中,BatteryService 通过HealthServiceWrapper来确定要使用的Health服务实例(来自vender的“default”实例或来自healthd的“backup”实例)。然后通过IHealth.registerCallback监听取Health事件。

  • Storaged。在Android 9中,storaged通过 libhealthhalutils来确定要使用的Health服务实例(来自vender的“default”实例或来自healthd的“backup”实例)。然后通过IHealth.registerCallback来监听Health事件并检索存储信息。

SELinux变化

新的health@2.0 HAL中SELinux的改动如下:

  • 添加health@2.0-servicefile_contexts
  • 允许system_serverstoraged使用hal_health
  • 允许system_serverBatteryService)注册 batteryproperties_serviceIBatteryPropertiesRegistrar)。
  • 允许healthd提供hal_health
  • 移除允许system_server/storaged通过binder调用healthd的规则。
  • 移除允许healthd注册batteryproperties_service(IBatteryPropertiesRegistrar)的规则。

对于有自己实现的设备,某些供应商的SELinux改动可能是有必要的。例如:

# device/<manufacturer>/<device>/sepolicy/vendor/file_contexts
/vendor/bin/hw/android\.hardware\.health@2\.0-service.<device> u:object_r:hal_health_default_exec:s0

# device/<manufacturer>/<device>/sepolicy/vendor/hal_health_default.te
# Add device specific permissions to hal_health_default domain, especially
# if it links to board-specific libhealthd or implements storage APIs.

Kernel接口

healthd守护进程和 android.hardware.health@2.0-service的默认实现访问以下Kernel接口来获取电池信息:

  • /sys/class/power_supply/*/capacity
  • /sys/class/power_supply/*/charge_counter
  • /sys/class/power_supply/*/charge_full
  • /sys/class/power_supply/*/current_avg
  • /sys/class/power_supply/*/current_max
  • /sys/class/power_supply/*/current_now
  • /sys/class/power_supply/*/cycle_count
  • /sys/class/power_supply/*/health
  • /sys/class/power_supply/*/online
  • /sys/class/power_supply/*/present
  • /sys/class/power_supply/*/status
  • /sys/class/power_supply/*/technology
  • /sys/class/power_supply/*/temp
  • /sys/class/power_supply/*/type
  • /sys/class/power_supply/*/voltage_max
  • /sys/class/power_supply/*/voltage_now

否则任何特定设备的Health HAL实现都会默认使用libbatterymonitor访问这些内核接口,除非在healthd_board_init(struct healthd_config*)中被重写。

如果这些文件缺失,或者healthd或默认服务从无法访问(如:文件是特定供应商文件夹的符号链接,由于SELinux的策略配置错误而拒绝访问),它们可能无法正常运行。因此,即使使用默认实现,也可能需要进行其他特定供应商的SELinux更改。

测试

Android 9包含专为health@2.0 HAL编写的新VTS测试。如果设备声明在设备manifest中提供health@2.0 HAL,则必须通过相应的VTS测试。default实例(确保设备正确实现HAL)和backup实例(确保healthd 在删除之前继续正常运行)两者都要编写测试。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • 1 Android Treble HAL 为了更好的了解Treble 架构里面的HAL,首先了解一下Android...
    做机人阅读 23,862评论 4 9
  • mean to add the formatted="false" attribute?.[ 46% 47325/...
    ProZoom阅读 2,723评论 0 3
  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 134,904评论 18 139
  • 01 俗话说,大难不死,必有后福。后福没见到,但是接下来的一年多,倒是平平静静。相安无事,就是万福了。 妻子带着女...
    晚来舟阅读 1,026评论 20 22
  • “有些东西你注视它越久,你就会越来越陌生,这座城市,这条街道,街道上来来往往的人,你身边熟悉的人,你的亲人,甚至是...
    丫是老段阅读 378评论 0 1