gpt4 book ai didi

java - 使用智能卡 IO 时无法检索第二张卡的 ATR

转载 作者:行者123 更新时间:2023-12-01 11:41:59 25 4
gpt4 key购买 nike

对于一些背景,我使用了 PN532 用户手册中指定的 In_List_Passive_Target 命令来检索终端字段中所有卡的 UID。我还使用 ACR122U 的伪命令 FF 00 00 00 04 将这些命令发送到 PN532。

>>  FF 00 00 00 04 D4 4A 01 00           # In_List_Passive_Target (1)
<< D5 4B 01 01 00 04 08 04 3E 58 A7 D1 # Response including UID (1)
>> FF 00 00 00 04 D4 4A 01 00 # In_List_Passive_Target (2)
<< D5 4B 01 01 00 04 08 04 9E 69 A7 D1 # Response including UID (2)
>> FF 00 00 00 04 D4 4A 01 00 # In_List_Passive_Target (3)
<< D5 4B 00 # No more cards in field (3)

既然我已经做到了这一点,我想一一选择这些。我可以通过在完成一张卡后暂停该卡 (In_Deselect),然后使用 In_List_Passive_Target 命令及其 UID 选择下一张卡。

但是,每次我选择一张卡时,我都想知道它返回的 ATR。事实证明,这对于 Java 智能卡 IO API 来说是很困难的,因为终端创建的卡对象始终是同一张卡(因此返回相同的 ATR),即使我断开该卡的连接然后创建一张新卡也是如此。考虑到如果我通过 PN532 终端命令 In_Data_Exchange 与卡通信,这很奇怪,它是正确的不同卡(不是通过卡对象访问的旧卡)。我需要 ATR 能够检测卡的类型(Mifare Classic、Desfire、Ultralight 等)

这是我为收集卡片而创建的函数:

public static void getCardsInField()
{
cardList = new ArrayList<AbstractCard>();
Boolean loop = true;

// Card already connected to the terminal
byte[] firstCardUID = transmitADPUCommand(GET_ADDRESS);
MifareClassic firstCard = new MifareClassic(cardChannel, firstCardUID);
cardList.add(firstCard);

System.out.println(firstCard);
System.out.println(readable(card.getATR().getBytes()));

while(loop)
{
byte[] inDeselectResponse = transmitADPUCommand(IN_DESELECT); // Deselect current card
byte[] inListPassiveTargetsResponse = transmitADPUCommand(IN_LIST_PASSIVE_TARGETS); // Select a new card

System.out.println(">> " + readable(IN_LIST_PASSIVE_TARGETS));
System.out.println("<< " + readable(inListPassiveTargetsResponse));

// Trying to create a new card object for new card
try
{
card.disconnect(true);
card = cardTerminal.connect("*");
cardChannel = card.getBasicChannel();
}
catch (CardException e)
{
e.printStackTrace();
}

if (Arrays.equals(inListPassiveTargetsResponse, IN_LIST_PASSIVE_TARGET_RESPONSE_NO_TARGETS)) // no more targets
{
loop = false;
}
else
{
byte[] loopCardUID = extractUID(inListPassiveTargetsResponse);
MifareClassic loopCard = new MifareClassic(cardChannel, loopCardUID);
cardList.add(loopCard);

System.out.println(loopCard);
System.out.println(readable(card.getATR().getBytes())); // this should be different ATR but it is the old cards atr
}
}
}

最佳答案

非接触式卡没有 ATR(重置应答)。 ATR 仅由接触卡生成(ISO/IEC 7816-3 响应重置引脚无效)。此外,PC/SC 模拟非接触式卡的 ATR(基于卡的某些参数),因为 PC/SC 主要是为接触式卡设计的,因此,PC/SC API 期望 ATR 可用。

非接触式卡还有其他值(value)。例如,基于 ISO/IEC 14443 A 类的卡具有 ATQA (SENS_RES)、SAK (SEL_RES)、UID (NFCID1),并且可能还具有 ATS(与 ATR 非常接近)。基于 ISO/IEC 14443 B 类的非接触式卡具有类似的值。

响应 InListPassiveTarget 命令,您将获得识别卡类型所需的所有信息:

Card 1: D5 4B 01 01 00 04 08 04 3E 58 A7 D1
Card 2: D5 4B 01 01 00 04 08 04 9E 69 A7 D1

对于卡 1,此数据解码为:

  • ATQA (SENS_RES) = 00 04
  • SAK (SEL_RES) = 08
  • UID (NFCID1) = 3E 58 A7 D1
  • ATS = 无

对于卡 2,此数据解码为:

  • ATQA (SENS_RES) = 00 04
  • SAK (SEL_RES) = 08
  • UID (NFCID1) = 9E 69 A7 D1
  • ATS = 无

因此,这两张卡的 ATQA = 00 04 和 SAK = 08,这意味着它们很可能是 MIFARE Classic 1K 或 MIFARE Plus。

参见MIFARE Type Identification Procedure查看用于识别 NXP 的 ISO/IEC 14443 A 类卡的完整值列表。

关于java - 使用智能卡 IO 时无法检索第二张卡的 ATR,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29450937/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com