我有一个旧的NFC阅读器,用于tikitag服务(该服务后来改名为触地,并最终在2012年左右被放弃)。由于该网站不再可用,我再也找不到原来的tikitag/touchatag驱动程序。经过一些搜索,我发现这个NFC阅读器是一个通用的ACS ACR122U读取器,并安装了一个来自这里的合适的驱动程序。我的系统是Windows 7(64位).
首先,我尝试了NFC工具库对NFC标记的高级读写访问。我说遇到了一个不受支持的标记时出错了;尽管阅读器上没有标记,甚至在附近也没有标记。似乎其他开发人员在这个库中也遇到了同样的错误,如这里所示。注意,这个标记是无限检测的(所以,它不会在被检测到一次之后就消失了)。
我将所需的低级别代码复制到一个单独的类中(即独立于NFC工具库)。您可以在下面找到此代码(类似的代码也可以在教程中找到):
import java.util.List;
import javax.smartcardio.Card;
import javax.smartcardio.CardTerminal;
import javax.smartcardio.TerminalFactory;
import org.nfctools.utils.NfcUtils;
public class NdefTest {
public static void main(String[] args) throws Exception {
TerminalFactory factory = TerminalFactory.getDefault();
List<CardTerminal> terminals = factory.terminals().list();
CardTerminal terminal = terminals.get(0);
if (terminal.waitForCardPresent(5000)) {
Card card = terminal.connect("T=0");
System.out.println(NfcUtils.convertBinToASCII(card.getATR().getHistoricalBytes()));
}
}
}此代码检测与使用NFC工具库时完全相同的“幻影”标记。因此,这个问题似乎与NFC工具库无关(正如库开发人员在响应错误报告时所暗示的那样)。要么我遗漏了什么,要么这个问题要么与安装的驱动程序、NFC读取器硬件有关,要么与javax.smartcardio中的一些未修复的错误有关(按可能的顺序列出)。
我试着卸载前面提到的驱动程序,让Windows 7自己安装一个合适的驱动程序(称为"Microsoft Usbccid (WUDF)"),这会导致与上面描述的相同的错误。我没有试过其他的读者,因为我只有一个。
(注意:在Windows设备概述中,这个NFC读取器的名称是“”,而不是"ACS ACR122“或其他相关的东西。不知道这是否重要,我只是想提一下。)
有没有人遇到过这个问题,并设法解决了?
更新
好的,在检测到模拟标记之后,我尝试向读取器发送一个CLF命令;即获取连接的PICC的ATS (ACR122U手册第11页):
TerminalFactory factory = TerminalFactory.getDefault();
List<CardTerminal> terminals = factory.terminals().list();
// (this is the correct terminal)
CardTerminal terminal = terminals.get(0);
if (terminal.waitForCardPresent(5000)) {
Card card = terminal.connect("*");
CardChannel channel = card.getBasicChannel();
// (I tried both 0x00 and 0x01 as P1, as well as 0x05 for Le)
CommandAPDU getAts = new CommandAPDU(0xFF, 0xCA, 0x00, 0x00, 0x04);
ResponseAPDU response = channel.transmit(getAts);
System.out.println(response.getSW1());
System.out.println(response.getSW2());
}但是我一直得到一个错误响应代码(0x630x00)。对我可能做错了什么有什么想法吗?
发布于 2013-10-05 19:51:18
您遇到的问题是,这个版本的ACR122U读取器以某种非标准的方式使用PC/SC (CCID)。
您用PC/SC API检测到的“卡”实际上要么是读取器模拟的虚拟卡(允许PC/SC API打开连接,即使没有卡),要么是读取器SAM插槽中的智能卡芯片(读取器外壳中的联系人卡)。
在任何一种情况下,此读取器只使用PC/SC作为本机命令的传输协议,用于此读取器中使用的非接触式前端芯片(NXP PN532)。因此,如果要使用读取器的非接触式功能,则必须使用CLF的本机命令集。有关详细信息,请参阅ACR122U API文档或libnfc实现。
发布于 2013-10-09 09:42:28
(所有的功劳都归功于迈克尔·罗兰,这篇文章的意思是作为一个解决方案摘要)
好的,Michael,给出最后一个注释中的例子,我终于理解了使用PC/SC协议来隧道CLF命令是什么意思。我测试了PN532文档中的一些命令,它们返回有效的结果。(但是,您作为示例提供的命令不起作用,导致读取器崩溃;必须重置它。)
例如,要获得固件版本:
CommandAPDU commApdu = new CommandAPDU(0xFF, 0x00, 0x00, 0x00,
new byte[] { (byte)0xD4, (byte)0x02 });InDataExchange命令:
CommandAPDU commApdu = new CommandAPDU(0xFF, 0x00, 0x00, 0x00,
new byte[] { (byte)0xD4, (byte)0x40, 0x01 });我找到了NFCIP库,它支持使用InDataExchange命令在对等点之间发送字节数组(例如ACS ACR122和nokia6131)。在阅读PN532文档(第131页)时,该命令似乎也允许读取标记。迈克尔,你知不知道有哪个库用读取(不同类型的)标记来处理这些低级命令。
https://stackoverflow.com/questions/19199875
复制相似问题