简体   繁体   English

如何从RFID标签读取数据?

[英]How to read data from RFID tag?

I want to read data from NFCv tag, I tried this method but didn't get the data.我想从 NFCv 标签中读取数据,我尝试了这种方法但没有得到数据。 I search on internet but didn't find any clue to read data, I used another play store application that tell me that there are 128 blocks and each block is of 4 bytes, and total there are 512 bytes我在互联网上搜索但没有找到任何读取数据的线索,我使用了另一个播放商店应用程序,告诉我有 128 个块,每个块有 4 个字节,总共有 512 个字节

try {
                        int offset = 0;  // offset of first block to read
                        int blocks = 128;  // number of blocks to read
                        byte[] cmd = new byte[]{
                                (byte)0x60,                  // flags: addressed (= UID field present)
                                (byte)0x23,                  // command: READ MULTIPLE BLOCKS
                                (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,  // placeholder for tag UID
                                (byte)(offset & 0x0ff),      // first block number
                                (byte)((blocks - 1) & 0x0ff) // number of blocks (-1 as 0x00 means one block)
                        };

                        System.arraycopy(id, 0, cmd, 2, 8);
                        byte[] userdata = nfcvTag.transceive(cmd);

                        userdata = Arrays.copyOfRange(userdata, 0, 32);
                        tagData.setText("DATA:" + bytesToHex(userdata));

This is the raw string which recieve from NFCV tag这是从 NFCV 标签接收的原始字符串

303330363036422031343530323030383034ffff
ffffffffffffffffffffffff3333303030204120
2046542031353033203030303030393433ffffff
ffffffff32322f30312f323031352d2d31343136
3037ffffffffffffffffffffffffffff752a307c
20dd0aeaffffffffffffffff089cffffffffffff
ffffffffffffffff0000093dffffffffffffffff
ffffffff27130fb60af1ffffffffffffffffffff
8000ffffffffffffffffffffffffffff00fd7d74
ffffffffffffffffffffffff2dcf6030ab0ee1ad
2db36004aadbe17c089f121b20362a7e089d1217
202f2a75ffffffffffffffffffffffffffffffff
ffffffffffffffffffffffffffffffff30303032
3030303600ac9b5300000aca00ac9bb700ac9bc4
00000000fffffffc02dd02de02de02de02dd02dd
02dd02db0000861300000a9c00ac9bff00acb829
00acb82a00acb8330000020dffffffeb03a0039e
039c039d039a039a0397039600008ad300000a51
00002a0800acb83d000000000000000000000000
00009ed500000000000000000000000000007ef9
ffffffffffffffffffffffffffffffffffffffff
ffffffffffffffffffffffffffffffffffffffff
ffffffffffffffff0000391effffffffffffffff
ffffffffffffffffffffffffffffffffffffffff
ffffffffffffffffffffffffffffffffffffffff
ffffffff000136ce2e656e64

The Android NFC stack supports NfcV by default - therefore use class NfcV , which abstracts all of that - instead of dealing with byte[] , which you probably don't understand (else you wouldn't ask). Android NFC 堆栈默认支持 NfcV - 因此使用 class NfcV ,它抽象了所有这些 - 而不是处理byte[] ,你可能不明白(否则你不会问)。

bytesToHex() may be useful for logging, but to decode byte[] to String that's rather: bytesToHex()可能对日志记录有用,但要将byte[]解码为String ,那就是:

new String(bytes, StandardCharsets.UTF_8)

The NfcV Android class does not have have any high level access methods it only has transceive(byte[]) method therefore you are using the right method and have to deal with byte arrays. NfcV Android class 没有任何高级访问方法,它只有transceive(byte[])方法,因此您使用的是正确的方法并且必须处理字节 ZA3CBC3F9D0CE2F2C1554E1B671D71。

Note adding the make/model for the tag or link to it's datasheet would help understand how to correctly read the Tag.注意添加标签的品牌/型号或链接到它的数据表将有助于理解如何正确读取标签。

But you have not taken in to account the MaxTransceiveLength this might be smaller than the amount of data you are trying to read in one go.但是您没有考虑MaxTransceiveLength ,这可能小于您尝试在 go 中读取的数据量。

The datahsheet would also tell you the MaxTransceiveLength数据表还会告诉您 MaxTransceiveLength

I don't know the max value for this Tag / NfcV but for Cards I used the MaxTransceiveLength is 253 bytes so I guess you might be trying to read too many blocks in one go and the card is returning the maximum it can.我不知道这个标签/NfcV 的最大值,但对于我使用的卡,MaxTransceiveLength 是 253 字节,所以我猜你可能试图在一个 go 中读取太多块,并且卡正在返回它可以返回的最大值。

Therefore I use code like below for my NfcA tags with similar commands (FAST Read)因此,我对具有类似命令的 NfcA 标签使用如下代码(快速读取)
I cannot give an NfcV example as I don't have the datasheet to know the exact command format but for showing how to take in to account the MaxTransceiveLength this is not relevant.我无法给出 NfcV 示例,因为我没有数据表来了解确切的命令格式,但为了展示如何考虑 MaxTransceiveLength,这并不相关。
Update added Logging in a more understandable format更新以更易于理解的格式添加了日志记录

// Work out how big a fast read we can do (2 bytes for CRC)
int maxTranscieveBytes = mNfcA.getMaxTransceiveLength() - 2;

// Work out how many pages can be fast read
int maxTranscievePages = maxTranscieveBytes / 4;

// Work out how many pages I want to read
int numOfPages = endPage - startPage + 1

while (numOfPages > 0){
// Work out the number of pages to read this time around
      if (numOfPages > maxTranscievePages) {
         readPages = maxTranscievePages;
         // adjust numOfPages left
         numOfPages -= maxTranscievePages;
      } else {
         // Last read
         readPages = numOfPages;
         numOfPages = 0;
      }

      // We can read the right number of pages
      byte[] result = mNfcA.transceive(new byte[] {
             (byte)0x3A,  // FAST_READ
             (byte)(startPage & 0x0ff),
             (byte)((startPage + readPages - 1) & 0x0ff),
      });

      // Adjust startpage for the number of pages read for next time around
      startPage += readPages;

      // Do some result checking

      // Log the data in more understandable format (one block/page per line)
      for(int i = 0; i < (result.length / 4); i++){
          String pageData = new String(result, (i * 4), 4, 
               StandardCharsets.UTF_8 );
          Log.v("NFC", i + "=" + pageData);                  
      }

}

This is a solution which I come with, Reading each block successively and adding each within a string, and in the last I have complete value of hexadecimal and also UTF-8 String这是我提供的一个解决方案,依次读取每个块并将每个块添加到一个字符串中,最后我有完整的十六进制值和 UTF-8 字符串

if(NfcAdapter.ACTION_TAG_DISCOVERED.equals(action)
                || NfcAdapter.ACTION_TECH_DISCOVERED.equals(action))
        {
            currentTag = intent.getParcelableExtra(NfcAdapter.EXTRA_TAG);
            byte[] id = currentTag.getId();
            StringBuffer buf = new StringBuffer();

            tagId.setText(bytesToHex(id));

            for (String tech : currentTag.getTechList()) {

                if (tech.equals(NfcV.class.getName())) {
                    NfcV nfcvTag = NfcV.get(currentTag);
                    int numberOfBlocks = 0;
                    fullData = new StringBuffer();
                    utf8String = new StringBuffer();
                    blocksData = new ArrayList<String>();
                    while(numberOfBlocks < 128)
                    {
                        try {
                            nfcvTag.connect();
//                        connectTag.setText("Hello NFC!");
                        } catch (IOException e) {
                            Toast.makeText(getApplicationContext(), "Could not open a connection!", Toast.LENGTH_SHORT).show();
                            return;
                        }
                        try {
//
                            byte[] tagUid = currentTag.getId();  // store tag UID for use in addressed commands
//
                            byte[] cmd = new byte[] {
                                    (byte)0x20,  // FLAGS
                                    (byte)0x20,  // READ_SINGLE_BLOCK
                                    0, 0, 0, 0, 0, 0, 0, 0,
                                    (byte)(numberOfBlocks & 0x0ff)
                            };
                            System.arraycopy(tagUid, 0, cmd, 2, 8);  // paste tag UID into command
                            byte[] response = nfcvTag.transceive(cmd);
                            String data =  bytesToHex(response).substring(2);
                            String utf8 = new String(response , "UTF-8");

                            blocksData.add(data.replaceAll(" " , ""));
                            fullData.append(data.replaceAll(" " , ""));
                            utf8String.append(utf8);
                            nfcvTag.close();
                            numberOfBlocks = numberOfBlocks + 1;

                        } catch (IOException e) {
                            Toast.makeText(getApplicationContext(), "An error occurred while reading! :" + e.toString() , Toast.LENGTH_SHORT).show();
                            return;
                        }
                    }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM