Muchos dispositivos con Android que ofrecen la función de NFC ya admiten la emulación de tarjetas NFC. En la mayoría de los casos, el dispositivo tiene un chip separado llamado Elemento seguro que emula la tarjeta. Muchas de las tarjetas SIM que brindan los proveedores de servicios inalámbricos también contienen un Elemento seguro.
Android 4.4 y versiones posteriores proporcionan un método adicional de emulación de tarjetas que no involucra un Elemento seguro, que se llama emulación de tarjetas basada en host. Esto permite que cualquier aplicación para Android emule una tarjeta y se comunique directamente con el lector de NFC. En este tema, se describe cómo funciona la emulación de tarjetas basada en el host (HCE) en Android y cómo usar esta técnica para desarrollar una app que emule una tarjeta NFC.
Emulación de tarjetas con un Elemento seguro
Cuando la emulación de tarjetas NFC se realiza a través de un Elemento seguro, los datos de la tarjeta que se emulará se almacenan en el Elemento seguro del dispositivo mediante una aplicación para Android. Luego, cuando el usuario acerca el dispositivo a una terminal NFC, el controlador de NFC del dispositivo enruta todos los datos del lector directamente al Elemento seguro. En la figura 1, se ilustra este concepto:
El Elemento seguro se comunica con la terminal NFC sin que intervenga ninguna aplicación para Android en la transacción. Una vez completada la transacción, la app puede enviar una consulta directamente al Elemento seguro para conocer el estado de la transacción y comunicárselo al usuario.
Emulación de tarjetas basada en el host
Cuando se emula una tarjeta NFC mediante la emulación basada en el host, los datos se enrutan directamente a la CPU del host en lugar de a un elemento seguro. En la figura 2, se ilustra cómo funciona la emulación de tarjetas basada en el host:
Tarjetas y protocolos NFC compatibles
Los estándares de NFC ofrecen compatibilidad con muchos protocolos diferentes, y se pueden emular varios tipos de tarjetas.
Android 4.4 y versiones posteriores admiten varios protocolos que son comunes en el mercado actual. Muchas tarjetas que usan la tecnología sin contacto ya se basan en estos protocolos, como las tarjetas de pago sin contacto. Los protocolos también son compatibles con diferentes lectores de NFC del mercado actual, incluidos los dispositivos con NFC de Android que funcionan como lectores (consulta la clase IsoDep
). De esa forma, puedes crear e implementar una solución NFC de principio a fin en torno a HCE utilizando solo dispositivos con Android.
En particular, Android 4.4 y versiones posteriores admiten la emulación de tarjetas que se basan en la especificación ISO-DEP de NFC Forum (basada en ISO/IEC 14443-4) y procesar unidades de datos de protocolo de aplicación (APDU) definidas en la especificación ISO/IEC 7816-4. Android exige la emulación de ISO-DEP solo por encima de la tecnología Nfc-A (ISO/IEC 14443-3 tipo A). La compatibilidad con la tecnología NFC-B (ISO/IEC 14443-4 tipo B) es opcional. En la figura 3, se ilustra la superposición de todas estas especificaciones.
Servicios de HCE
La arquitectura de HCE en Android se basa en los componentes Service
de Android (conocidos como servicios de HCE). Una de las principales ventajas de un servicio es que se puede ejecutar en segundo plano sin una interfaz de usuario. Este es un comportamiento natural para muchas aplicaciones de HCE, como las de tarjetas de transporte público o de lealtad. En esos casos, el usuario no debería abrir la app para usarla. En su lugar, cuando se presiona el dispositivo contra el lector de NFC, se inicia el servicio correcto si aún no está en ejecución y se ejecuta la transacción en segundo plano. Por supuesto, puedes iniciar IU adicionales (como notificaciones para el usuario) desde tu servicio cuando corresponda.
Selección de servicios
Cuando el usuario toca un dispositivo con un lector de NFC, el sistema Android necesita saber con qué servicio de HCE desea comunicarse el lector de NFC. La especificación ISO/IEC 7816-4 define una forma de seleccionar aplicaciones centrada en un ID de aplicación (AID). Un AID consta de hasta 16 bytes. Si estás emulando tarjetas para una infraestructura de lector de NFC ya existente, los AID que buscan esos lectores, a menudo, son conocidos y están registrados de manera pública (por ejemplo, los AID de redes de pagos como Visa y MasterCard).
Si quieres implementar una nueva infraestructura de lector para tu aplicación, debes registrar tus propios AID. El procedimiento de registro de los AID se define en la especificación ISO/IEC 7816-5. Recomendamos registrar un AID según 7816-5 si vas a implementar una aplicación de HCE para Android, ya que evita las colisiones con otras apps.
Grupos de AID
En algunos casos, es posible que un servicio de HCE deba registrar varios AID y establecerse como el controlador predeterminado de todos los AID para implementar una aplicación determinada. No se admiten algunos AID del grupo que se dirigen a otro servicio.
Una lista de AIDs que se mantienen juntos se denomina grupo de AID. Android garantiza una de las siguientes opciones a todos los AID de un grupo:
- Todos los AID del grupo se enrutan a este servicio de HCE.
- No se enruta ningún AID del grupo a este servicio de HCE (por ejemplo, porque el usuario prefirió otro servicio que también solicitó uno o más AID de tu grupo).
En otras palabras, no existe un estado intermedio en el que los AID del grupo se puedan distribuir a diferentes servicios de HCE.
Grupos y categorías de AID
Puedes asociar cada grupo de AID con una categoría. Esto permite que Android agrupe los servicios de HCE por categoría y, por consiguiente, que el usuario establezca valores predeterminados en el nivel de categoría en lugar de en el nivel del AID. Evita mencionar los AIDs en cualquier sector de tu aplicación que vea el usuario promedio, ya que no representan nada para ellos.
Android 4.4 y versiones posteriores admiten dos categorías:
CATEGORY_PAYMENT
(que cubre las apps de pagos estándares de la industria)CATEGORY_OTHER
(para todas las demás apps de HCE)
Cómo implementar un servicio de HCE
Para emular una tarjeta NFC mediante la emulación de tarjetas basada en host, debes crear un componente Service
que maneje las transacciones con NFC.
Cómo comprobar la compatibilidad con HCE
Tu aplicación puede verificar si un dispositivo es compatible con HCE si comprueba la función FEATURE_NFC_HOST_CARD_EMULATION
. Usa la etiqueta <uses-feature>
en el manifiesto de la aplicación para declarar que usa la función HCE y si la necesita o no para funcionar.
Implementación del servicio
Android 4.4 y versiones posteriores proporcionan una clase Service
de conveniencia que puedes usar como base para implementar un servicio de HCE: la clase HostApduService
.
El primer paso es extender HostApduService
, como se muestra en la siguiente muestra de código:
Kotlin
class MyHostApduService : HostApduService() { override fun processCommandApdu(commandApdu: ByteArray, extras: Bundle?): ByteArray { ... } override fun onDeactivated(reason: Int) { ... } }
Java
public class MyHostApduService extends HostApduService { @Override public byte[] processCommandApdu(byte[] apdu, Bundle extras) { ... } @Override public void onDeactivated(int reason) { ... } }
HostApduService
declara dos métodos abstractos que debes anular e implementar. Se llama a uno de ellos, processCommandApdu()
, cada vez que un lector de NFC envía una unidad de datos del protocolo de aplicación (APDU) a tu servicio. Las APDU se definen en la especificación ISO/IEC 7816-4. Son los paquetes de nivel de aplicación que se intercambian entre el lector de NFC y tu servicio de HCE. Ese protocolo de nivel de aplicación es de dúplex medio: el lector de NFC te envía una APDU de comando y espera a que envíes una APDU de respuesta.
Como ya se mencionó, Android usa el AID para determinar con qué servicio de HCE se quiere comunicar el lector. Por lo general, la primera APDU que envía un lector de NFC a tu dispositivo es una APDU SELECT AID
. Esta APDU contiene el AID con el que el lector se quiere comunicar. Android extrae ese AID de la APDU, lo resuelve en un servicio de HCE y luego reenvía esa APDU al servicio resuelto.
Puedes enviar una APDU de respuesta si muestras los bytes de la APDU de respuesta de processCommandApdu()
. Ten en cuenta que se llama a este método en el subproceso principal de tu aplicación, que no debes bloquear. Si no puedes calcular y mostrar una APDU de respuesta de inmediato, muestra un valor nulo. Luego, puedes realizar el trabajo necesario en otro subproceso y usar el método sendResponseApdu()
definido en la clase HostApduService
para enviar la respuesta cuando hayas terminado.
Android seguirá reenviando nuevas APDU del lector a tu servicio hasta que se dé una de estas dos situaciones:
- El lector de NFC envía otra APDU
SELECT AID
, que el SO resuelve en un servicio diferente. - Deja de funcionar el vínculo de NFC entre el lector de NFC y tu dispositivo.
En ambos casos, se llama a la implementación de onDeactivated()
de tu clase con un argumento en el que se indica qué sucedió.
Si estás trabajando con una infraestructura de lector existente, debes implementar el protocolo de nivel de aplicación que esperan los lectores en tu servicio de HCE.
Si vas a implementar una nueva infraestructura de lector que también controlas, puedes definir un protocolo y una secuencia de APDU propios. Intenta limitar la cantidad de APDU y el tamaño de los datos que se intercambiarán. De este modo, te asegurarás de que los usuarios solo tengan que mantener su dispositivo sobre el lector de NFC durante poco tiempo. Un límite superior razonable es de aproximadamente 1 KB de datos, una cantidad que, en general, se puede cambiar en 300 ms.
Declaración del servicio en el manifiesto y registro del AID
Debes declarar tu servicio en el manifiesto como de costumbre, pero también debes agregar algunos elementos adicionales a la declaración del servicio:
Para indicarle a la plataforma que es un servicio de HCE que implementa una interfaz
HostApduService
, agrega un filtro de intents para la acciónSERVICE_INTERFACE
a la declaración de tu servicio.Para indicarle a la plataforma qué grupos de AID solicita este servicio, incluye una etiqueta
SERVICE_META_DATA
<meta-data>
en la declaración del servicio que dirija a un recurso XML con información adicional sobre el servicio de HCE.Establece el atributo
android:exported
entrue
y solicita el permisoandroid.permission.BIND_NFC_SERVICE
en la declaración del servicio. El primero garantiza que las aplicaciones externas puedan vincularse al servicio. El segundo exige que solo las aplicaciones externas que tienen el permisoandroid.permission.BIND_NFC_SERVICE
puedan vincularse. Dado queandroid.permission.BIND_NFC_SERVICE
es un permiso del sistema, exige que solo el SO Android pueda vincularse a tu servicio.
El siguiente es un ejemplo de una declaración de manifiesto HostApduService
:
<service android:name=".MyHostApduService" android:exported="true" android:permission="android.permission.BIND_NFC_SERVICE"> <intent-filter> <action android:name="android.nfc.cardemulation.action.HOST_APDU_SERVICE"/> </intent-filter> <meta-data android:name="android.nfc.cardemulation.host_apdu_service" android:resource="@xml/apduservice"/> </service>
Esta etiqueta de metadatos dirige a un archivo apduservice.xml
. A continuación, se muestra un ejemplo de un archivo con una declaración de un solo grupo de AID que contiene dos AID de propiedad:
<host-apdu-service xmlns:android="http://schemas.android.com/apk/res/android" android:description="@string/servicedesc" android:requireDeviceUnlock="false"> <aid-group android:description="@string/aiddescription" android:category="other"> <aid-filter android:name="F0010203040506"/> <aid-filter android:name="F0394148148100"/> </aid-group> </host-apdu-service>
La etiqueta <host-apdu-service>
debe contener un atributo <android:description>
que incluya una descripción del servicio que sea sencilla y puedas mostrar en la IU de la app. Puedes usar el atributo requireDeviceUnlock
para especificar que el dispositivo está desbloqueado antes de invocar este servicio para controlar las APDU.
El <host-apdu-service>
debe contener una o más etiquetas <aid-group>
. Cada etiqueta <aid-group>
debe cumplir con lo siguiente:
- Debe incluir un atributo
android:description
que contenga una descripción del grupo de AID sencilla y adecuada para mostrarse en la IU. - Debe tener su atributo
android:category
establecido para indicar la categoría a la que pertenece el grupo de AID, como las constantes de cadenas definidas porCATEGORY_PAYMENT
oCATEGORY_OTHER
. - Contiene una o más etiquetas
<aid-filter>
, cada una de las cuales contiene un AID único. Especifica el AID en formato hexadecimal y asegúrate de que contenga un número par de caracteres.
Tu aplicación también debe tener el permiso NFC
para registrarse como servicio de HCE.
Resolución de conflictos de AID
Se pueden instalar varios componentes HostApduService
en un solo dispositivo y varios servicios pueden registrar el mismo AID. Android determina cuál servicio invocar mediante los siguientes pasos:
- Si la app de billetera predeterminada que seleccionó el usuario registró el AID, se invoca esa app.
- Si la app de billetera predeterminada no registró el AID, se invoca el servicio que lo registró.
- Si más de un servicio registró el AID, Android le pregunta al usuario qué servicio invocar.
Verifica si tu app es la app de billetera predeterminada
Las apps pueden verificar si son la app de billetera predeterminada pasando RoleManager.ROLE_WALLET
a RoleManager.isRoleHeld()
.
Si tu app no es la predeterminada, puedes solicitar el rol de billetera predeterminado pasando RoleManager.ROLE_WALLET
a RoleManager.createRequestRoleIntent()
.
Aplicaciones de billetera
Android considera como aplicaciones de billetera a los servicios de HCE que declararon un grupo de AID con la categoría de pago. Android 15 y versiones posteriores incluyen un rol predeterminado de la app de billetera que el usuario puede seleccionar. Para ello, debe navegar a Configuración > Apps > Apps predeterminadas. Esto define la aplicación de billetera predeterminada que se invocará cuando se presione una terminal de pago.
Recursos obligatorios para aplicaciones de billetera
Para ofrecer una experiencia del usuario más atractiva visualmente, las aplicaciones de billetera con HCE deben proporcionar un banner de servicio.
Android 13 y versiones posteriores
Para que se ajuste mejor a la lista de selección de pagos predeterminada en la IU de Configuración, ajusta el requisito del banner a un ícono cuadrado. Idealmente, debería ser idéntico al diseño del ícono del selector de la aplicación. Este ajuste crea más coherencia y un aspecto más ordenado.
Android 12 y versiones anteriores
Establece el tamaño del banner del servicio en 260 x 96 dp y, luego, agrega el atributo android:apduServiceBanner
a la etiqueta <host-apdu-service>
, que dirige al recurso de diseño, para establecer el tamaño del banner del servicio en tu archivo XML de metadatos. El siguiente es un ejemplo:
<host-apdu-service xmlns:android="http://schemas.android.com/apk/res/android" android:description="@string/servicedesc" android:requireDeviceUnlock="false" android:apduServiceBanner="@drawable/my_banner"> <aid-group android:description="@string/aiddescription" android:category="payment"> <aid-filter android:name="F0010203040506"/> <aid-filter android:name="F0394148148100"/> </aid-group> </host-apdu-service>
Modo de observación
Android 15 presenta la función Modo de observación. Cuando está habilitado, el modo de observación permite que el dispositivo observe los bucles de sondeo de NFC y envíe notificaciones sobre ellos a los componentes HostApduService
adecuados para que se preparen para interactuar con una terminal NFC determinada. Un HostApduService
puede poner el dispositivo en modo de observación pasando true
a setObserveModeEnabled()
.
Esto le indica a la pila de NFC que no permita transacciones de NFC y, en su lugar, observe pasivamente los bucles de sondeo.
Filtros de bucle de sondeo
Puedes registrar filtros de bucle de sondeo para un HostApduService
con cualquiera de los siguientes métodos:
registerPollingLoopFilterForService()
para los filtros que deben coincidir exactamente con una trama de sondeoregisterPollingLoopPatternFilterForService()
para los filtros que coinciden con una expresión regular en los fotogramas de sondeo.
Cuando un filtro de bucle de sondeo coincide con tramas de sondeo no estándar, la pila de NFC enruta esas tramas de sondeo al HostApduService
correspondiente llamando a su método processPollingFrames()
. Esto permite que el servicio tome los pasos necesarios para garantizar que el usuario esté listo para realizar transacciones y tenga la intención de hacerlo, por ejemplo, autenticarlo. Si un lector de NFC usa solo tramas estándar en su bucle de sondeo, la pila de NFC enruta esas tramas de sondeo al servicio en primer plano preferido si ese servicio está en primer plano o al titular de rol de billetera predeterminado de lo contrario.
Las notificaciones de marco de sondeo también incluyen una medición específica del proveedor de la intensidad del campo que puedes recuperar llamando a getVendorSpecificGain()
.
Los proveedores pueden proporcionar mediciones con su propia escala, siempre que se ajusten a un solo byte.
Responde a los bucles de sondeo y sale del modo de observación
Cuando el servicio esté listo para realizar transacciones, puede salir del modo de observación pasando false
a setObserveModeEnabled()
. Luego, la pila de NFC permitirá que las transacciones continúen.
Los componentes HostApduService
pueden indicar que se debe habilitar el modo de observación cuando son el servicio de pago preferido. Para ello, configura shouldDefaultToObserveMode
como true
en el manifiesto o llama a CardEmulation.setShouldDefaultToObserveModeForService()
.
Los componentes HostApduService
y OffHostApduService
también pueden indicar que los filtros de bucle de sondeo que coinciden con las tramas de bucle de sondeo recibidas deben inhabilitar automáticamente el modo de observación y permitir que las transacciones continúen configurando autoTransact
en true
en la declaración PollingLoopFilter
del manifiesto.
Pantalla apagada y comportamiento de pantalla de bloqueo
El comportamiento de los servicios de HCE varía según la versión de Android que se ejecute en el dispositivo.
Android 12 y versiones posteriores
En las apps que se orientan a Android 12 (nivel de API 31) y versiones posteriores, puedes habilitar los pagos mediante NFC sin que la pantalla del dispositivo esté encendida. Para ello, configura requireDeviceScreenOn
en false
.
Android 10 y versiones posteriores
Los dispositivos que ejecutan Android 10 (nivel de API 29) o versiones posteriores admiten NFC seguro. Mientras el NFC seguro está activado, todos los emuladores de tarjetas (aplicaciones de host y fuera del host) no están disponibles cuando la pantalla del dispositivo está apagada. Mientras el NFC seguro está desactivado, las aplicaciones fuera del host están disponibles cuando la pantalla del dispositivo está apagada. Puedes verificar la compatibilidad con NFC seguro con isSecureNfcSupported()
.
En dispositivos que ejecutan Android 10 y versiones posteriores, se aplica la misma funcionalidad para configurar android:requireDeviceUnlock
en true
que con dispositivos que ejecutan Android 9 y versiones anteriores, pero solo cuando la función Proteger NFC está desactivada. Es decir, si la función Proteger NFC está activada, los servicios de HCE no pueden funcionar desde la pantalla de bloqueo, independientemente de la configuración de android:requireDeviceUnlock
.
Android 9 y versiones anteriores
En dispositivos que ejecutan Android 9 (nivel de API 28) y versiones anteriores, el controlador de NFC y el procesador de la aplicación se apagan por completo cuando la pantalla del dispositivo está apagada. Por lo tanto, los servicios de HCE no funcionan cuando la pantalla está apagada.
Además, en Android 9 y versiones anteriores, los servicios de HCE pueden funcionar desde la pantalla de bloqueo.
Sin embargo, esto se controla mediante el atributo android:requireDeviceUnlock
de la etiqueta <host-apdu-service>
de tu servicio de HCE. De forma predeterminada, no es obligatorio desbloquear la pantalla y se invoca el servicio aun cuando el dispositivo esté bloqueado.
Si configuras el atributo android:requireDeviceUnlock
como true
para tu servicio de HCE, Android le solicita al usuario que desbloquee el dispositivo cuando suceda lo siguiente:
- el usuario presiona un lector de NFC.
- El lector de NFC selecciona un AID que se resuelve en tu servicio.
Después de desbloquear el dispositivo, Android muestra un diálogo para pedirle al usuario que vuelva a presionar para completar la transacción. Esto es necesario porque el usuario puede haber movido el dispositivo fuera del lector de NFC para desbloquearlo.
Coexistencia con tarjetas que tienen Elemento seguro
Esta sección es de interés para los desarrolladores que implementaron una aplicación que necesita un Elemento seguro para emular una tarjeta. La implementación de HCE de Android está diseñada para funcionar en paralelo con otros métodos de implementación de la emulación de tarjetas, incluido el uso de Elementos seguros.
Esta coexistencia se basa en un principio llamado enrutamiento AID. El controlador de NFC mantiene una tabla de enrutamiento que consiste en una lista (finita) de reglas de enrutamiento. Cada una de ellas contiene un AID y un destino. El destino puede ser la CPU del host, donde se ejecutan las apps para Android, o un elemento seguro conectado.
Cuando el lector de NFC envía una APDU con un SELECT AID
, el controlador de NFC la analiza y verifica si los AID coinciden con cualquier AID en su tabla de enrutamiento. Si coincide, esa APDU y todas las APDU siguientes se enviarán al destino asociado con el AID hasta que se reciba otra APDU SELECT AID
o se corte el vínculo con NFC.
En la figura 4, se ilustra esta arquitectura:
Por lo general, el controlador de NFC también contiene una ruta predeterminada para las APDU. Cuando no se encuentra un AID en la tabla de enrutamiento, se utiliza la ruta predeterminada. Si bien esta configuración puede variar en función del dispositivo, los dispositivos Android deben garantizar que los AID que registra tu app se enruten correctamente al host.
Las aplicaciones para Android que implementan un servicio de HCE o que usan un Elemento seguro no necesitan configurar la tabla de enrutamiento, ya que Android lo hace automáticamente. Android solo tiene que saber cuáles son los AID que pueden manejar los servicios de HCE y cuáles puede manejar el Elemento seguro. La tabla de enrutamiento se configura automáticamente en función de los servicios instalados y los que el usuario haya establecido como preferidos.
En la siguiente sección, se explica cómo declarar AID para aplicaciones que usan un elemento seguro en la emulación de tarjetas.
Registro de AID con Elementos seguros
Las aplicaciones que utilizan un Elemento seguro para emular tarjetas pueden declarar un servicio fuera del host en su manifiesto. La declaración de dicho servicio es casi idéntica a la de un servicio de HCE. Las excepciones son las siguientes:
- La acción que se usa en el filtro de intents debe establecerse en
SERVICE_INTERFACE
. - El atributo de nombre de los metadatos debe establecerse en
SERVICE_META_DATA
. El archivo XML de metadatos debe usar la etiqueta raíz
<offhost-apdu-service>
.<service android:name=".MyOffHostApduService" android:exported="true" android:permission="android.permission.BIND_NFC_SERVICE"> <intent-filter> <action android:name="android.nfc.cardemulation.action.OFF_HOST_APDU_SERVICE"/> </intent-filter> <meta-data android:name="android.nfc.cardemulation.off_host_apdu_service" android:resource="@xml/apduservice"/> </service>
El siguiente es un ejemplo del archivo apduservice.xml
correspondiente que registra dos AID:
<offhost-apdu-service xmlns:android="http://schemas.android.com/apk/res/android" android:description="@string/servicedesc"> <aid-group android:description="@string/subscription" android:category="other"> <aid-filter android:name="F0010203040506"/> <aid-filter android:name="F0394148148100"/> </aid-group> </offhost-apdu-service>
El atributo android:requireDeviceUnlock
no se aplica a los servicios fuera del host, ya que la CPU del host no participa en la transacción y, por lo tanto, no puede evitar que el Elemento seguro ejecute transacciones cuando el dispositivo está bloqueado.
El atributo android:apduServiceBanner
es obligatorio para los servicios fuera del host que son aplicaciones de pagos y para que se puedan seleccionar como una aplicación de pagos predeterminada.
Invocación de servicio fuera del host
Android nunca inicia un servicio que se declare como "fuera del host" ni se vincula con él, ya que el Elemento seguro es el que ejecuta las transacciones en sí, no el servicio de Android. La declaración del servicio solo permite que las aplicaciones registren los AID presentes en el Elemento seguro.
HCE y seguridad
La arquitectura de HCE proporciona un aspecto de seguridad básico: como tu servicio está protegido por el permiso del sistema BIND_NFC_SERVICE
, solo el SO puede vincularse y comunicarse con él.
Esto garantiza que cualquier APDU que recibas sea una APDU que recibió el SO desde el controlador de NFC y que cualquier APDU que envíes de vuelta solo vaya al SO, el cual, a su vez, reenviará directamente las APDU al controlador de NFC.
El último problema que queda es dónde obtienes los datos que envía tu app al lector de NFC. Esto se desacopla de forma intencional en el diseño de HCE: no le importa de dónde provienen los datos; solo se asegura de que se transporten de manera segura al controlador de NFC y al lector de NFC.
Para almacenar y recuperar de forma segura los datos que deseas enviar desde tu servicio de HCE, puedes, por ejemplo, utilizar la zona de pruebas de aplicaciones para Android, que aísla de otras apps los datos de tu app. Para obtener más detalles sobre la seguridad de Android, consulta el artículo Sugerencias de seguridad.
Parámetros y detalles del protocolo
Esta sección está orientada a los desarrolladores que desean comprender qué parámetros de protocolo utilizan los dispositivos con HCE durante las fases de anticolisión y activación de los protocolos de NFC. Esto permite construir una infraestructura de lector que sea compatible con los dispositivos Android con HCE.
Anticolisión y activación del protocolo Nfc-A (ISO/IEC 14443 tipo A)
Como parte de la activación del protocolo Nfc-A, se intercambian múltiples tramas.
En la primera parte del intercambio, el dispositivo con HCE presenta su UID; se debe suponer que los dispositivos con HCE tienen un UID aleatorio. Esto significa que, cada vez que el dispositivo toque el lector, el UID que se presente será un UID generado de forma aleatoria. Por tal motivo, los lectores de NFC no deben depender del UID de los dispositivos con HCE como una forma de autenticación o identificación.
Después, el lector de NFC puede seleccionar el dispositivo con HCE enviando un comando SEL_REQ
. La respuesta SEL_RES
del dispositivo con HCE tiene al menos el sexto bit (0x20) establecido, lo que indica que el dispositivo es compatible con ISO-DEP. Ten en cuenta que también se pueden establecer otros bits en SEL_RES
, lo que indica, por ejemplo, compatibilidad con el protocolo NFC-DEP (p2p). Debido a que se pueden establecer otros bits, los lectores que deseen interactuar con dispositivos con HCE deberán buscar explícitamente solo el sexto bit y no comparar el SEL_RES
completo con un valor de 0x20.
Activación de ISO-DEP
Después de activar el protocolo Nfc-A, el lector de NFC inicia la activación del protocolo ISO-DEP. Envía un comando RATS (solicitud de respuesta para seleccionar). El controlador NFC genera la respuesta RATS, la ATS, y los servicios de HCE no la pueden configurar. Sin embargo, las implementaciones de HCE deben cumplir con los requisitos de NFC Forum para la respuesta ATS, por lo que los lectores de NFC pueden contar con que estos parámetros se establezcan de acuerdo con lo que exige NFC Forum para cualquier dispositivo con HCE.
En la siguiente sección, se proporcionan más detalles sobre los bytes individuales de la respuesta ATS que brinda el controlador de NFC en un dispositivo con HCE:
- TL: Es la longitud de la respuesta ATS. No debe indicar una longitud superior a 20 bytes.
- T0: Los bits 5, 6 y 7 deben establecerse en todos los dispositivos con HCE, lo que indica que TA(1), TB(1) y TC(1) están incluidos en la respuesta ATS. Los bits 1 a 4 indican el FSCI, que codifica el tamaño máximo de trama. En los dispositivos con HCE, el valor del FSCI debe ser de entre 0 h y 8 h.
- T(A)1: Define las tasas de bits entre el lector y el emulador, y si pueden ser asimétricas. No hay garantías ni requisitos de tasas de bits para los dispositivos con HCE.
- T(B)1: Los bits 1 a 4 indican el número entero del tiempo de seguridad de la trama de inicio (SFGI). En dispositivos con HCE, el SFGI debe ser <= 8 h. Los bits 5 a 8 indican el número entero de tiempo de espera de la trama (FWI) y codifican el tiempo de espera de la trama (FWT). En dispositivos con HCE, el FWI debe ser <= 8 h.
- T(C)1: El bit 5 indica compatibilidad con las funciones avanzadas del protocolo. Los dispositivos con HCE pueden o no admitir estas funciones. El bit 2 indica compatibilidad con el DID. Los dispositivos con HCE pueden o no ser compatibles con el DID. El bit 1 indica compatibilidad con la NAD. Los dispositivos con HCE no deben admitir la NAD y deben establecer el bit 1 en cero.
- Bytes históricos: Los dispositivos con HCE pueden mostrar hasta 15 bytes históricos. Los lectores de NFC que deseen interactuar con los servicios de HCE no deben hacer suposiciones sobre el contenido de los bytes históricos ni sobre su presencia.
Ten en cuenta que muchos dispositivos con HCE tal vez cumplan con los requisitos de protocolo que las redes de pagos agrupadas en EMVCo definieron en la especificación de su protocolo de comunicación sin contacto. En particular:
- El FSCI en T0 debe ser de entre 2 h y 8 h.
- T(A)1 debe establecerse en 0x80, lo que indica que solo se admite la tasa de bits de 106 kbit/s, y las tasas de bits asimétricas entre el lector y el emulador no son compatibles.
- El FWI en T(B)1 debe ser <= 7 h.
Intercambio de datos de APDU
Como se indicó anteriormente, las implementaciones de HCE solo admiten un canal lógico único. Intentar seleccionar aplicaciones en diferentes canales lógicos no funciona en un dispositivo con HCE.