【问题标题】:Can't exchange data between Android phone and Arduino with NFC module, using HCE使用 HCE 无法在带有 NFC 模块的 Android 手机和 Arduino 之间交换数据
【发布时间】:2014-03-25 18:28:31
【问题描述】:

拜托,我需要任何帮助来解决我的问题。 我无法使用 HCE 在 Android (4.4.2) 手机和带有 NFC 模块的 Arduino 之间正常交换数据。
我以 Android 示例为例,稍作更改以仅返回 IMEI 号码。

public byte[] processCommandApdu(byte[] commandApdu, Bundle extras) {
    if (Arrays.equals(SELECT_APDU, commandApdu)) {
        String data = ((TelephonyManager)getSystemService(Context.TELEPHONY_SERVICE)).getDeviceId();
        return ConcatArrays(data.getBytes(), SELECT_OK_SW);
    } else {
        return UNKNOWN_CMD_SW;
    }
}

在 Arduino 方面,我的代码是:

void loop(){
    Serial.println("Waiting for an ISO14443A card");
    uint8_t success;

    success = nfc.inListPassiveTarget();
    if(success){
        Serial.println("Found something!");      
        uint8_t responseLength = 32;
        uint8_t response[32];
        uint8_t selectApdu[] = { 
             0x00, /* CLA */
             0xA4, /* INS */
             0x04, /* P1  */
             0x00, /* P2  */
             0x05, /* Length of AID  */
             0xF2, 0x22, 0x022, 0x22, 0x22, /* AID */
             0x00  /* Le  */};

        success = nfc.inDataExchange(selectApdu, sizeof(selectApdu), response, &responseLength);
        Serial.print("EX_RES:");
        Serial.println(success);

        if(success) {
            Serial.print("responseLength: "); 
            Serial.println(responseLength);
            for(int i=0; i<responseLength; i++){
                Serial.print(response[i]);
                Serial.print(", ");
            }
            Serial.println();
            Serial.println("========================");
        }
        else {
            Serial.println("Failed sending SELECT AID"); 
        }
    }
    else {
        Serial.println("Didn't find anything!");
    }

    delay(1000);
}

最初,我收到“发送 SELECT AID 失败”,所以我试图找出原因。所以我在 PN532.cpp 文件中更新了 inDataExchange 的代码。所以现在看起来像这样:

// initially function was returning bool
uint8_t PN532::inDataExchange(uint8_t *send, uint8_t sendLength, uint8_t *response, uint8_t *responseLength){

uint8_t i;
pn532_packetbuffer[0] = 0x40; // PN532_COMMAND_INDATAEXCHANGE;
pn532_packetbuffer[1] = inListedTag;

if (HAL(writeCommand)(pn532_packetbuffer, 2, send, sendLength)) {
    return 2; // initially was false
}

int16_t status = HAL(readResponse)(response, *responseLength, 1000);
if (status < 0) {
    return 3;  // initially was false
}

if ((response[0] & 0x3f) != 0) {
    DMSG("Status code indicates an error\n");
    return 4;  // initially was false
}

uint8_t length = status;
length -= 1;

if (length > *responseLength) {
    length = *responseLength; // silent truncation...
}

for (uint8_t i = 0; i < length; i++) {
    response[i] = response[i + 1];
}
*responseLength = length;

return 5;  // initially was true
}

现在,我收到了这样的日志输出:

等待 ISO14443A 卡 发现了一些东西! EX_RES:5 响应长度1:18 35, 51, 53, 55, 50, 52, 54, 48, 53, 52, 49, 57, 50, 55, 49, 57, 144, 0, ========================= 等待 ISO14443A 卡 发现了一些东西! EX_RES:4 响应长度1:32 11, 51, 53, 55, 50, 52, 54, 48, 53, 52, 49, 57, 50, 55, 49, 57, 144, 0, 0, 36, 0, 0, 3, 5, 17, 2, 117, 0, 194, 1, 6, 7, ========================= 等待 ISO14443A 卡 发现了一些东西! EX_RES:4 响应长度1:32 1, 51, 53, 55, 50, 52, 54, 48, 53, 52, 49, 57, 50, 55, 49, 57, 144, 0, 0, 36, 0, 0, 3, 5, 17, 2, 117, 0, 194, 1, 6, 7, ========================= 等待 ISO14443A 卡 发现了一些东西! EX_RES:4 响应长度1:32 11, 51, 53, 55, 50, 52, 54, 48, 53, 52, 49, 57, 50, 55, 49, 57, 144, 0, 0, 36, 0, 0, 3, 5, 17, 2, 117, 0, 254, 0, 0, 0, =========================

我知道这个结果是不正确的,并且值是不变的缓冲区(因为错误),除了第一个数字,它会不时变化。
有时我会收到这样奇怪的日志:

EX_RES:4 响应长度:18 11, 219, 13, 51, 8, 187, 181, 0, 2, 54, 1, 1, 2, 140, 0, 7, 72, 1, EX_RES:4 响应长度:18 1, 72, 1, 2, 37, 0, 4, 228, 4, 160, 4, 168, 7, 236, 2, 138, 50, 0,

有什么问题?也许有人遇到过这个问题?也许图书馆有问题,或者我做错了什么?
我正在使用:

【问题讨论】:

  • 代码和日志输出不匹配(例如,您发布的代码中没有使用 EX_RES2 和 responseLength2)。请更新问题以包含匹配的代码/日志输出。
  • 我还是不相信你给出的日志输出是来自上面的代码。特别是在第三步中,response 缓冲区的第一个字节再次神奇地变为35。实际上,如果 inDataExchange 返回错误代码 3,则该字节将保持为 11(如果数组分配在与前一轮相同的内存上)或者整个响应缓冲区将包含随机垃圾(如果数组像以前一样分配在不同的内存区域上)。
  • 如果没有看到您实际在做什么(实际代码/实际输出),这很难说。
  • 现在我真的更新了,写了新的日志输出。另外,arduino论坛的一个人告诉我手动设置responseLength,所以我做了,现在我看不到错误3,不知道它是否相关:)
  • 你的项目是开源的吗?

标签: android arduino nfc apdu hce


【解决方案1】:

我终于让它工作了。首先想说问题的出现是因为我对Android编程的无能(我完全是新手)。

  1. responseLength 必须手动设置,理想情况下,必须等于响应缓冲区大小(感谢 arduino 论坛的 Traveller99)

  2. 如果屏幕关闭,HCE 将无法工作(这是有趣的部分 :))

    当前的 Android 实现会在设备屏幕关闭时完全关闭 NFC 控制器和应用处理器。因此,当屏幕关闭时,HCE 服务将不起作用。但是,HCE 服务可以在锁定屏幕上运行。

感谢Michael 的帮助!

【讨论】:

  • 供以后遇到此问题的人参考。我只是遇到了同样的问题,但是 responseLength 还不够我必须添加它 1 我的意思是responseLength + 1 因为我通过 SPI 与我的 PN532 模块进行通信,我的猜测是因为 SPI COM 使用全双工它需要 + 1帧来获取最后一个字节。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2023-01-19
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-03-30
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多