Android NFC框架的NfcService与hal层代码概览

Android NFC框架的NfcService与hal层代码概览

Android 平台中,NFC系统模块运行在"com.android.nfc"进程中,该进程对应的应用程序文件为NfcNci.apk,源码路径为 packages/apps/Nfc,依赖的关键库有

  • libnfc_nci_jni.so, 源码路径为packages/apps/Nfc/nci/jni;
  • libnfc-nci.so, 源码路径为system/nfc。

hal层服务运行在"android.hardware.nfc@1.2-service"进程中, 源码路径为vendor/nxp/nfc,但hal层服务不同厂商实现有不同进程名和源码路径,具体看NFC芯片实现方案,这边只是个例子。

本文主要探究一下NfcService与hal层交互的主要代码。

NfcService与hal层之间各层代码的关系如图所示:

制图不易,欢迎点赞

NfcService与NativeNfcManage

NfcService 和 NativeNfcManager 在 Android NFC 框架中分别处于Java服务层和JNI native层,它们之间的关系如下:

层级关系与职责分工
NfcService
  • 运行在 Android Framework 的 Java 层,是整个 NFC 服务的核心,负责管理 NFC 的生命周期、系统事件、策略、权限、广播、AIDL 接口等。
  • 直接面向系统服务、应用层(如 NfcAdapter)、系统设置等,处理用户操作、系统广播、策略决策等高层逻辑。
  • 通过 DeviceHost 接口与底层交互。
NativeNfcManager
  • 运行在 JNI native 层,实现了 DeviceHost 接口,负责将 Java 层的 NFC 操作请求通过 JNI 调用转发到底层 C/C++(如 libnfc-nci中的NfcAdaptation和nfa_api)。
  • 负责底层 NFC 硬件的初始化、发现、数据收发、Tag/P2P/卡模拟等具体操作。
  • 负责将底层事件通过回调通知 Java 层。
交互流程
  • NfcService 持有一个 DeviceHost 类型的成员变量,实际赋值为 NativeNfcManager 实例。
  • 当 Java 层(如系统服务、应用)调用 NFC 相关 API(如 enable/disable、读写 Tag、P2P、卡模拟等)时,NfcService 负责高层逻辑和权限校验,然后调用 DeviceHost(即 NativeNfcManager)的相关方法。
  • NativeNfcManager 通过 JNI 调用 native C/C++ 层的实现(libnfc_nci_jni.so中NativeNfcManager.cpp的nfcManager_initNativeStruc(), nfcManager_doInitialize(),nfcManager_sendRawFrame()等),完成实际的 NFC 硬件操作。
  • 当底层有事件(如 Tag 发现、P2P 连接、卡模拟事件等)时,NativeNfcManager 通过回调接口{notifyRfFieldDeactivated(), notifyNdefMessageListeners()...}通知 NfcService,由 NfcService 进一步分发到系统或应用。

libnfc-nci.so

libnfc-nci.so对上层提供了NfcAdaptation和nfa_api接口。

NfcAdaptation

NfcAdaptation 在 Android NFC 系统中扮演着"适配层"的角色。它的主要作用是作为 NFC HAL(硬件抽象层)与更高层 NFC 栈之间的桥梁,负责管理、初始化、配置和控制底层 NFC 硬件服务。下面详细说明其核心作用:

  1. HAL 适配与多版本支持
  • NfcAdaptation 负责适配不同版本的 NFC HAL(如 HIDL 1.0/1.1/1.2 以及 AIDL 版本)。
  • 它会自动检测和选择可用的 HAL 实现,并为上层提供统一的接口调用方式(HalOpen, HalWrite(), HalCoreInitialized()...)。
  1. 生命周期管理
  • 提供初始化(Initialize)、反初始化(Finalize)、工厂重置(FactoryReset)、设备关机(DeviceShutdown)等方法,管理 NFC 服务的生命周期。
  • 负责在服务死亡(如 HAL 进程崩溃)时进行清理和重置(如 HalAidlBinderDiedImpl)。
  1. 配置与参数下发
  • 负责从配置文件(如 NfcConfig)读取参数,并下发到 HAL 或 NFC 控制器。
  • 支持厂商定制参数、白名单、协议配置等。
  1. 事件与数据回调适配 实现了 HAL 到上层的事件和数据回调适配(如 INfcClientCallback、INfcAidlClientCallback),将底层事件转换为上层可识别的事件。
nfa_api

nfa_api是 Broadcom/Android NFC 应用层(NFA, NFC application layer)的对外接口。 定义在system/nfc/src/nfa/include/nfa_api.h。这些接口是上层应用/服务与底层 NFC 控制器(NFCC)之间的桥梁。其主要功能 API如下:

初始化与关闭

  • NFA_Init:初始化 NFA 控制块,传入 HAL 入口表。
  • NFA_Enable/NFA_Disable:启用/关闭 NFC 功能。

配置与参数管理

  • NFA_SetConfig/NFA_GetConfig:设置/获取 NFCC 配置参数。

RF 控制与发现

  • NFA_EnablePolling/NFA_DisablePolling:启用/禁用轮询。
  • NFA_EnableListening/NFA_DisableListening:启用/禁用监听。
  • NFA_StartRfDiscovery/NFA_StopRfDiscovery:开始/停止射频发现。
  • NFA_Select/NFA_Deactivate:选择/去激活发现到的设备。

数据通信

  • NFA_SendRawFrame:发送原始数据帧。

NDEF 相关

  • NFA_RegisterNDefTypeHandler/NFA_DeregisterNDefTypeHandler:注册/注销 NDEF 类型处理器。
  • NFA_RegisterNDefUriHandler:注册 URI 类型的 NDEF 处理器。

厂商扩展

  • NFA_SendVsCommand/NFA_SendRawVsCommand:发送厂商自定义命令。

其它功能

  • 电源管理、P2P、卡模拟、HCI 配置等。

nfa_api.h还定义了大量用于事件回调的数据结构(如 tNFA_ACTIVATED、tNFA_DISC_RESULT、tNFA_NDEF_DETECT 等),便于上层应用获取详细事件信息。

hal层实现nfc_hal_service

INfc

INfc的hal层有多种版本的实现: HIDL 1.0/1.1/1.2 以及 AIDL,接口有 open() coreInitialized() write() ...

  • open() 先读取NFC芯片配置文件,如libnfc-nxp.conf:
ini 复制代码
###############################################################################
# Nfc Device Node name
NXP_NFC_DEV_NODE="/dev/pn544"

###############################################################################
# Extension for Mifare reader enable
MIFARE_READER_ENABLE=0x01

###############################################################################
# Vendor Specific Proprietary Protocol & Discovery Configuration
# Set to 0xFF if unsupported
#  byte[0] NCI_PROTOCOL_18092_ACTIVE
#  byte[1] NCI_PROTOCOL_B_PRIME
#  byte[2] NCI_PROTOCOL_DUAL
#  byte[3] NCI_PROTOCOL_15693
#  byte[4] NCI_PROTOCOL_KOVIO
#  byte[5] NCI_PROTOCOL_MIFARE
#  byte[6] NCI_DISCOVERY_TYPE_POLL_KOVIO
#  byte[7] NCI_DISCOVERY_TYPE_POLL_B_PRIME
#  byte[8] NCI_DISCOVERY_TYPE_LISTEN_B_PRIME
NFA_PROPRIETARY_CFG={05, FF, FF, 06, 81, 80, 70, FF, FF}

NXP_NFC_DEV_NODE定义了NFC芯片的驱动节点,这里"/dev/pn544"是一个i2c的节点,open()流程中会打开这个节点,用后续跟NFC芯片的通信。 open()流程不仅打开芯片设备节点,还初始化了各种数据、事件收发线程,用于处理应用层,和芯片的命令、数据。

  • coreInitialized() 对NFC芯片做初始化。

  • write() 往NFC芯片下发命令或数据。

INfcClientCallback

INfcClientCallback是回调接口,用于向上层发送事件(sendEvent())和发送NFC芯片上传的数据(sendData())。 其中向上层发送的事件有:

复制代码
HAL_NFC_OPEN_CPLT_EVT
HAL_NFC_CLOSE_CPLT_EVT
HAL_NFC_POST_INIT_CPLT_EVT
HAL_NFC_PRE_DISCOVER_CPLT_EVT
HAL_NFC_REQUEST_CONTROL_EVT
HAL_NFC_RELEASE_CONTROL_EVT
HAL_NFC_ERROR_EVT
HAL_HCI_NETWORK_RESET
相关推荐
消失的旧时光-194312 分钟前
Android 接入 Flutter(Add-to-App)最小闭环:10 分钟跑起第一个混合页面
android·flutter
城东米粉儿27 分钟前
android StrictMode 笔记
android
Zender Han30 分钟前
Flutter Android 启动页 & App 图标替换(不使用任何插件的完整实践)
android·flutter·ios
童无极42 分钟前
Android 弹幕君APP开发实战01
android
赛恩斯1 小时前
kotlin 为什么可以在没有kotlin 环境的安卓系统上运行的
android·开发语言·kotlin
于山巅相见1 小时前
【3588】Android动态隐藏导航栏
android·导航栏·状态栏·android11
乡野码圣1 小时前
【RK3588 Android12】开发效率提升技巧
android·嵌入式硬件
eybk1 小时前
Beeware生成安卓apk取得系统tts语音朗读例子
android
zhangphil2 小时前
Android图像显示,CPU的Skia与GPU的Vulkan高性能渲染系统
android