00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00025 #ifdef HAVE_CONFIG_H
00026 #include "config.h"
00027 #endif // HAVE_CONFIG_H
00028
00029 #include <stdio.h>
00030 #include <stdlib.h>
00031 #include <stddef.h>
00032 #include <stdint.h>
00033 #include <stdbool.h>
00034 #include <string.h>
00035
00036 #include <nfc/nfc.h>
00037
00038 #include <nfc/nfc-messages.h>
00039 #include "bitutils.h"
00040
00041 #define SAK_FLAG_ATS_SUPPORTED 0x20
00042
00043 #define MAX_FRAME_LEN 264
00044
00045 static byte_t abtRx[MAX_FRAME_LEN];
00046 static size_t szRxBits;
00047 static size_t szRxLen;
00048 static byte_t abtUid[10];
00049 static size_t szUidLen = 4;
00050 static nfc_device_t* pnd;
00051
00052 bool quiet_output = false;
00053
00054
00055 byte_t abtReqa [1] = { 0x26 };
00056 byte_t abtSelectAll [2] = { 0x93,0x20 };
00057 byte_t abtSelectTag [9] = { 0x93,0x70,0x00,0x00,0x00,0x00,0x00,0x00,0x00 };
00058 byte_t abtRats [4] = { 0xe0,0x50,0xbc,0xa5 };
00059 byte_t abtHalt [4] = { 0x50,0x00,0x57,0xcd };
00060
00061 bool transmit_bits(const byte_t* pbtTx, const size_t szTxBits)
00062 {
00063
00064 if(!quiet_output)
00065 {
00066 printf("R: ");
00067 print_hex_bits(pbtTx,szTxBits);
00068 }
00069
00070
00071 if (!nfc_initiator_transceive_bits(pnd,pbtTx,szTxBits,NULL,abtRx,&szRxBits,NULL)) return false;
00072
00073
00074 if(!quiet_output)
00075 {
00076 printf("T: ");
00077 print_hex_bits(abtRx,szRxBits);
00078 }
00079
00080
00081 return true;
00082 }
00083
00084
00085 bool transmit_bytes(const byte_t* pbtTx, const size_t szTxLen)
00086 {
00087
00088 if(!quiet_output)
00089 {
00090 printf("R: ");
00091 print_hex(pbtTx,szTxLen);
00092 }
00093
00094
00095 if (!nfc_initiator_transceive_bytes(pnd,pbtTx,szTxLen,abtRx,&szRxLen)) return false;
00096
00097
00098 if(!quiet_output)
00099 {
00100 printf("T: ");
00101 print_hex(abtRx,szRxLen);
00102 }
00103
00104
00105 return true;
00106 }
00107
00108 void print_usage(char* argv[])
00109 {
00110 printf("Usage: %s [OPTIONS]\n", argv[0]);
00111 printf("Options:\n");
00112 printf("\t-h\tHelp. Print this message.\n");
00113 printf("\t-q\tQuiet mode. Suppress output of READER and EMULATOR data (improves timing).\n");
00114 }
00115
00116 int main(int argc,char* argv[])
00117 {
00118 int arg;
00119
00120
00121 for (arg=1;arg<argc;arg++) {
00122 if (0 == strcmp(argv[arg], "-h")) {
00123 print_usage(argv);
00124 return 0;
00125 } else if (0 == strcmp(argv[arg], "-q")) {
00126 INFO("%s", "Quiet mode.");
00127 quiet_output = true;
00128 } else {
00129 ERR("%s is not supported option.", argv[arg]);
00130 print_usage(argv);
00131 return -1;
00132 }
00133 }
00134
00135
00136 pnd = nfc_connect(NULL);
00137
00138 if (!pnd)
00139 {
00140 printf("Error connecting NFC reader\n");
00141 return 1;
00142 }
00143 nfc_initiator_init(pnd);
00144
00145
00146 nfc_configure(pnd,NDO_ACTIVATE_FIELD,false);
00147
00148
00149 nfc_configure(pnd,NDO_HANDLE_CRC,false);
00150 nfc_configure(pnd,NDO_HANDLE_PARITY,true);
00151
00152
00153 nfc_configure(pnd,NDO_ACTIVATE_FIELD,true);
00154
00155 printf("\nConnected to NFC reader: %s\n\n",pnd->acName);
00156
00157
00158 if (!transmit_bits(abtReqa,7))
00159 {
00160 printf("Error: No tag available\n");
00161 nfc_disconnect(pnd);
00162 return 1;
00163 }
00164
00165
00166 transmit_bytes(abtSelectAll,2);
00167
00168
00169 memcpy(abtUid,abtRx,4);
00170 memcpy(abtSelectTag+2,abtRx,5);
00171 append_iso14443a_crc(abtSelectTag,7);
00172 transmit_bytes(abtSelectTag,9);
00173
00174
00175 if (abtUid[0]!= 0x88)
00176 {
00177 szUidLen = 4;
00178 } else {
00179
00180 abtSelectAll[0] = 0x95;
00181 abtSelectTag[0] = 0x95;
00182
00183
00184 transmit_bytes(abtSelectAll,2);
00185
00186
00187 memcpy(abtUid+4,abtRx,4);
00188 memcpy(abtSelectTag+2,abtRx,5);
00189 append_iso14443a_crc(abtSelectTag,7);
00190 transmit_bytes(abtSelectTag,9);
00191 szUidLen = 7;
00192 }
00193
00194
00195 if (abtRx[0] & SAK_FLAG_ATS_SUPPORTED) transmit_bytes(abtRats,4);
00196
00197
00198 transmit_bytes(abtHalt,4);
00199
00200 printf("\nFound tag with UID: ");
00201 if (szUidLen == 4)
00202 {
00203 printf("%08x\n",swap_endian32(abtUid));
00204 } else {
00205 printf("%014llx\n",swap_endian64(abtUid)&0x00ffffffffffffffull);
00206 }
00207
00208 nfc_disconnect(pnd);
00209 return 0;
00210 }