Merge libnfc-1.5-new-api branch to trunk (r1168:1303).
This commit is contained in:
commit
26245add73
82 changed files with 4481 additions and 3212 deletions
|
|
@ -1,4 +1,4 @@
|
|||
SET(UTILS-SOURCES nfc-emulate-forum-tag2 nfc-emulate-forum-tag4 nfc-list nfc-relay-picc nfc-mfclassic nfc-mfultralight)
|
||||
SET(UTILS-SOURCES nfc-emulate-forum-tag4 nfc-list nfc-relay-picc nfc-mfclassic nfc-mfultralight)
|
||||
|
||||
ADD_LIBRARY(nfcutils STATIC
|
||||
nfc-utils.c
|
||||
|
|
|
|||
|
|
@ -1,10 +1,10 @@
|
|||
bin_PROGRAMS = \
|
||||
nfc-emulate-forum-tag2 \
|
||||
nfc-emulate-forum-tag4 \
|
||||
nfc-list \
|
||||
nfc-mfclassic \
|
||||
nfc-mfsetuid \
|
||||
nfc-mfultralight \
|
||||
nfc-probe \
|
||||
nfc-read-forum-tag3 \
|
||||
nfc-relay-picc
|
||||
|
||||
|
|
@ -18,10 +18,6 @@ noinst_LTLIBRARIES = libnfcutils.la
|
|||
|
||||
libnfcutils_la_SOURCES = nfc-utils.c
|
||||
|
||||
nfc_emulate_forum_tag2_SOURCES = nfc-emulate-forum-tag2.c
|
||||
nfc_emulate_forum_tag2_LDADD = $(top_builddir)/libnfc/libnfc.la \
|
||||
libnfcutils.la
|
||||
|
||||
nfc_emulate_forum_tag4_SOURCES = nfc-emulate-forum-tag4.c
|
||||
nfc_emulate_forum_tag4_LDADD = $(top_builddir)/libnfc/libnfc.la \
|
||||
libnfcutils.la
|
||||
|
|
@ -41,6 +37,10 @@ nfc_mfsetuid_LDADD = $(top_builddir)/libnfc/libnfc.la \
|
|||
nfc_mfultralight_SOURCES = nfc-mfultralight.c mifare.c mifare.h
|
||||
nfc_mfultralight_LDADD = $(top_builddir)/libnfc/libnfc.la
|
||||
|
||||
nfc_probe_SOURCES = nfc-probe.c
|
||||
nfc_probe_LDADD = $(top_builddir)/libnfc/libnfc.la \
|
||||
libnfcutils.la
|
||||
|
||||
nfc_read_forum_tag3_SOURCES = nfc-read-forum-tag3.c
|
||||
nfc_read_forum_tag3_LDADD = $(top_builddir)/libnfc/libnfc.la \
|
||||
libnfcutils.la
|
||||
|
|
@ -57,9 +57,4 @@ dist_man_MANS = \
|
|||
nfc-mfultralight.1 \
|
||||
nfc-relay-picc.1
|
||||
|
||||
if HAS_LOG4C
|
||||
AM_CFLAGS += @log4c_CFLAGS@
|
||||
LIBADD = @log4c_LIBS@
|
||||
endif
|
||||
|
||||
EXTRA_DIST = CMakeLists.txt
|
||||
|
|
|
|||
|
|
@ -48,13 +48,13 @@
|
|||
* The MIFARE Classic Specification (http://www.nxp.com/acrobat/other/identification/M001053_MF1ICS50_rev5_3.pdf) explains more about this process.
|
||||
*/
|
||||
bool
|
||||
nfc_initiator_mifare_cmd (nfc_device_t * pnd, const mifare_cmd mc, const uint8_t ui8Block, mifare_param * pmp)
|
||||
nfc_initiator_mifare_cmd (nfc_device *pnd, const mifare_cmd mc, const uint8_t ui8Block, mifare_param *pmp)
|
||||
{
|
||||
byte_t abtRx[265];
|
||||
uint8_t abtRx[265];
|
||||
size_t szRx = sizeof(abtRx);
|
||||
size_t szParamLen;
|
||||
byte_t abtCmd[265];
|
||||
bool bEasyFraming;
|
||||
uint8_t abtCmd[265];
|
||||
//bool bEasyFraming;
|
||||
|
||||
abtCmd[0] = mc; // The MIFARE Classic command
|
||||
abtCmd[1] = ui8Block; // The block address (1K=0x00..0x39, 4K=0x00..0xff)
|
||||
|
|
@ -69,19 +69,19 @@ nfc_initiator_mifare_cmd (nfc_device_t * pnd, const mifare_cmd mc, const uint8_t
|
|||
// Authenticate command
|
||||
case MC_AUTH_A:
|
||||
case MC_AUTH_B:
|
||||
szParamLen = sizeof (mifare_param_auth);
|
||||
szParamLen = sizeof (struct mifare_param_auth);
|
||||
break;
|
||||
|
||||
// Data command
|
||||
case MC_WRITE:
|
||||
szParamLen = sizeof (mifare_param_data);
|
||||
szParamLen = sizeof (struct mifare_param_data);
|
||||
break;
|
||||
|
||||
// Value command
|
||||
case MC_DECREMENT:
|
||||
case MC_INCREMENT:
|
||||
case MC_TRANSFER:
|
||||
szParamLen = sizeof (mifare_param_value);
|
||||
szParamLen = sizeof (struct mifare_param_value);
|
||||
break;
|
||||
|
||||
// Please fix your code, you never should reach this statement
|
||||
|
|
@ -92,30 +92,34 @@ nfc_initiator_mifare_cmd (nfc_device_t * pnd, const mifare_cmd mc, const uint8_t
|
|||
|
||||
// When available, copy the parameter bytes
|
||||
if (szParamLen)
|
||||
memcpy (abtCmd + 2, (byte_t *) pmp, szParamLen);
|
||||
memcpy (abtCmd + 2, (uint8_t *) pmp, szParamLen);
|
||||
|
||||
bEasyFraming = pnd->bEasyFraming;
|
||||
if (!nfc_configure (pnd, NDO_EASY_FRAMING, true)) {
|
||||
nfc_perror (pnd, "nfc_configure");
|
||||
// FIXME: Save and restore bEasyFraming
|
||||
// bEasyFraming = nfc_device_get_property_bool (pnd, NP_EASY_FRAMING, &bEasyFraming);
|
||||
if (nfc_device_set_property_bool (pnd, NP_EASY_FRAMING, true) < 0) {
|
||||
nfc_perror (pnd, "nfc_device_set_property_bool");
|
||||
return false;
|
||||
}
|
||||
// Fire the mifare command
|
||||
if (!nfc_initiator_transceive_bytes (pnd, abtCmd, 2 + szParamLen, abtRx, &szRx, NULL)) {
|
||||
if (pnd->iLastError == EINVRXFRAM) {
|
||||
// "Invalid received frame" AKA EINVRXFRAM, usual means we are
|
||||
int res;
|
||||
if ((res = nfc_initiator_transceive_bytes (pnd, abtCmd, 2 + szParamLen, abtRx, &szRx, -1)) < 0) {
|
||||
if (res == NFC_ERFTRANS) {
|
||||
// "Invalid received frame", usual means we are
|
||||
// authenticated on a sector but the requested MIFARE cmd (read, write)
|
||||
// is not permitted by current acces bytes;
|
||||
// So there is nothing to do here.
|
||||
} else {
|
||||
nfc_perror (pnd, "nfc_initiator_transceive_bytes");
|
||||
}
|
||||
nfc_configure (pnd, NDO_EASY_FRAMING, bEasyFraming);
|
||||
// XXX nfc_device_set_property_bool (pnd, NP_EASY_FRAMING, bEasyFraming);
|
||||
return false;
|
||||
}
|
||||
if (!nfc_configure (pnd, NDO_EASY_FRAMING, bEasyFraming)) {
|
||||
nfc_perror (pnd, "nfc_configure");
|
||||
/* XXX
|
||||
if (nfc_device_set_property_bool (pnd, NP_EASY_FRAMING, bEasyFraming) < 0) {
|
||||
nfc_perror (pnd, "nfc_device_set_property_bool");
|
||||
return false;
|
||||
}
|
||||
*/
|
||||
|
||||
// When we have executed a read command, copy the received bytes into the param
|
||||
if (mc == MC_READ) {
|
||||
|
|
|
|||
|
|
@ -38,7 +38,7 @@
|
|||
|
||||
# include <nfc/nfc-types.h>
|
||||
|
||||
// Compiler directive, set struct alignment to 1 byte_t for compatibility
|
||||
// Compiler directive, set struct alignment to 1 uint8_t for compatibility
|
||||
# pragma pack(1)
|
||||
|
||||
typedef enum {
|
||||
|
|
@ -53,50 +53,50 @@ typedef enum {
|
|||
} mifare_cmd;
|
||||
|
||||
// MIFARE command params
|
||||
typedef struct {
|
||||
byte_t abtKey[6];
|
||||
byte_t abtUid[4];
|
||||
} mifare_param_auth;
|
||||
struct mifare_param_auth {
|
||||
uint8_t abtKey[6];
|
||||
uint8_t abtUid[4];
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
byte_t abtData[16];
|
||||
} mifare_param_data;
|
||||
struct mifare_param_data {
|
||||
uint8_t abtData[16];
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
byte_t abtValue[4];
|
||||
} mifare_param_value;
|
||||
struct mifare_param_value {
|
||||
uint8_t abtValue[4];
|
||||
};
|
||||
|
||||
typedef union {
|
||||
mifare_param_auth mpa;
|
||||
mifare_param_data mpd;
|
||||
mifare_param_value mpv;
|
||||
struct mifare_param_auth mpa;
|
||||
struct mifare_param_data mpd;
|
||||
struct mifare_param_value mpv;
|
||||
} mifare_param;
|
||||
|
||||
// Reset struct alignment to default
|
||||
# pragma pack()
|
||||
|
||||
bool nfc_initiator_mifare_cmd (nfc_device_t * pnd, const mifare_cmd mc, const uint8_t ui8Block, mifare_param * pmp);
|
||||
bool nfc_initiator_mifare_cmd (nfc_device *pnd, const mifare_cmd mc, const uint8_t ui8Block, mifare_param *pmp);
|
||||
|
||||
// Compiler directive, set struct alignment to 1 byte_t for compatibility
|
||||
// Compiler directive, set struct alignment to 1 uint8_t for compatibility
|
||||
# pragma pack(1)
|
||||
|
||||
// MIFARE Classic
|
||||
typedef struct {
|
||||
byte_t abtUID[4];
|
||||
byte_t btBCC;
|
||||
byte_t btUnknown;
|
||||
byte_t abtATQA[2];
|
||||
byte_t abtUnknown[8];
|
||||
uint8_t abtUID[4];
|
||||
uint8_t btBCC;
|
||||
uint8_t btUnknown;
|
||||
uint8_t abtATQA[2];
|
||||
uint8_t abtUnknown[8];
|
||||
} mifare_classic_block_manufacturer;
|
||||
|
||||
typedef struct {
|
||||
byte_t abtData[16];
|
||||
uint8_t abtData[16];
|
||||
} mifare_classic_block_data;
|
||||
|
||||
typedef struct {
|
||||
byte_t abtKeyA[6];
|
||||
byte_t abtAccessBits[4];
|
||||
byte_t abtKeyB[6];
|
||||
uint8_t abtKeyA[6];
|
||||
uint8_t abtAccessBits[4];
|
||||
uint8_t abtKeyB[6];
|
||||
} mifare_classic_block_trailer;
|
||||
|
||||
typedef union {
|
||||
|
|
@ -111,17 +111,17 @@ typedef struct {
|
|||
|
||||
// MIFARE Ultralight
|
||||
typedef struct {
|
||||
byte_t sn0[3];
|
||||
byte_t btBCC0;
|
||||
byte_t sn1[4];
|
||||
byte_t btBCC1;
|
||||
byte_t internal;
|
||||
byte_t lock[2];
|
||||
byte_t otp[4];
|
||||
uint8_t sn0[3];
|
||||
uint8_t btBCC0;
|
||||
uint8_t sn1[4];
|
||||
uint8_t btBCC1;
|
||||
uint8_t internal;
|
||||
uint8_t lock[2];
|
||||
uint8_t otp[4];
|
||||
} mifareul_block_manufacturer;
|
||||
|
||||
typedef struct {
|
||||
byte_t abtData[16];
|
||||
uint8_t abtData[16];
|
||||
} mifareul_block_data;
|
||||
|
||||
typedef union {
|
||||
|
|
|
|||
|
|
@ -1,208 +0,0 @@
|
|||
/*-
|
||||
* Public platform independent Near Field Communication (NFC) library examples
|
||||
*
|
||||
* Copyright (C) 2011, Romuald Conty
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
* 1) Redistributions of source code must retain the above copyright notice,
|
||||
* this list of conditions and the following disclaimer.
|
||||
* 2 )Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
* Note that this license only applies on the examples, NFC library itself is under LGPL
|
||||
*
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file nfc-emulate-forum-tag2.c
|
||||
* @brief Emulates a NFC Forum Tag Type 2 with a NDEF message
|
||||
* This example allow to emulate an NFC Forum Tag Type 2 that contains a read-only NDEF message.
|
||||
*
|
||||
* It have been developed using PN533 USB hardware as target and Google Nexus S phone as initiator.
|
||||
*
|
||||
* This is know to NOT work with Nokia 6212 Classic and could not work with
|
||||
* several NFC Forum compiliant devices due to these reasons:
|
||||
* - The emulated target only have a 4 bytes UID where 7 bytes UID (as a real
|
||||
* Mifare Ultralight tag) are usually attempted;
|
||||
* - The chip is emulating a ISO/IEC 14443-3 tag, without any hardware helper.
|
||||
* If the initiator have too short timeouts for software-based emulation
|
||||
* (which is usually the case), this example will failed, this is not a bug
|
||||
* and we can't do anything using this kind of hardware (PN531/PN533).
|
||||
*/
|
||||
|
||||
/*
|
||||
* This implementation was written based on information provided by the
|
||||
* following documents:
|
||||
*
|
||||
* NFC Forum Type 2 Tag Operation
|
||||
* Technical Specification
|
||||
* NFCForum-TS-Type-2-Tag_1.0 - 2007-07-09
|
||||
*
|
||||
* ISO/IEC 14443-3
|
||||
* First edition - 2001-02-01
|
||||
* Identification cards — Contactless integrated circuit(s) cards — Proximity cards
|
||||
* Part 3: Initialization and anticollision
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif // HAVE_CONFIG_H
|
||||
|
||||
#include <errno.h>
|
||||
#include <signal.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include <nfc/nfc.h>
|
||||
#include <nfc/nfc-emulation.h>
|
||||
|
||||
#include "nfc-utils.h"
|
||||
|
||||
static nfc_device_t *pnd;
|
||||
|
||||
void
|
||||
stop_emulation (int sig)
|
||||
{
|
||||
(void)sig;
|
||||
if (pnd) {
|
||||
nfc_abort_command(pnd);
|
||||
} else {
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
||||
static uint8_t __nfcforum_tag2_memory_area[] = {
|
||||
0x00, 0x00, 0x00, 0x00, // Block 0
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0xFF, 0xFF, // Block 2 (Static lock bytes: CC area and data area are read-only locked)
|
||||
0xE1, 0x10, 0x06, 0x0F, // Block 3 (CC - NFC-Forum Tag Type 2 version 1.0, Data area (from block 4 to the end) is 48 bytes, Read-only mode)
|
||||
|
||||
0x03, 33, 0xd1, 0x02, // Block 4 (NDEF)
|
||||
0x1c, 0x53, 0x70, 0x91,
|
||||
0x01, 0x09, 0x54, 0x02,
|
||||
0x65, 0x6e, 0x4c, 0x69,
|
||||
|
||||
0x62, 0x6e, 0x66, 0x63,
|
||||
0x51, 0x01, 0x0b, 0x55,
|
||||
0x03, 0x6c, 0x69, 0x62,
|
||||
0x6e, 0x66, 0x63, 0x2e,
|
||||
|
||||
0x6f, 0x72, 0x67, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
};
|
||||
|
||||
#define READ 0x30
|
||||
#define WRITE 0xA2
|
||||
#define SECTOR_SELECT 0xC2
|
||||
|
||||
#define HALT 0x50
|
||||
int
|
||||
nfcforum_tag2_io (struct nfc_emulator *emulator, const byte_t *data_in, const size_t data_in_len, byte_t *data_out, const size_t data_out_len)
|
||||
{
|
||||
int res = 0;
|
||||
|
||||
uint8_t *nfcforum_tag2_memory_area = (uint8_t *)(emulator->user_data);
|
||||
|
||||
printf (" In: ");
|
||||
print_hex (data_in, data_in_len);
|
||||
|
||||
switch (data_in[0]) {
|
||||
case READ:
|
||||
if (data_out_len >= 16) {
|
||||
memcpy(data_out, nfcforum_tag2_memory_area + (data_in[1] * 4), 16);
|
||||
res = 16;
|
||||
} else {
|
||||
res = -ENOSPC;
|
||||
}
|
||||
break;
|
||||
case HALT:
|
||||
printf ("HALT sent\n");
|
||||
res = -ECONNABORTED;
|
||||
break;
|
||||
default:
|
||||
printf ("Unknown command: 0x%02x\n", data_in[0]);
|
||||
res = -ENOTSUP;
|
||||
}
|
||||
|
||||
if (res < 0) {
|
||||
ERR ("%s (%d)", strerror (-res), -res);
|
||||
} else {
|
||||
printf (" Out: ");
|
||||
print_hex (data_out, res);
|
||||
}
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
int
|
||||
main(int argc, char *argv[])
|
||||
{
|
||||
(void)argc;
|
||||
(void)argv;
|
||||
|
||||
nfc_target_t nt = {
|
||||
.nm = {
|
||||
.nmt = NMT_ISO14443A,
|
||||
.nbr = NBR_UNDEFINED, // Will be updated by nfc_target_init()
|
||||
},
|
||||
.nti = {
|
||||
.nai = {
|
||||
.abtAtqa = { 0x00, 0x04 },
|
||||
.abtUid = { 0x08, 0x00, 0xb0, 0x0b },
|
||||
.szUidLen = 4,
|
||||
.btSak = 0x00,
|
||||
.szAtsLen = 0,
|
||||
},
|
||||
}
|
||||
};
|
||||
|
||||
struct nfc_emulation_state_machine state_machine = {
|
||||
.io = nfcforum_tag2_io
|
||||
};
|
||||
|
||||
struct nfc_emulator emulator = {
|
||||
.target= &nt,
|
||||
.state_machine = &state_machine,
|
||||
.user_data = __nfcforum_tag2_memory_area,
|
||||
};
|
||||
|
||||
signal (SIGINT, stop_emulation);
|
||||
pnd = nfc_connect (NULL);
|
||||
|
||||
if (pnd == NULL) {
|
||||
ERR("Unable to connect to NFC device");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
printf ("Connected to NFC device: %s\n", pnd->acName);
|
||||
printf ("Emulating NDEF tag now, please touch it with a second NFC device\n");
|
||||
|
||||
if (nfc_emulate_target (pnd, &emulator) < 0) {
|
||||
goto error;
|
||||
}
|
||||
|
||||
nfc_disconnect(pnd);
|
||||
|
||||
exit (EXIT_SUCCESS);
|
||||
|
||||
error:
|
||||
if (pnd) {
|
||||
nfc_perror (pnd, argv[0]);
|
||||
nfc_disconnect (pnd);
|
||||
}
|
||||
}
|
||||
|
|
@ -68,7 +68,7 @@
|
|||
|
||||
#include "nfc-utils.h"
|
||||
|
||||
static nfc_device_t *pnd;
|
||||
static nfc_device *pnd;
|
||||
static bool quiet_output = false;
|
||||
|
||||
#define SYMBOL_PARAM_fISO14443_4_PICC 0x20
|
||||
|
|
@ -113,7 +113,7 @@ uint8_t nfcforum_capability_container[] = {
|
|||
#define ISO144434A_RATS 0xE0
|
||||
|
||||
int
|
||||
nfcforum_tag4_io (struct nfc_emulator *emulator, const byte_t *data_in, const size_t data_in_len, byte_t *data_out, const size_t data_out_len)
|
||||
nfcforum_tag4_io (struct nfc_emulator *emulator, const uint8_t *data_in, const size_t data_in_len, uint8_t *data_out, const size_t data_out_len)
|
||||
{
|
||||
int res = 0;
|
||||
|
||||
|
|
@ -289,7 +289,7 @@ usage (char *progname)
|
|||
int
|
||||
main (int argc, char *argv[])
|
||||
{
|
||||
nfc_target_t nt = {
|
||||
nfc_target nt = {
|
||||
.nm = {
|
||||
.nmt = NMT_ISO14443A,
|
||||
.nbr = NBR_UNDEFINED, // Will be updated by nfc_target_init()
|
||||
|
|
@ -345,31 +345,34 @@ main (int argc, char *argv[])
|
|||
err (EXIT_FAILURE, "Can't load NDEF file '%s'", argv[1]);
|
||||
}
|
||||
}
|
||||
|
||||
nfc_init (NULL);
|
||||
|
||||
// Try to open the NFC reader
|
||||
pnd = nfc_connect (NULL);
|
||||
pnd = nfc_open (NULL, NULL);
|
||||
|
||||
if (pnd == NULL) {
|
||||
ERR("Unable to connect to NFC device");
|
||||
ERR("Unable to open NFC device");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
signal (SIGINT, stop_emulation);
|
||||
|
||||
printf ("Connected to NFC device: %s\n", pnd->acName);
|
||||
printf ("NFC device: %s opened\n", nfc_device_get_name(pnd));
|
||||
printf ("Emulating NDEF tag now, please touch it with a second NFC device\n");
|
||||
|
||||
if (0 != nfc_emulate_target (pnd, &emulator)) { // contains already nfc_target_init() call
|
||||
nfc_perror (pnd, "nfc_emulate_target");
|
||||
}
|
||||
|
||||
nfc_disconnect(pnd);
|
||||
nfc_close(pnd);
|
||||
|
||||
if (argc == 3) {
|
||||
if (!(ndef_message_save (argv[2], &nfcforum_tag4_data))) {
|
||||
err (EXIT_FAILURE, "Can't save NDEF file '%s'", argv[2]);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
nfc_exit (NULL);
|
||||
exit (EXIT_SUCCESS);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ This tool displays all available information at selection time.
|
|||
|
||||
.SH OPTIONS
|
||||
.TP
|
||||
.B \-v, \-\-verbose
|
||||
.B \-v
|
||||
Tells
|
||||
.I
|
||||
nfc-list
|
||||
|
|
|
|||
145
utils/nfc-list.c
145
utils/nfc-list.c
|
|
@ -57,23 +57,38 @@
|
|||
#define MAX_DEVICE_COUNT 16
|
||||
#define MAX_TARGET_COUNT 16
|
||||
|
||||
static nfc_device_t *pnd;
|
||||
static nfc_device *pnd;
|
||||
|
||||
void
|
||||
print_usage (const char* progname)
|
||||
{
|
||||
printf ("usage: %s [-v]\n", progname);
|
||||
printf (" -v\t verbose display\n");
|
||||
}
|
||||
|
||||
int
|
||||
main (int argc, const char *argv[])
|
||||
{
|
||||
(void) argc;
|
||||
const char *acLibnfcVersion;
|
||||
size_t szDeviceFound;
|
||||
size_t szTargetFound;
|
||||
size_t i;
|
||||
bool verbose = false;
|
||||
nfc_device_desc_t *pnddDevices;
|
||||
int res = 0;
|
||||
|
||||
nfc_init (NULL);
|
||||
|
||||
// Display libnfc version
|
||||
acLibnfcVersion = nfc_version ();
|
||||
printf ("%s uses libnfc %s\n", argv[0], acLibnfcVersion);
|
||||
if (argc != 1) {
|
||||
if ((argc == 2) && (0 == strcmp ("-v", argv[1]))) {
|
||||
verbose = true;
|
||||
} else {
|
||||
print_usage (argv[0]);
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
||||
pnddDevices = parse_args (argc, argv, &szDeviceFound, &verbose);
|
||||
#ifdef HAVE_LIBUSB
|
||||
# ifdef DEBUG
|
||||
usb_set_debug (4);
|
||||
|
|
@ -82,7 +97,7 @@ main (int argc, const char *argv[])
|
|||
|
||||
/* Lazy way to open an NFC device */
|
||||
#if 0
|
||||
pnd = nfc_connect (NULL);
|
||||
pnd = nfc_open (NULL, NULL);
|
||||
#endif
|
||||
|
||||
/* If specific device is wanted, i.e. an ARYGON device on /dev/ttyUSB0 */
|
||||
|
|
@ -91,7 +106,7 @@ main (int argc, const char *argv[])
|
|||
ndd.pcDriver = "ARYGON";
|
||||
ndd.pcPort = "/dev/ttyUSB0";
|
||||
ndd.uiSpeed = 115200;
|
||||
pnd = nfc_connect (&ndd);
|
||||
pnd = nfc_open (NULL, &ndd);
|
||||
#endif
|
||||
|
||||
/* If specific device is wanted, i.e. a SCL3711 on USB */
|
||||
|
|
@ -99,45 +114,41 @@ main (int argc, const char *argv[])
|
|||
nfc_device_desc_t ndd;
|
||||
ndd.pcDriver = "PN533_USB";
|
||||
strcpy(ndd.acDevice, "SCM Micro / SCL3711-NFC&RW");
|
||||
pnd = nfc_connect (&ndd);
|
||||
pnd = nfc_open (NULL, &ndd);
|
||||
#endif
|
||||
|
||||
if (szDeviceFound == 0) {
|
||||
if (!(pnddDevices = malloc (MAX_DEVICE_COUNT * sizeof (*pnddDevices)))) {
|
||||
fprintf (stderr, "malloc() failed\n");
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
|
||||
nfc_list_devices (pnddDevices, MAX_DEVICE_COUNT, &szDeviceFound);
|
||||
}
|
||||
nfc_connstring connstrings[MAX_DEVICE_COUNT];
|
||||
size_t szDeviceFound = nfc_list_devices (NULL, connstrings, MAX_DEVICE_COUNT);
|
||||
|
||||
if (szDeviceFound == 0) {
|
||||
printf ("No NFC device found.\n");
|
||||
}
|
||||
|
||||
for (i = 0; i < szDeviceFound; i++) {
|
||||
nfc_target_t ant[MAX_TARGET_COUNT];
|
||||
pnd = nfc_connect (&(pnddDevices[i]));
|
||||
nfc_target ant[MAX_TARGET_COUNT];
|
||||
pnd = nfc_open (NULL, connstrings[i]);
|
||||
|
||||
if (pnd == NULL) {
|
||||
ERR ("%s", "Unable to connect to NFC device.");
|
||||
ERR ("%s", "Unable to open NFC device.");
|
||||
continue;
|
||||
}
|
||||
nfc_initiator_init (pnd);
|
||||
if (nfc_initiator_init (pnd) < 0) {
|
||||
nfc_perror (pnd, "nfc_initiator_init");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
printf ("Connected to NFC device: %s\n", pnd->acName);
|
||||
printf ("NFC device: %s opened\n", nfc_device_get_name (pnd));
|
||||
|
||||
nfc_modulation_t nm;
|
||||
nfc_modulation nm;
|
||||
|
||||
nm.nmt = NMT_ISO14443A;
|
||||
nm.nbr = NBR_106;
|
||||
// List ISO14443A targets
|
||||
if (nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT, &szTargetFound)) {
|
||||
size_t n;
|
||||
if (verbose || (szTargetFound > 0)) {
|
||||
printf ("%d ISO14443A passive target(s) found%s\n", (int) szTargetFound, (szTargetFound == 0) ? ".\n" : ":");
|
||||
if ((res = nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT)) >= 0) {
|
||||
int n;
|
||||
if (verbose) {
|
||||
printf ("%d ISO14443A passive target(s) found%s\n", res, (res == 0) ? ".\n" : ":");
|
||||
}
|
||||
for (n = 0; n < szTargetFound; n++) {
|
||||
for (n = 0; n < res; n++) {
|
||||
print_nfc_iso14443a_info (ant[n].nti.nai, verbose);
|
||||
printf ("\n");
|
||||
}
|
||||
|
|
@ -146,26 +157,24 @@ main (int argc, const char *argv[])
|
|||
nm.nmt = NMT_FELICA;
|
||||
nm.nbr = NBR_212;
|
||||
// List Felica tags
|
||||
if (nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT, &szTargetFound)) {
|
||||
size_t n;
|
||||
if (verbose || (szTargetFound > 0)) {
|
||||
printf ("%d Felica (212 kbps) passive target(s) found%s\n", (int) szTargetFound,
|
||||
(szTargetFound == 0) ? ".\n" : ":");
|
||||
if ((res = nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT)) >= 0) {
|
||||
int n;
|
||||
if (verbose) {
|
||||
printf ("%d Felica (212 kbps) passive target(s) found%s\n", res, (res == 0) ? ".\n" : ":");
|
||||
}
|
||||
for (n = 0; n < szTargetFound; n++) {
|
||||
for (n = 0; n < res; n++) {
|
||||
print_nfc_felica_info (ant[n].nti.nfi, verbose);
|
||||
printf ("\n");
|
||||
}
|
||||
}
|
||||
|
||||
nm.nbr = NBR_424;
|
||||
if (nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT, &szTargetFound)) {
|
||||
size_t n;
|
||||
if (verbose || (szTargetFound > 0)) {
|
||||
printf ("%d Felica (424 kbps) passive target(s) found%s\n", (int) szTargetFound,
|
||||
(szTargetFound == 0) ? ".\n" : ":");
|
||||
if ((res = nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT)) >= 0) {
|
||||
int n;
|
||||
if (verbose) {
|
||||
printf ("%d Felica (424 kbps) passive target(s) found%s\n", res, (res == 0) ? ".\n" : ":");
|
||||
}
|
||||
for (n = 0; n < szTargetFound; n++) {
|
||||
for (n = 0; n < res; n++) {
|
||||
print_nfc_felica_info (ant[n].nti.nfi, verbose);
|
||||
printf ("\n");
|
||||
}
|
||||
|
|
@ -174,12 +183,12 @@ main (int argc, const char *argv[])
|
|||
nm.nmt = NMT_ISO14443B;
|
||||
nm.nbr = NBR_106;
|
||||
// List ISO14443B targets
|
||||
if (nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT, &szTargetFound)) {
|
||||
size_t n;
|
||||
if (verbose || (szTargetFound > 0)) {
|
||||
printf ("%d ISO14443B passive target(s) found%s\n", (int) szTargetFound, (szTargetFound == 0) ? ".\n" : ":");
|
||||
if ((res = nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT)) >= 0) {
|
||||
int n;
|
||||
if (verbose) {
|
||||
printf ("%d ISO14443B passive target(s) found%s\n", res, (res == 0) ? ".\n" : ":");
|
||||
}
|
||||
for (n = 0; n < szTargetFound; n++) {
|
||||
for (n = 0; n < res; n++) {
|
||||
print_nfc_iso14443b_info (ant[n].nti.nbi, verbose);
|
||||
printf ("\n");
|
||||
}
|
||||
|
|
@ -188,12 +197,12 @@ main (int argc, const char *argv[])
|
|||
nm.nmt = NMT_ISO14443BI;
|
||||
nm.nbr = NBR_106;
|
||||
// List ISO14443B' targets
|
||||
if (nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT, &szTargetFound)) {
|
||||
size_t n;
|
||||
if (verbose || (szTargetFound > 0)) {
|
||||
printf ("%d ISO14443B' passive target(s) found%s\n", (int) szTargetFound, (szTargetFound == 0) ? ".\n" : ":");
|
||||
if ((res = nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT)) >= 0) {
|
||||
int n;
|
||||
if (verbose) {
|
||||
printf ("%d ISO14443B' passive target(s) found%s\n", res, (res == 0) ? ".\n" : ":");
|
||||
}
|
||||
for (n = 0; n < szTargetFound; n++) {
|
||||
for (n = 0; n < res; n++) {
|
||||
print_nfc_iso14443bi_info (ant[n].nti.nii, verbose);
|
||||
printf ("\n");
|
||||
}
|
||||
|
|
@ -202,12 +211,12 @@ main (int argc, const char *argv[])
|
|||
nm.nmt = NMT_ISO14443B2SR;
|
||||
nm.nbr = NBR_106;
|
||||
// List ISO14443B-2 ST SRx family targets
|
||||
if (nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT, &szTargetFound)) {
|
||||
size_t n;
|
||||
if (verbose || (szTargetFound > 0)) {
|
||||
printf ("%d ISO14443B-2 ST SRx passive target(s) found%s\n", (int) szTargetFound, (szTargetFound == 0) ? ".\n" : ":");
|
||||
if ((res = nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT)) >= 0) {
|
||||
int n;
|
||||
if (verbose) {
|
||||
printf ("%d ISO14443B-2 ST SRx passive target(s) found%s\n", res, (res == 0) ? ".\n" : ":");
|
||||
}
|
||||
for (n = 0; n < szTargetFound; n++) {
|
||||
for (n = 0; n < res; n++) {
|
||||
print_nfc_iso14443b2sr_info (ant[n].nti.nsi, verbose);
|
||||
printf ("\n");
|
||||
}
|
||||
|
|
@ -216,12 +225,12 @@ main (int argc, const char *argv[])
|
|||
nm.nmt = NMT_ISO14443B2CT;
|
||||
nm.nbr = NBR_106;
|
||||
// List ISO14443B-2 ASK CTx family targets
|
||||
if (nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT, &szTargetFound)) {
|
||||
size_t n;
|
||||
if (verbose || (szTargetFound > 0)) {
|
||||
printf ("%d ISO14443B-2 ASK CTx passive target(s) found%s\n", (int) szTargetFound, (szTargetFound == 0) ? ".\n" : ":");
|
||||
if ((res = nfc_initiator_list_passive_targets (pnd, nm, ant, MAX_TARGET_COUNT)) >= 0) {
|
||||
int n;
|
||||
if (verbose) {
|
||||
printf ("%d ISO14443B-2 ASK CTx passive target(s) found%s\n", res, (res == 0) ? ".\n" : ":");
|
||||
}
|
||||
for (n = 0; n < szTargetFound; n++) {
|
||||
for (n = 0; n < res; n++) {
|
||||
print_nfc_iso14443b2ct_info (ant[n].nti.nci, verbose);
|
||||
printf ("\n");
|
||||
}
|
||||
|
|
@ -230,19 +239,19 @@ main (int argc, const char *argv[])
|
|||
nm.nmt = NMT_JEWEL;
|
||||
nm.nbr = NBR_106;
|
||||
// List Jewel targets
|
||||
if (nfc_initiator_list_passive_targets(pnd, nm, ant, MAX_TARGET_COUNT, &szTargetFound )) {
|
||||
size_t n;
|
||||
if (verbose || (szTargetFound > 0)) {
|
||||
printf("%d Jewel passive target(s) found%s\n", (int)szTargetFound, (szTargetFound==0)?".\n":":");
|
||||
if ((res = nfc_initiator_list_passive_targets(pnd, nm, ant, MAX_TARGET_COUNT)) >= 0) {
|
||||
int n;
|
||||
if (verbose) {
|
||||
printf("%d Jewel passive target(s) found%s\n", res, (res == 0)?".\n":":");
|
||||
}
|
||||
for(n=0; n<szTargetFound; n++) {
|
||||
for(n = 0; n < res; n++) {
|
||||
print_nfc_jewel_info (ant[n].nti.nji, verbose);
|
||||
printf("\n");
|
||||
}
|
||||
}
|
||||
nfc_disconnect (pnd);
|
||||
nfc_close (pnd);
|
||||
}
|
||||
|
||||
free (pnddDevices);
|
||||
|
||||
nfc_exit (NULL);
|
||||
return 0;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -52,15 +52,15 @@
|
|||
#include "mifare.h"
|
||||
#include "nfc-utils.h"
|
||||
|
||||
static nfc_device_t *pnd;
|
||||
static nfc_target_t nt;
|
||||
static nfc_device *pnd;
|
||||
static nfc_target nt;
|
||||
static mifare_param mp;
|
||||
static mifare_classic_tag mtKeys;
|
||||
static mifare_classic_tag mtDump;
|
||||
static bool bUseKeyA;
|
||||
static bool bUseKeyFile;
|
||||
static uint8_t uiBlocks;
|
||||
static byte_t keys[] = {
|
||||
static uint8_t keys[] = {
|
||||
0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
|
||||
0xd3, 0xf7, 0xd3, 0xf7, 0xd3, 0xf7,
|
||||
0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5,
|
||||
|
|
@ -72,7 +72,7 @@ static byte_t keys[] = {
|
|||
0xab, 0xcd, 0xef, 0x12, 0x34, 0x56
|
||||
};
|
||||
|
||||
static const nfc_modulation_t nmMifare = {
|
||||
static const nfc_modulation nmMifare = {
|
||||
.nmt = NMT_ISO14443A,
|
||||
.nbr = NBR_106,
|
||||
};
|
||||
|
|
@ -81,24 +81,24 @@ static size_t num_keys = sizeof (keys) / 6;
|
|||
|
||||
#define MAX_FRAME_LEN 264
|
||||
|
||||
static byte_t abtRx[MAX_FRAME_LEN];
|
||||
static size_t szRxBits;
|
||||
static uint8_t abtRx[MAX_FRAME_LEN];
|
||||
static int szRxBits;
|
||||
static size_t szRx = sizeof(abtRx);
|
||||
|
||||
byte_t abtHalt[4] = { 0x50, 0x00, 0x00, 0x00 };
|
||||
uint8_t abtHalt[4] = { 0x50, 0x00, 0x00, 0x00 };
|
||||
|
||||
// special unlock command
|
||||
byte_t abtUnlock1[1] = { 0x40 };
|
||||
byte_t abtUnlock2[1] = { 0x43 };
|
||||
uint8_t abtUnlock1[1] = { 0x40 };
|
||||
uint8_t abtUnlock2[1] = { 0x43 };
|
||||
|
||||
static bool
|
||||
transmit_bits (const byte_t * pbtTx, const size_t szTxBits)
|
||||
transmit_bits (const uint8_t *pbtTx, const size_t szTxBits)
|
||||
{
|
||||
// Show transmitted command
|
||||
printf ("Sent bits: ");
|
||||
print_hex_bits (pbtTx, szTxBits);
|
||||
// Transmit the bit frame command, we don't use the arbitrary parity feature
|
||||
if (!nfc_initiator_transceive_bits (pnd, pbtTx, szTxBits, NULL, abtRx, &szRxBits, NULL))
|
||||
if ((szRxBits = nfc_initiator_transceive_bits (pnd, pbtTx, szTxBits, NULL, abtRx, NULL)) < 0)
|
||||
return false;
|
||||
|
||||
// Show received answer
|
||||
|
|
@ -110,13 +110,13 @@ transmit_bits (const byte_t * pbtTx, const size_t szTxBits)
|
|||
|
||||
|
||||
static bool
|
||||
transmit_bytes (const byte_t * pbtTx, const size_t szTx)
|
||||
transmit_bytes (const uint8_t *pbtTx, const size_t szTx)
|
||||
{
|
||||
// Show transmitted command
|
||||
printf ("Sent bits: ");
|
||||
print_hex (pbtTx, szTx);
|
||||
// Transmit the command bytes
|
||||
if (!nfc_initiator_transceive_bytes (pnd, pbtTx, szTx, abtRx, &szRx, NULL))
|
||||
if (nfc_initiator_transceive_bytes (pnd, pbtTx, szTx, abtRx, &szRx, 0) < 0)
|
||||
return false;
|
||||
|
||||
// Show received answer
|
||||
|
|
@ -127,7 +127,7 @@ transmit_bytes (const byte_t * pbtTx, const size_t szTx)
|
|||
}
|
||||
|
||||
static void
|
||||
print_success_or_failure (bool bFailure, uint32_t * uiBlockCounter)
|
||||
print_success_or_failure (bool bFailure, uint32_t *uiBlockCounter)
|
||||
{
|
||||
printf ("%c", (bFailure) ? 'x' : '.');
|
||||
if (uiBlockCounter && !bFailure)
|
||||
|
|
@ -219,12 +219,12 @@ unlock_card (void)
|
|||
printf ("Unlocking card\n");
|
||||
|
||||
// Configure the CRC
|
||||
if (!nfc_configure (pnd, NDO_HANDLE_CRC, false)) {
|
||||
if (nfc_device_set_property_bool (pnd, NP_HANDLE_CRC, false) < 0) {
|
||||
nfc_perror (pnd, "nfc_configure");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
// Use raw send/receive methods
|
||||
if (!nfc_configure (pnd, NDO_EASY_FRAMING, false)) {
|
||||
if (nfc_device_set_property_bool (pnd, NP_EASY_FRAMING, false) < 0) {
|
||||
nfc_perror (pnd, "nfc_configure");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
|
@ -243,13 +243,13 @@ unlock_card (void)
|
|||
|
||||
// reset reader
|
||||
// Configure the CRC
|
||||
if (!nfc_configure (pnd, NDO_HANDLE_CRC, true)) {
|
||||
nfc_perror (pnd, "nfc_configure");
|
||||
if (nfc_device_set_property_bool (pnd, NP_HANDLE_CRC, true) < 0) {
|
||||
nfc_perror (pnd, "nfc_device_set_property_bool");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
// Switch off raw send/receive methods
|
||||
if (!nfc_configure (pnd, NDO_EASY_FRAMING, true)) {
|
||||
nfc_perror (pnd, "nfc_configure");
|
||||
if (nfc_device_set_property_bool (pnd, NP_EASY_FRAMING, true) < 0) {
|
||||
nfc_perror (pnd, "nfc_device_set_property_bool");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
return true;
|
||||
|
|
@ -280,7 +280,7 @@ read_card (int read_unlocked)
|
|||
// Show if the readout went well
|
||||
if (bFailure) {
|
||||
// When a failure occured we need to redo the anti-collision
|
||||
if (!nfc_initiator_select_passive_target (pnd, nmMifare, NULL, 0, &nt)) {
|
||||
if (nfc_initiator_select_passive_target (pnd, nmMifare, NULL, 0, &nt) < 0) {
|
||||
printf ("!\nError: tag was removed\n");
|
||||
return false;
|
||||
}
|
||||
|
|
@ -353,7 +353,7 @@ write_card (int write_block_zero)
|
|||
// Show if the readout went well
|
||||
if (bFailure) {
|
||||
// When a failure occured we need to redo the anti-collision
|
||||
if (!nfc_initiator_select_passive_target (pnd, nmMifare, NULL, 0, &nt)) {
|
||||
if (nfc_initiator_select_passive_target (pnd, nmMifare, NULL, 0, &nt) < 0) {
|
||||
printf ("!\nError: tag was removed\n");
|
||||
return false;
|
||||
}
|
||||
|
|
@ -458,7 +458,7 @@ int
|
|||
main (int argc, const char *argv[])
|
||||
{
|
||||
action_t atAction = ACTION_USAGE;
|
||||
byte_t *pbtUID;
|
||||
uint8_t *pbtUID;
|
||||
FILE *pfKeys = NULL;
|
||||
FILE *pfDump = NULL;
|
||||
int unlock= 0;
|
||||
|
|
@ -537,29 +537,35 @@ main (int argc, const char *argv[])
|
|||
}
|
||||
// printf("Successfully opened required files\n");
|
||||
|
||||
nfc_init (NULL);
|
||||
|
||||
// Try to open the NFC reader
|
||||
pnd = nfc_connect (NULL);
|
||||
pnd = nfc_open (NULL, NULL);
|
||||
if (pnd == NULL) {
|
||||
printf ("Error connecting NFC reader\n");
|
||||
printf ("Error opening NFC reader\n");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
nfc_initiator_init (pnd);
|
||||
if (nfc_initiator_init (pnd) < 0) {
|
||||
nfc_perror (pnd, "nfc_initiator_init");
|
||||
exit (EXIT_FAILURE);
|
||||
};
|
||||
|
||||
// Let the reader only try once to find a tag
|
||||
if (!nfc_configure (pnd, NDO_INFINITE_SELECT, false)) {
|
||||
nfc_perror (pnd, "nfc_configure");
|
||||
if (nfc_device_set_property_bool (pnd, NP_INFINITE_SELECT, false) < 0) {
|
||||
nfc_perror (pnd, "nfc_device_set_property_bool");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
// Disable ISO14443-4 switching in order to read devices that emulate Mifare Classic with ISO14443-4 compliance.
|
||||
nfc_configure (pnd, NDO_AUTO_ISO14443_4, false);
|
||||
nfc_device_set_property_bool (pnd, NP_AUTO_ISO14443_4, false);
|
||||
|
||||
printf ("Connected to NFC reader: %s\n", pnd->acName);
|
||||
printf ("NFC reader: %s opened\n", nfc_device_get_name (pnd));
|
||||
|
||||
// Try to find a MIFARE Classic tag
|
||||
if (!nfc_initiator_select_passive_target (pnd, nmMifare, NULL, 0, &nt)) {
|
||||
if (nfc_initiator_select_passive_target (pnd, nmMifare, NULL, 0, &nt) < 0) {
|
||||
printf ("Error: no tag was found\n");
|
||||
nfc_disconnect (pnd);
|
||||
nfc_close (pnd);
|
||||
nfc_exit (NULL);
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
// Test if we are dealing with a MIFARE compatible tag
|
||||
|
|
@ -571,10 +577,10 @@ main (int argc, const char *argv[])
|
|||
pbtUID = nt.nti.nai.abtUid;
|
||||
|
||||
if (bUseKeyFile) {
|
||||
byte_t fileUid[4];
|
||||
uint8_t fileUid[4];
|
||||
memcpy (fileUid, mtKeys.amb[0].mbm.abtUID, 4);
|
||||
// Compare if key dump UID is the same as the current tag UID, at least for the first 4 bytes
|
||||
if (memcmp (nt.nti.nai.abtUid, fileUid, 4) != 0) {
|
||||
if (memcmp (pbtUID, fileUid, 4) != 0) {
|
||||
printf ("Expected MIFARE Classic card with UID starting as: %02x%02x%02x%02x\n",
|
||||
fileUid[0], fileUid[1], fileUid[2], fileUid[3]);
|
||||
}
|
||||
|
|
@ -615,7 +621,7 @@ main (int argc, const char *argv[])
|
|||
write_card (unlock);
|
||||
}
|
||||
|
||||
nfc_disconnect (pnd);
|
||||
nfc_close (pnd);
|
||||
break;
|
||||
|
||||
case ACTION_EXTRACT:{
|
||||
|
|
@ -658,6 +664,7 @@ main (int argc, const char *argv[])
|
|||
printf ("Done, all bytes have been extracted!\n");
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
nfc_exit (NULL);
|
||||
exit (EXIT_SUCCESS);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -56,39 +56,39 @@
|
|||
|
||||
#define MAX_FRAME_LEN 264
|
||||
|
||||
static byte_t abtRx[MAX_FRAME_LEN];
|
||||
static size_t szRxBits;
|
||||
static uint8_t abtRx[MAX_FRAME_LEN];
|
||||
static int szRxBits;
|
||||
static size_t szRx = sizeof(abtRx);
|
||||
static byte_t abtRawUid[12];
|
||||
static byte_t abtAtqa[2];
|
||||
static byte_t abtSak;
|
||||
static byte_t abtAts[MAX_FRAME_LEN];
|
||||
static byte_t szAts = 0;
|
||||
static uint8_t abtRawUid[12];
|
||||
static uint8_t abtAtqa[2];
|
||||
static uint8_t abtSak;
|
||||
static uint8_t abtAts[MAX_FRAME_LEN];
|
||||
static uint8_t szAts = 0;
|
||||
static size_t szCL = 1;//Always start with Cascade Level 1 (CL1)
|
||||
static nfc_device_t *pnd;
|
||||
static nfc_device *pnd;
|
||||
|
||||
bool quiet_output = false;
|
||||
bool iso_ats_supported = false;
|
||||
|
||||
// ISO14443A Anti-Collision Commands
|
||||
byte_t abtReqa[1] = { 0x26 };
|
||||
byte_t abtSelectAll[2] = { 0x93, 0x20 };
|
||||
byte_t abtSelectTag[9] = { 0x93, 0x70, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
|
||||
byte_t abtRats[4] = { 0xe0, 0x50, 0x00, 0x00 };
|
||||
byte_t abtHalt[4] = { 0x50, 0x00, 0x00, 0x00 };
|
||||
uint8_t abtReqa[1] = { 0x26 };
|
||||
uint8_t abtSelectAll[2] = { 0x93, 0x20 };
|
||||
uint8_t abtSelectTag[9] = { 0x93, 0x70, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
|
||||
uint8_t abtRats[4] = { 0xe0, 0x50, 0x00, 0x00 };
|
||||
uint8_t abtHalt[4] = { 0x50, 0x00, 0x00, 0x00 };
|
||||
#define CASCADE_BIT 0x04
|
||||
|
||||
// special unlock command
|
||||
byte_t abtUnlock1[1] = { 0x40 };
|
||||
byte_t abtUnlock2[1] = { 0x43 };
|
||||
byte_t abtWipe[1] = { 0x41 };
|
||||
byte_t abtWrite[4] = { 0xa0, 0x00, 0x5f, 0xb1 };
|
||||
byte_t abtData[18] = { 0x01, 0x23, 0x45, 0x67, 0x00, 0x08, 0x04, 0x00, 0x46, 0x59, 0x25, 0x58, 0x49, 0x10, 0x23, 0x02, 0x23, 0xeb };
|
||||
byte_t abtBlank[18] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x80, 0x69, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x36, 0xCC };
|
||||
uint8_t abtUnlock1[1] = { 0x40 };
|
||||
uint8_t abtUnlock2[1] = { 0x43 };
|
||||
uint8_t abtWipe[1] = { 0x41 };
|
||||
uint8_t abtWrite[4] = { 0xa0, 0x00, 0x5f, 0xb1 };
|
||||
uint8_t abtData[18] = { 0x01, 0x23, 0x45, 0x67, 0x00, 0x08, 0x04, 0x00, 0x46, 0x59, 0x25, 0x58, 0x49, 0x10, 0x23, 0x02, 0x23, 0xeb };
|
||||
uint8_t abtBlank[18] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x80, 0x69, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x36, 0xCC };
|
||||
|
||||
|
||||
static bool
|
||||
transmit_bits (const byte_t * pbtTx, const size_t szTxBits)
|
||||
transmit_bits (const uint8_t *pbtTx, const size_t szTxBits)
|
||||
{
|
||||
// Show transmitted command
|
||||
if (!quiet_output) {
|
||||
|
|
@ -96,7 +96,7 @@ transmit_bits (const byte_t * pbtTx, const size_t szTxBits)
|
|||
print_hex_bits (pbtTx, szTxBits);
|
||||
}
|
||||
// Transmit the bit frame command, we don't use the arbitrary parity feature
|
||||
if (!nfc_initiator_transceive_bits (pnd, pbtTx, szTxBits, NULL, abtRx, &szRxBits, NULL))
|
||||
if ((szRxBits = nfc_initiator_transceive_bits (pnd, pbtTx, szTxBits, NULL, abtRx, NULL)) < 0)
|
||||
return false;
|
||||
|
||||
// Show received answer
|
||||
|
|
@ -110,7 +110,7 @@ transmit_bits (const byte_t * pbtTx, const size_t szTxBits)
|
|||
|
||||
|
||||
static bool
|
||||
transmit_bytes (const byte_t * pbtTx, const size_t szTx)
|
||||
transmit_bytes (const uint8_t *pbtTx, const size_t szTx)
|
||||
{
|
||||
// Show transmitted command
|
||||
if (!quiet_output) {
|
||||
|
|
@ -118,7 +118,7 @@ transmit_bytes (const byte_t * pbtTx, const size_t szTx)
|
|||
print_hex (pbtTx, szTx);
|
||||
}
|
||||
// Transmit the command bytes
|
||||
if (!nfc_initiator_transceive_bytes (pnd, pbtTx, szTx, abtRx, &szRx, NULL))
|
||||
if (nfc_initiator_transceive_bytes (pnd, pbtTx, szTx, abtRx, &szRx, 0) < 0)
|
||||
return false;
|
||||
|
||||
// Show received answer
|
||||
|
|
@ -177,39 +177,45 @@ main (int argc, char *argv[])
|
|||
}
|
||||
}
|
||||
|
||||
nfc_init (NULL);
|
||||
|
||||
// Try to open the NFC reader
|
||||
pnd = nfc_connect (NULL);
|
||||
pnd = nfc_open (NULL, NULL);
|
||||
|
||||
if (!pnd) {
|
||||
printf ("Error connecting NFC reader\n");
|
||||
printf ("Error opening NFC reader\n");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
// Initialise NFC device as "initiator"
|
||||
nfc_initiator_init (pnd);
|
||||
if (nfc_initiator_init (pnd) < 0) {
|
||||
nfc_perror (pnd, "nfc_initiator_init");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
// Configure the CRC
|
||||
if (!nfc_configure (pnd, NDO_HANDLE_CRC, false)) {
|
||||
nfc_perror (pnd, "nfc_configure");
|
||||
if (nfc_device_set_property_bool (pnd, NP_HANDLE_CRC, false) < 0) {
|
||||
nfc_perror (pnd, "nfc_device_set_property_bool");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
// Use raw send/receive methods
|
||||
if (!nfc_configure (pnd, NDO_EASY_FRAMING, false)) {
|
||||
nfc_perror (pnd, "nfc_configure");
|
||||
if (nfc_device_set_property_bool (pnd, NP_EASY_FRAMING, false) < 0) {
|
||||
nfc_perror (pnd, "nfc_device_set_property_bool");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
// Disable 14443-4 autoswitching
|
||||
if (!nfc_configure (pnd, NDO_AUTO_ISO14443_4, false)) {
|
||||
nfc_perror (pnd, "nfc_configure");
|
||||
if (nfc_device_set_property_bool (pnd, NP_AUTO_ISO14443_4, false) < 0) {
|
||||
nfc_perror (pnd, "nfc_device_set_property_bool");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
printf ("Connected to NFC reader: %s\n\n", pnd->acName);
|
||||
printf ("NFC reader: %s opened\n", nfc_device_get_name (pnd));
|
||||
|
||||
// Send the 7 bits request command specified in ISO 14443A (0x26)
|
||||
if (!transmit_bits (abtReqa, 7)) {
|
||||
printf ("Error: No tag available\n");
|
||||
nfc_disconnect (pnd);
|
||||
nfc_close (pnd);
|
||||
nfc_exit (NULL);
|
||||
return 1;
|
||||
}
|
||||
memcpy (abtAtqa, abtRx, 2);
|
||||
|
|
@ -338,7 +344,7 @@ main (int argc, char *argv[])
|
|||
transmit_bytes (abtWrite,4);
|
||||
transmit_bytes (abtData,18);
|
||||
if(format) {
|
||||
for(i= 3 ; i < 64 ; i += 4) {
|
||||
for(i = 3 ; i < 64 ; i += 4) {
|
||||
abtWrite[1]= (char) i;
|
||||
iso14443a_crc_append (abtWrite, 2);
|
||||
transmit_bytes (abtWrite,4);
|
||||
|
|
@ -347,6 +353,7 @@ main (int argc, char *argv[])
|
|||
}
|
||||
|
||||
|
||||
nfc_disconnect (pnd);
|
||||
nfc_close (pnd);
|
||||
nfc_exit (NULL);
|
||||
return 0;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -51,13 +51,13 @@
|
|||
#include "nfc-utils.h"
|
||||
#include "mifare.h"
|
||||
|
||||
static nfc_device_t *pnd;
|
||||
static nfc_target_t nt;
|
||||
static nfc_device *pnd;
|
||||
static nfc_target nt;
|
||||
static mifare_param mp;
|
||||
static mifareul_tag mtDump;
|
||||
static uint32_t uiBlocks = 0xF;
|
||||
|
||||
static const nfc_modulation_t nmMifare = {
|
||||
static const nfc_modulation nmMifare = {
|
||||
.nmt = NMT_ISO14443A,
|
||||
.nbr = NBR_106,
|
||||
};
|
||||
|
|
@ -142,7 +142,7 @@ write_card (void)
|
|||
// Show if the readout went well
|
||||
if (bFailure) {
|
||||
// When a failure occured we need to redo the anti-collision
|
||||
if (!nfc_initiator_select_passive_target (pnd, nmMifare, NULL, 0, &nt)) {
|
||||
if (nfc_initiator_select_passive_target (pnd, nmMifare, NULL, 0, &nt) < 0) {
|
||||
ERR ("tag was removed");
|
||||
return false;
|
||||
}
|
||||
|
|
@ -204,34 +204,41 @@ main (int argc, const char *argv[])
|
|||
}
|
||||
DBG ("Successfully opened the dump file\n");
|
||||
|
||||
nfc_init (NULL);
|
||||
|
||||
// Try to open the NFC device
|
||||
pnd = nfc_connect (NULL);
|
||||
pnd = nfc_open (NULL, NULL);
|
||||
if (pnd == NULL) {
|
||||
ERR ("Error connecting NFC device\n");
|
||||
ERR ("Error opening NFC device\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
nfc_initiator_init (pnd);
|
||||
if (nfc_initiator_init (pnd) < 0) {
|
||||
nfc_perror (pnd, "nfc_initiator_init");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
// Let the device only try once to find a tag
|
||||
if (!nfc_configure (pnd, NDO_INFINITE_SELECT, false)) {
|
||||
nfc_perror (pnd, "nfc_configure");
|
||||
if (nfc_device_set_property_bool (pnd, NP_INFINITE_SELECT, false) < 0) {
|
||||
nfc_perror (pnd, "nfc_device_set_property_bool");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
printf ("Connected to NFC device: %s\n", pnd->acName);
|
||||
printf ("NFC device: %s opened\n", nfc_device_get_name (pnd));
|
||||
|
||||
// Try to find a MIFARE Ultralight tag
|
||||
if (!nfc_initiator_select_passive_target (pnd, nmMifare, NULL, 0, &nt)) {
|
||||
if (nfc_initiator_select_passive_target (pnd, nmMifare, NULL, 0, &nt) < 0) {
|
||||
ERR ("no tag was found\n");
|
||||
nfc_disconnect (pnd);
|
||||
nfc_close (pnd);
|
||||
nfc_exit (NULL);
|
||||
return 1;
|
||||
}
|
||||
// Test if we are dealing with a MIFARE compatible tag
|
||||
|
||||
if (nt.nti.nai.abtAtqa[1] != 0x44) {
|
||||
ERR ("tag is not a MIFARE Ultralight card\n");
|
||||
nfc_disconnect (pnd);
|
||||
nfc_close (pnd);
|
||||
nfc_exit (NULL);
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
// Get the info from the current tag
|
||||
|
|
@ -262,7 +269,7 @@ main (int argc, const char *argv[])
|
|||
write_card ();
|
||||
}
|
||||
|
||||
nfc_disconnect (pnd);
|
||||
|
||||
nfc_close (pnd);
|
||||
nfc_exit (NULL);
|
||||
return EXIT_SUCCESS;
|
||||
}
|
||||
|
|
|
|||
115
utils/nfc-probe.c
Normal file
115
utils/nfc-probe.c
Normal file
|
|
@ -0,0 +1,115 @@
|
|||
/*-
|
||||
* Public platform independent Near Field Communication (NFC) library examples
|
||||
*
|
||||
* Copyright (C) 2009, Roel Verdult
|
||||
* Copyright (C) 2010, Romuald Conty, Romain Tartière
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
* 1) Redistributions of source code must retain the above copyright notice,
|
||||
* this list of conditions and the following disclaimer.
|
||||
* 2 )Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
* Note that this license only applies on the examples, NFC library itself is under LGPL
|
||||
*
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file nfc-probe.c
|
||||
* @brief Lists each available NFC device
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif // HAVE_CONFIG_H
|
||||
|
||||
#ifdef HAVE_LIBUSB
|
||||
# ifdef DEBUG
|
||||
# include <sys/param.h>
|
||||
# include <usb.h>
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#include <err.h>
|
||||
#include <stdio.h>
|
||||
#include <stddef.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <nfc/nfc.h>
|
||||
|
||||
#include "nfc-utils.h"
|
||||
|
||||
#define MAX_DEVICE_COUNT 16
|
||||
#define MAX_TARGET_COUNT 16
|
||||
|
||||
static nfc_device *pnd;
|
||||
|
||||
void
|
||||
print_usage (const char* progname)
|
||||
{
|
||||
printf ("usage: %s [-v]\n", progname);
|
||||
printf (" -v\t verbose display\n");
|
||||
}
|
||||
|
||||
int
|
||||
main (int argc, const char *argv[])
|
||||
{
|
||||
(void) argc;
|
||||
const char *acLibnfcVersion;
|
||||
size_t i;
|
||||
bool verbose = false;
|
||||
|
||||
nfc_init (NULL);
|
||||
|
||||
// Display libnfc version
|
||||
acLibnfcVersion = nfc_version ();
|
||||
printf ("%s uses libnfc %s\n", argv[0], acLibnfcVersion);
|
||||
if (argc != 1) {
|
||||
if ((argc == 2) && (0 == strcmp ("-v", argv[1]))) {
|
||||
verbose = true;
|
||||
} else {
|
||||
print_usage (argv[0]);
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef HAVE_LIBUSB
|
||||
# ifdef DEBUG
|
||||
usb_set_debug (4);
|
||||
# endif
|
||||
#endif
|
||||
|
||||
nfc_connstring connstrings[MAX_DEVICE_COUNT];
|
||||
size_t szDeviceFound = nfc_list_devices (NULL, connstrings, MAX_DEVICE_COUNT);
|
||||
|
||||
if (szDeviceFound == 0) {
|
||||
printf ("No NFC device found.\n");
|
||||
}
|
||||
|
||||
printf ("%d NFC device(s) found:\n", szDeviceFound);
|
||||
for (i = 0; i < szDeviceFound; i++) {
|
||||
pnd = nfc_open (NULL, connstrings[i]);
|
||||
if (pnd != NULL) {
|
||||
printf ("- %s:\n %s\n", nfc_device_get_name (pnd), nfc_device_get_connstring (pnd));
|
||||
}
|
||||
nfc_close (pnd);
|
||||
}
|
||||
|
||||
nfc_exit (NULL);
|
||||
return 0;
|
||||
}
|
||||
|
|
@ -56,7 +56,7 @@
|
|||
|
||||
#include "nfc-utils.h"
|
||||
|
||||
static nfc_device_t *pnd;
|
||||
static nfc_device *pnd;
|
||||
|
||||
void
|
||||
print_usage(char *progname)
|
||||
|
|
@ -76,7 +76,7 @@ void stop_select (int sig)
|
|||
}
|
||||
|
||||
void
|
||||
build_felica_frame(const nfc_felica_info_t nfi, const byte_t command, const byte_t* payload, const size_t payload_len, byte_t * frame, size_t * frame_len)
|
||||
build_felica_frame(const nfc_felica_info nfi, const uint8_t command, const uint8_t *payload, const size_t payload_len, uint8_t *frame, size_t *frame_len)
|
||||
{
|
||||
frame[0] = 1 + 1 + 8 + payload_len;
|
||||
*frame_len = frame[0];
|
||||
|
|
@ -87,9 +87,9 @@ build_felica_frame(const nfc_felica_info_t nfi, const byte_t command, const byte
|
|||
|
||||
#define CHECK 0x06
|
||||
int
|
||||
nfc_forum_tag_type3_check (nfc_device_t *pnd, const nfc_target_t nt, const uint16_t block, const uint8_t block_count, byte_t * data, size_t * data_len)
|
||||
nfc_forum_tag_type3_check (nfc_device *pnd, const nfc_target nt, const uint16_t block, const uint8_t block_count, uint8_t *data, size_t *data_len)
|
||||
{
|
||||
byte_t payload[1024] = {
|
||||
uint8_t payload[1024] = {
|
||||
1, // Services
|
||||
0x0B, 0x00, // NFC Forum Tag Type 3's Service code
|
||||
block_count,
|
||||
|
|
@ -97,7 +97,7 @@ nfc_forum_tag_type3_check (nfc_device_t *pnd, const nfc_target_t nt, const uint1
|
|||
};
|
||||
|
||||
size_t payload_len = 1 + 2 + 1;
|
||||
for (uint8_t b=0; b<block_count; b++) {
|
||||
for (uint8_t b = 0; b < block_count; b++) {
|
||||
if (block < 0x100) {
|
||||
payload[payload_len++] = 0x80;
|
||||
payload[payload_len++] = block + b;
|
||||
|
|
@ -108,18 +108,18 @@ nfc_forum_tag_type3_check (nfc_device_t *pnd, const nfc_target_t nt, const uint1
|
|||
}
|
||||
}
|
||||
|
||||
byte_t frame[1024];
|
||||
uint8_t frame[1024];
|
||||
size_t frame_len = sizeof(frame);
|
||||
build_felica_frame (nt.nti.nfi, CHECK, payload, payload_len, frame, &frame_len);
|
||||
|
||||
byte_t res[1024];
|
||||
uint8_t res[1024];
|
||||
|
||||
size_t res_len;
|
||||
if (!nfc_initiator_transceive_bytes (pnd, frame, frame_len, res, &res_len, NULL)) {
|
||||
if (nfc_initiator_transceive_bytes (pnd, frame, frame_len, res, &res_len, 0) < 0) {
|
||||
return -1;
|
||||
}
|
||||
const size_t res_overhead = 1 + 1 + 8 + 2; // 1+1+8+2: LEN + CMD + NFCID2 + STATUS
|
||||
if (res_len<res_overhead) {
|
||||
if (res_len < res_overhead) {
|
||||
// Not enough data
|
||||
return -1;
|
||||
}
|
||||
|
|
@ -136,8 +136,8 @@ nfc_forum_tag_type3_check (nfc_device_t *pnd, const nfc_target_t nt, const uint1
|
|||
// NFCID2 does not match
|
||||
return -1;
|
||||
}
|
||||
const byte_t status_flag1 = res[10];
|
||||
const byte_t status_flag2 = res[11];
|
||||
const uint8_t status_flag1 = res[10];
|
||||
const uint8_t status_flag2 = res[11];
|
||||
if ((status_flag1) || (status_flag2)) {
|
||||
// Felica card's error
|
||||
fprintf (stderr, "Status bytes: %02x, %02x\n", status_flag1, status_flag2);
|
||||
|
|
@ -193,43 +193,48 @@ main(int argc, char *argv[])
|
|||
exit (EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
||||
nfc_init (NULL);
|
||||
|
||||
pnd = nfc_connect (NULL);
|
||||
pnd = nfc_open (NULL, NULL);
|
||||
|
||||
if (pnd == NULL) {
|
||||
ERR("Unable to connect to NFC device");
|
||||
ERR("Unable to open NFC device");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
fprintf (message_stream, "Connected to NFC device: %s\n", pnd->acName);
|
||||
fprintf (message_stream, "NFC device: %s opened\n", nfc_device_get_name (pnd));
|
||||
|
||||
nfc_modulation_t nm = {
|
||||
nfc_modulation nm = {
|
||||
.nmt = NMT_FELICA,
|
||||
.nbr = NBR_212,
|
||||
};
|
||||
|
||||
signal (SIGINT, stop_select);
|
||||
|
||||
nfc_target_t nt;
|
||||
nfc_target nt;
|
||||
|
||||
nfc_initiator_init(pnd);
|
||||
if (nfc_initiator_init (pnd) < 0) {
|
||||
nfc_perror (pnd, "nfc_initiator_init");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
fprintf (message_stream, "Place your NFC Forum Tag Type 3 in the field...\n");
|
||||
|
||||
int error = EXIT_SUCCESS;
|
||||
// Polling payload (SENSF_REQ) must be present (see NFC Digital Protol)
|
||||
const byte_t *pbtSensfReq = (byte_t*)"\x00\xff\xff\x01\x00";
|
||||
if (!nfc_initiator_select_passive_target(pnd, nm, pbtSensfReq, 5, &nt)) {
|
||||
const uint8_t *pbtSensfReq = (uint8_t*)"\x00\xff\xff\x01\x00";
|
||||
if (nfc_initiator_select_passive_target(pnd, nm, pbtSensfReq, 5, &nt) < 0) {
|
||||
nfc_perror (pnd, "nfc_initiator_select_passive_target");
|
||||
error = EXIT_FAILURE;
|
||||
goto error;
|
||||
}
|
||||
|
||||
// Check if System Code equals 0x12fc
|
||||
const byte_t abtNfcForumSysCode[] = { 0x12, 0xfc };
|
||||
const uint8_t abtNfcForumSysCode[] = { 0x12, 0xfc };
|
||||
if (0 != memcmp (nt.nti.nfi.abtSysCode, abtNfcForumSysCode, 2)) {
|
||||
// Retry with special polling
|
||||
const byte_t *pbtSensfReqNfcForum = (byte_t*)"\x00\x12\xfc\x01\x00";
|
||||
if (!nfc_initiator_select_passive_target(pnd, nm, pbtSensfReqNfcForum, 5, &nt)) {
|
||||
const uint8_t *pbtSensfReqNfcForum = (uint8_t*)"\x00\x12\xfc\x01\x00";
|
||||
if (nfc_initiator_select_passive_target(pnd, nm, pbtSensfReqNfcForum, 5, &nt) < 0) {
|
||||
nfc_perror (pnd, "nfc_initiator_select_passive_target");
|
||||
error = EXIT_FAILURE;
|
||||
goto error;
|
||||
|
|
@ -244,13 +249,13 @@ main(int argc, char *argv[])
|
|||
|
||||
//print_nfc_felica_info(nt.nti.nfi, true);
|
||||
|
||||
if (!nfc_configure (pnd, NDO_EASY_FRAMING, false) || !nfc_configure (pnd, NDO_INFINITE_SELECT, false)) {
|
||||
nfc_perror (pnd, "nfc_configure");
|
||||
if ((nfc_device_set_property_bool (pnd, NP_EASY_FRAMING, false) < 0) || (nfc_device_set_property_bool (pnd, NP_INFINITE_SELECT, false) < 0)) {
|
||||
nfc_perror (pnd, "nfc_device_set_property_bool");
|
||||
error = EXIT_FAILURE;
|
||||
goto error;
|
||||
}
|
||||
|
||||
byte_t data[1024];
|
||||
uint8_t data[1024];
|
||||
size_t data_len = sizeof(data);
|
||||
int len;
|
||||
|
||||
|
|
@ -271,7 +276,7 @@ main(int argc, char *argv[])
|
|||
fprintf (message_stream, "NDEF data lenght: %d bytes\n", ndef_data_len);
|
||||
|
||||
uint16_t ndef_calculated_checksum = 0;
|
||||
for (size_t n=0; n<14; n++)
|
||||
for (size_t n = 0; n < 14; n++)
|
||||
ndef_calculated_checksum += data[n];
|
||||
|
||||
const uint16_t ndef_checksum = (data[14] << 8) + data[15];
|
||||
|
|
@ -291,7 +296,7 @@ main(int argc, char *argv[])
|
|||
const uint16_t block_count_to_check = (ndef_data_len / 16) + 1;
|
||||
|
||||
data_len = 0;
|
||||
for (uint16_t b=0; b<(block_count_to_check/block_max_per_check); b+=block_max_per_check) {
|
||||
for (uint16_t b = 0; b < (block_count_to_check/block_max_per_check); b += block_max_per_check) {
|
||||
size_t len = sizeof(data) - data_len;
|
||||
if(!nfc_forum_tag_type3_check (pnd, nt, 1+b, MIN(block_max_per_check, (block_count_to_check-(b*block_max_per_check))), data + data_len, &len)) {
|
||||
nfc_perror (pnd, "nfc_forum_tag_type3_check");
|
||||
|
|
@ -309,7 +314,8 @@ main(int argc, char *argv[])
|
|||
error:
|
||||
fclose (ndef_stream);
|
||||
if (pnd) {
|
||||
nfc_disconnect (pnd);
|
||||
nfc_close (pnd);
|
||||
}
|
||||
nfc_exit (NULL);
|
||||
exit (error);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -57,12 +57,12 @@
|
|||
#define MAX_FRAME_LEN 264
|
||||
#define MAX_DEVICE_COUNT 2
|
||||
|
||||
static byte_t abtCapdu[MAX_FRAME_LEN];
|
||||
static uint8_t abtCapdu[MAX_FRAME_LEN];
|
||||
static size_t szCapduLen;
|
||||
static byte_t abtRapdu[MAX_FRAME_LEN];
|
||||
static uint8_t abtRapdu[MAX_FRAME_LEN];
|
||||
static size_t szRapduLen;
|
||||
static nfc_device_t *pndInitiator;
|
||||
static nfc_device_t *pndTarget;
|
||||
static nfc_device *pndInitiator;
|
||||
static nfc_device *pndTarget;
|
||||
static bool quitting = false;
|
||||
static bool quiet_output = false;
|
||||
static bool initiator_only_mode = false;
|
||||
|
|
@ -92,29 +92,29 @@ print_usage (char *argv[])
|
|||
printf ("\t-n N\tAdds a waiting time of N seconds (integer) in the relay to mimic long distance.\n");
|
||||
}
|
||||
|
||||
bool print_hex_fd4 (const byte_t * pbtData, const size_t szBytes, const char * pchPrefix)
|
||||
bool print_hex_fd4 (const uint8_t *pbtData, const size_t szBytes, const char *pchPrefix)
|
||||
{
|
||||
size_t szPos;
|
||||
if (szBytes > MAX_FRAME_LEN) {
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
if (fprintf (fd4, "#%s %04zx: ", pchPrefix, szBytes)<0) {
|
||||
if (fprintf (fd4, "#%s %04zx: ", pchPrefix, szBytes) < 0) {
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
|
||||
for (szPos = 0; szPos < szBytes; szPos++) {
|
||||
if (fprintf (fd4, "%02x ", pbtData[szPos])<0) {
|
||||
if (fprintf (fd4, "%02x ", pbtData[szPos]) < 0) {
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
}
|
||||
if (fprintf (fd4, "\n")<0) {
|
||||
if (fprintf (fd4, "\n") < 0) {
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
fflush(fd4);
|
||||
return EXIT_SUCCESS;
|
||||
}
|
||||
|
||||
bool scan_hex_fd3 (byte_t *pbtData, size_t *pszBytes, const char * pchPrefix)
|
||||
bool scan_hex_fd3 (uint8_t *pbtData, size_t *pszBytes, const char *pchPrefix)
|
||||
{
|
||||
size_t szPos;
|
||||
unsigned int uiBytes;
|
||||
|
|
@ -129,7 +129,7 @@ bool scan_hex_fd3 (byte_t *pbtData, size_t *pszBytes, const char * pchPrefix)
|
|||
}
|
||||
strncpy(pchScan, pchPrefix, 250);
|
||||
strcat(pchScan, " %04x:");
|
||||
if (fscanf (fd3, pchScan, &uiBytes)<1) {
|
||||
if (fscanf (fd3, pchScan, &uiBytes) < 1) {
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
*pszBytes=uiBytes;
|
||||
|
|
@ -137,7 +137,7 @@ bool scan_hex_fd3 (byte_t *pbtData, size_t *pszBytes, const char * pchPrefix)
|
|||
return EXIT_FAILURE;
|
||||
}
|
||||
for (szPos = 0; szPos < *pszBytes; szPos++) {
|
||||
if (fscanf (fd3, "%02x", &uiData)<1) {
|
||||
if (fscanf (fd3, "%02x", &uiData) < 1) {
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
pbtData[szPos]=uiData;
|
||||
|
|
@ -149,10 +149,8 @@ int
|
|||
main (int argc, char *argv[])
|
||||
{
|
||||
int arg;
|
||||
size_t szFound;
|
||||
nfc_device_desc_t *pnddDevices;
|
||||
const char *acLibnfcVersion = nfc_version ();
|
||||
nfc_target_t ntRealTarget;
|
||||
nfc_target ntRealTarget;
|
||||
|
||||
// Get commandline options
|
||||
for (arg = 1; arg < argc; arg++) {
|
||||
|
|
@ -170,7 +168,7 @@ main (int argc, char *argv[])
|
|||
initiator_only_mode = true;
|
||||
target_only_mode = false;
|
||||
} else if (0 == strcmp (argv[arg], "-n")) {
|
||||
if (++arg==argc || (sscanf(argv[arg], "%i", &waiting_time)<1)) {
|
||||
if (++arg == argc || (sscanf(argv[arg], "%i", &waiting_time) < 1)) {
|
||||
ERR ("Missing or wrong waiting time value: %s.", argv[arg]);
|
||||
print_usage (argv);
|
||||
return EXIT_FAILURE;
|
||||
|
|
@ -192,13 +190,11 @@ main (int argc, char *argv[])
|
|||
signal (SIGINT, (void (*)()) intr_hdlr);
|
||||
#endif
|
||||
|
||||
// Allocate memory to put the result of available devices listing
|
||||
if (!(pnddDevices = malloc (MAX_DEVICE_COUNT * sizeof (*pnddDevices)))) {
|
||||
fprintf (stderr, "malloc() failed\n");
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
nfc_init (NULL);
|
||||
|
||||
nfc_connstring connstrings[MAX_DEVICE_COUNT];
|
||||
// List available devices
|
||||
nfc_list_devices (pnddDevices, MAX_DEVICE_COUNT, &szFound);
|
||||
size_t szFound = nfc_list_devices (NULL, connstrings, MAX_DEVICE_COUNT);
|
||||
|
||||
if (initiator_only_mode || target_only_mode) {
|
||||
if (szFound < 1) {
|
||||
|
|
@ -210,7 +206,7 @@ main (int argc, char *argv[])
|
|||
}
|
||||
else {
|
||||
if (szFound < 2) {
|
||||
ERR ("%zd device found but two connected devices are needed to relay NFC.", szFound);
|
||||
ERR ("%zd device found but two opened devices are needed to relay NFC.", szFound);
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
}
|
||||
|
|
@ -219,35 +215,37 @@ main (int argc, char *argv[])
|
|||
// Try to open the NFC reader used as initiator
|
||||
// Little hack to allow using initiator no matter if
|
||||
// there is already a target used locally or not on the same machine:
|
||||
// if there is more than one readers connected we connect to the second reader
|
||||
// if there is more than one readers opened we open the second reader
|
||||
// (we hope they're always detected in the same order)
|
||||
if (szFound == 1) {
|
||||
pndInitiator = nfc_connect (&(pnddDevices[0]));
|
||||
pndInitiator = nfc_open (NULL, connstrings[0]);
|
||||
} else {
|
||||
pndInitiator = nfc_connect (&(pnddDevices[1]));
|
||||
pndInitiator = nfc_open (NULL, connstrings[1]);
|
||||
}
|
||||
|
||||
if (!pndInitiator) {
|
||||
printf ("Error connecting NFC reader\n");
|
||||
printf ("Error opening NFC reader\n");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
printf ("Connected to the NFC reader device: %s\n", pndInitiator->acName);
|
||||
printf ("NFC reader device: %s opened\n", nfc_device_get_name (pndInitiator));
|
||||
|
||||
if (!nfc_initiator_init (pndInitiator)) {
|
||||
if (nfc_initiator_init (pndInitiator) < 0) {
|
||||
printf ("Error: fail initializing initiator\n");
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
nfc_exit (NULL);
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
// Try to find a ISO 14443-4A tag
|
||||
nfc_modulation_t nm = {
|
||||
nfc_modulation nm = {
|
||||
.nmt = NMT_ISO14443A,
|
||||
.nbr = NBR_106,
|
||||
};
|
||||
if (!nfc_initiator_select_passive_target (pndInitiator, nm, NULL, 0, &ntRealTarget)) {
|
||||
if (nfc_initiator_select_passive_target (pndInitiator, nm, NULL, 0, &ntRealTarget) < 0) {
|
||||
printf ("Error: no tag was found\n");
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
nfc_exit (NULL);
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
|
|
@ -256,22 +254,26 @@ main (int argc, char *argv[])
|
|||
if (initiator_only_mode) {
|
||||
if (print_hex_fd4(ntRealTarget.nti.nai.abtUid, ntRealTarget.nti.nai.szUidLen, "UID") != EXIT_SUCCESS) {
|
||||
fprintf (stderr, "Error while printing UID to FD4\n");
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
if (print_hex_fd4(ntRealTarget.nti.nai.abtAtqa, 2, "ATQA") != EXIT_SUCCESS) {
|
||||
fprintf (stderr, "Error while printing ATQA to FD4\n");
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
if (print_hex_fd4(&(ntRealTarget.nti.nai.btSak), 1, "SAK") != EXIT_SUCCESS) {
|
||||
fprintf (stderr, "Error while printing SAK to FD4\n");
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
if (print_hex_fd4(ntRealTarget.nti.nai.abtAts, ntRealTarget.nti.nai.szAtsLen, "ATS") != EXIT_SUCCESS) {
|
||||
fprintf (stderr, "Error while printing ATS to FD4\n");
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
|
@ -284,7 +286,7 @@ main (int argc, char *argv[])
|
|||
printf ("Hint: tag <---> initiator (relay) <---> target (relay) <---> original reader\n\n");
|
||||
}
|
||||
if (!initiator_only_mode) {
|
||||
nfc_target_t ntEmulatedTarget = {
|
||||
nfc_target ntEmulatedTarget = {
|
||||
.nm = {
|
||||
.nmt = NMT_ISO14443A,
|
||||
.nbr = NBR_106,
|
||||
|
|
@ -294,22 +296,25 @@ main (int argc, char *argv[])
|
|||
size_t foo;
|
||||
if (scan_hex_fd3(ntEmulatedTarget.nti.nai.abtUid, &(ntEmulatedTarget.nti.nai.szUidLen), "UID") != EXIT_SUCCESS) {
|
||||
fprintf (stderr, "Error while scanning UID from FD3\n");
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
if (scan_hex_fd3(ntEmulatedTarget.nti.nai.abtAtqa, &foo, "ATQA") != EXIT_SUCCESS) {
|
||||
fprintf (stderr, "Error while scanning ATQA from FD3\n");
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
if (scan_hex_fd3(&(ntEmulatedTarget.nti.nai.btSak), &foo, "SAK") != EXIT_SUCCESS) {
|
||||
fprintf (stderr, "Error while scanning SAK from FD3\n");
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
if (scan_hex_fd3(ntEmulatedTarget.nti.nai.abtAts, &(ntEmulatedTarget.nti.nai.szAtsLen), "ATS") != EXIT_SUCCESS) {
|
||||
fprintf (stderr, "Error while scanning ATS from FD3\n");
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
} else {
|
||||
|
|
@ -331,11 +336,11 @@ main (int argc, char *argv[])
|
|||
// PC/SC pseudo-ATR = 3B 80 80 01 01 if there is no historical bytes
|
||||
|
||||
// Creates ATS and copy max 48 bytes of Tk:
|
||||
byte_t * pbtTk;
|
||||
uint8_t * pbtTk;
|
||||
size_t szTk;
|
||||
pbtTk = iso14443a_locate_historical_bytes (ntEmulatedTarget.nti.nai.abtAts, ntEmulatedTarget.nti.nai.szAtsLen, &szTk);
|
||||
szTk = (szTk > 48) ? 48 : szTk;
|
||||
byte_t pbtTkt[48];
|
||||
uint8_t pbtTkt[48];
|
||||
memcpy(pbtTkt, pbtTk, szTk);
|
||||
ntEmulatedTarget.nti.nai.abtAts[0] = 0x75;
|
||||
ntEmulatedTarget.nti.nai.abtAts[1] = 0x33;
|
||||
|
|
@ -348,23 +353,26 @@ main (int argc, char *argv[])
|
|||
print_nfc_iso14443a_info (ntEmulatedTarget.nti.nai, false);
|
||||
|
||||
// Try to open the NFC emulator device
|
||||
pndTarget = nfc_connect (&(pnddDevices[0]));
|
||||
pndTarget = nfc_open (NULL, connstrings[0]);
|
||||
if (pndTarget == NULL) {
|
||||
printf ("Error connecting NFC emulator device\n");
|
||||
printf ("Error opening NFC emulator device\n");
|
||||
if (!target_only_mode) {
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
}
|
||||
nfc_exit (NULL);
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
|
||||
printf ("Connected to the NFC emulator device: %s\n", pndTarget->acName);
|
||||
printf ("NFC emulator device: %s opened\n", nfc_device_get_name (pndTarget));
|
||||
|
||||
if (!nfc_target_init (pndTarget, &ntEmulatedTarget, abtCapdu, &szCapduLen)) {
|
||||
szCapduLen = sizeof (abtCapdu);
|
||||
if (nfc_target_init (pndTarget, &ntEmulatedTarget, abtCapdu, szCapduLen, 0) < 0) {
|
||||
ERR ("%s", "Initialization of NFC emulator failed");
|
||||
if (!target_only_mode) {
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
}
|
||||
nfc_disconnect (pndTarget);
|
||||
nfc_close (pndTarget);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
printf ("%s\n", "Done, relaying frames now!");
|
||||
|
|
@ -373,27 +381,32 @@ main (int argc, char *argv[])
|
|||
|
||||
while (!quitting) {
|
||||
bool ret;
|
||||
int res = 0;
|
||||
if (!initiator_only_mode) {
|
||||
// Receive external reader command through target
|
||||
if (!nfc_target_receive_bytes(pndTarget,abtCapdu,&szCapduLen, NULL)) {
|
||||
if ((res = nfc_target_receive_bytes(pndTarget, abtCapdu, sizeof (abtCapdu), 0)) < 0) {
|
||||
nfc_perror (pndTarget, "nfc_target_receive_bytes");
|
||||
if (!target_only_mode) {
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
}
|
||||
nfc_disconnect (pndTarget);
|
||||
nfc_close (pndTarget);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
szCapduLen = (size_t) res;
|
||||
if (target_only_mode) {
|
||||
if (print_hex_fd4(abtCapdu, szCapduLen, "C-APDU") != EXIT_SUCCESS) {
|
||||
fprintf (stderr, "Error while printing C-APDU to FD4\n");
|
||||
nfc_disconnect (pndTarget);
|
||||
nfc_close (pndTarget);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (scan_hex_fd3(abtCapdu, &szCapduLen, "C-APDU") != EXIT_SUCCESS) {
|
||||
fprintf (stderr, "Error while scanning C-APDU from FD3\n");
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
|
@ -405,12 +418,13 @@ main (int argc, char *argv[])
|
|||
|
||||
if (!target_only_mode) {
|
||||
// Forward the frame to the original tag
|
||||
ret = nfc_initiator_transceive_bytes
|
||||
(pndInitiator, abtCapdu, szCapduLen, abtRapdu, &szRapduLen, NULL);
|
||||
ret = (nfc_initiator_transceive_bytes
|
||||
(pndInitiator, abtCapdu, szCapduLen, abtRapdu, &szRapduLen, 0) < 0) ? 0 : 1;
|
||||
} else {
|
||||
if (scan_hex_fd3(abtRapdu, &szRapduLen, "R-APDU") != EXIT_SUCCESS) {
|
||||
fprintf (stderr, "Error while scanning R-APDU from FD3\n");
|
||||
nfc_disconnect (pndTarget);
|
||||
nfc_close (pndTarget);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
ret = true;
|
||||
|
|
@ -430,20 +444,23 @@ main (int argc, char *argv[])
|
|||
}
|
||||
if (!initiator_only_mode) {
|
||||
// Transmit the response bytes
|
||||
if (!nfc_target_send_bytes(pndTarget, abtRapdu, szRapduLen, NULL)) {
|
||||
if (nfc_target_send_bytes(pndTarget, abtRapdu, szRapduLen, 0) < 0) {
|
||||
nfc_perror (pndTarget, "nfc_target_send_bytes");
|
||||
if (!target_only_mode) {
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
}
|
||||
if (!initiator_only_mode) {
|
||||
nfc_disconnect (pndTarget);
|
||||
nfc_close (pndTarget);
|
||||
nfc_exit (NULL);
|
||||
}
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
} else {
|
||||
if (print_hex_fd4(abtRapdu, szRapduLen, "R-APDU") != EXIT_SUCCESS) {
|
||||
fprintf (stderr, "Error while printing R-APDU to FD4\n");
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
nfc_exit (NULL);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
|
@ -451,11 +468,12 @@ main (int argc, char *argv[])
|
|||
}
|
||||
|
||||
if (!target_only_mode) {
|
||||
nfc_disconnect (pndInitiator);
|
||||
nfc_close (pndInitiator);
|
||||
}
|
||||
if (!initiator_only_mode) {
|
||||
nfc_disconnect (pndTarget);
|
||||
nfc_close (pndTarget);
|
||||
}
|
||||
nfc_exit (NULL);
|
||||
exit (EXIT_SUCCESS);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -33,7 +33,7 @@
|
|||
|
||||
#include "nfc-utils.h"
|
||||
|
||||
static const byte_t OddParity[256] = {
|
||||
static const uint8_t OddParity[256] = {
|
||||
1, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1,
|
||||
0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0,
|
||||
0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0,
|
||||
|
|
@ -52,14 +52,14 @@ static const byte_t OddParity[256] = {
|
|||
1, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1
|
||||
};
|
||||
|
||||
byte_t
|
||||
oddparity (const byte_t bt)
|
||||
uint8_t
|
||||
oddparity (const uint8_t bt)
|
||||
{
|
||||
return OddParity[bt];
|
||||
}
|
||||
|
||||
void
|
||||
oddparity_bytes_ts (const byte_t * pbtData, const size_t szLen, byte_t * pbtPar)
|
||||
oddparity_bytes_ts (const uint8_t *pbtData, const size_t szLen, uint8_t *pbtPar)
|
||||
{
|
||||
size_t szByteNr;
|
||||
// Calculate the parity bits for the command
|
||||
|
|
@ -69,7 +69,7 @@ oddparity_bytes_ts (const byte_t * pbtData, const size_t szLen, byte_t * pbtPar)
|
|||
}
|
||||
|
||||
void
|
||||
print_hex (const byte_t * pbtData, const size_t szBytes)
|
||||
print_hex (const uint8_t *pbtData, const size_t szBytes)
|
||||
{
|
||||
size_t szPos;
|
||||
|
||||
|
|
@ -80,7 +80,7 @@ print_hex (const byte_t * pbtData, const size_t szBytes)
|
|||
}
|
||||
|
||||
void
|
||||
print_hex_bits (const byte_t * pbtData, const size_t szBits)
|
||||
print_hex_bits (const uint8_t *pbtData, const size_t szBits)
|
||||
{
|
||||
uint8_t uRemainder;
|
||||
size_t szPos;
|
||||
|
|
@ -102,7 +102,7 @@ print_hex_bits (const byte_t * pbtData, const size_t szBits)
|
|||
}
|
||||
|
||||
void
|
||||
print_hex_par (const byte_t * pbtData, const size_t szBits, const byte_t * pbtDataPar)
|
||||
print_hex_par (const uint8_t *pbtData, const size_t szBits, const uint8_t *pbtDataPar)
|
||||
{
|
||||
uint8_t uRemainder;
|
||||
size_t szPos;
|
||||
|
|
@ -133,7 +133,7 @@ print_hex_par (const byte_t * pbtData, const size_t szBits, const byte_t * pbtDa
|
|||
#define SAK_ISO18092_COMPLIANT 0x40
|
||||
|
||||
void
|
||||
print_nfc_iso14443a_info (const nfc_iso14443a_info_t nai, bool verbose)
|
||||
print_nfc_iso14443a_info (const nfc_iso14443a_info nai, bool verbose)
|
||||
{
|
||||
printf (" ATQA (SENS_RES): ");
|
||||
print_hex (nai.abtAtqa, 2);
|
||||
|
|
@ -202,7 +202,7 @@ print_nfc_iso14443a_info (const nfc_iso14443a_info_t nai, bool verbose)
|
|||
|
||||
size_t offset = 1;
|
||||
if (nai.abtAts[0] & 0x10) { // TA(1) present
|
||||
byte_t TA = nai.abtAts[offset];
|
||||
uint8_t TA = nai.abtAts[offset];
|
||||
offset++;
|
||||
printf ("* Bit Rate Capability:\n");
|
||||
if (TA == 0) {
|
||||
|
|
@ -234,7 +234,7 @@ print_nfc_iso14443a_info (const nfc_iso14443a_info_t nai, bool verbose)
|
|||
}
|
||||
}
|
||||
if (nai.abtAts[0] & 0x20) { // TB(1) present
|
||||
byte_t TB= nai.abtAts[offset];
|
||||
uint8_t TB= nai.abtAts[offset];
|
||||
offset++;
|
||||
printf ("* Frame Waiting Time: %.4g ms\n",256.0*16.0*(1<<((TB & 0xf0) >> 4))/13560.0);
|
||||
if ((TB & 0x0f) == 0) {
|
||||
|
|
@ -244,7 +244,7 @@ print_nfc_iso14443a_info (const nfc_iso14443a_info_t nai, bool verbose)
|
|||
}
|
||||
}
|
||||
if (nai.abtAts[0] & 0x40) { // TC(1) present
|
||||
byte_t TC = nai.abtAts[offset];
|
||||
uint8_t TC = nai.abtAts[offset];
|
||||
offset++;
|
||||
if (TC & 0x1) {
|
||||
printf("* Node ADdress supported\n");
|
||||
|
|
@ -260,20 +260,20 @@ print_nfc_iso14443a_info (const nfc_iso14443a_info_t nai, bool verbose)
|
|||
if (nai.szAtsLen > offset) {
|
||||
printf ("* Historical bytes Tk: " );
|
||||
print_hex (nai.abtAts + offset, (nai.szAtsLen - offset));
|
||||
byte_t CIB = nai.abtAts[offset];
|
||||
uint8_t CIB = nai.abtAts[offset];
|
||||
offset++;
|
||||
if (CIB != 0x00 && CIB != 0x10 && (CIB & 0xf0) != 0x80) {
|
||||
printf(" * Proprietary format\n");
|
||||
if (CIB == 0xc1) {
|
||||
printf(" * Tag byte: Mifare or virtual cards of various types\n");
|
||||
byte_t L = nai.abtAts[offset];
|
||||
uint8_t L = nai.abtAts[offset];
|
||||
offset++;
|
||||
if (L != (nai.szAtsLen - offset)) {
|
||||
printf(" * Warning: Type Identification Coding length (%i)", L);
|
||||
printf(" not matching Tk length (%zi)\n", (nai.szAtsLen - offset));
|
||||
}
|
||||
if ((nai.szAtsLen - offset - 2) > 0) { // Omit 2 CRC bytes
|
||||
byte_t CTC = nai.abtAts[offset];
|
||||
uint8_t CTC = nai.abtAts[offset];
|
||||
offset++;
|
||||
printf(" * Chip Type: ");
|
||||
switch (CTC & 0xf0) {
|
||||
|
|
@ -316,7 +316,7 @@ print_nfc_iso14443a_info (const nfc_iso14443a_info_t nai, bool verbose)
|
|||
}
|
||||
}
|
||||
if ((nai.szAtsLen - offset) > 0) { // Omit 2 CRC bytes
|
||||
byte_t CVC = nai.abtAts[offset];
|
||||
uint8_t CVC = nai.abtAts[offset];
|
||||
offset++;
|
||||
printf(" * Chip Status: ");
|
||||
switch (CVC & 0xf0) {
|
||||
|
|
@ -350,7 +350,7 @@ print_nfc_iso14443a_info (const nfc_iso14443a_info_t nai, bool verbose)
|
|||
}
|
||||
}
|
||||
if ((nai.szAtsLen - offset) > 0) { // Omit 2 CRC bytes
|
||||
byte_t VCS = nai.abtAts[offset];
|
||||
uint8_t VCS = nai.abtAts[offset];
|
||||
offset++;
|
||||
printf(" * Specifics (Virtual Card Selection):\n");
|
||||
if ((VCS & 0x09) == 0x00) {
|
||||
|
|
@ -530,7 +530,7 @@ print_nfc_iso14443a_info (const nfc_iso14443a_info_t nai, bool verbose)
|
|||
}
|
||||
|
||||
void
|
||||
print_nfc_felica_info (const nfc_felica_info_t nfi, bool verbose)
|
||||
print_nfc_felica_info (const nfc_felica_info nfi, bool verbose)
|
||||
{
|
||||
(void) verbose;
|
||||
printf (" ID (NFCID2): ");
|
||||
|
|
@ -542,7 +542,7 @@ print_nfc_felica_info (const nfc_felica_info_t nfi, bool verbose)
|
|||
}
|
||||
|
||||
void
|
||||
print_nfc_jewel_info (const nfc_jewel_info_t nji, bool verbose)
|
||||
print_nfc_jewel_info (const nfc_jewel_info nji, bool verbose)
|
||||
{
|
||||
(void) verbose;
|
||||
printf (" ATQA (SENS_RES): ");
|
||||
|
|
@ -555,7 +555,7 @@ print_nfc_jewel_info (const nfc_jewel_info_t nji, bool verbose)
|
|||
#define PI_NAD_SUPPORTED 0x01
|
||||
#define PI_CID_SUPPORTED 0x02
|
||||
void
|
||||
print_nfc_iso14443b_info (const nfc_iso14443b_info_t nbi, bool verbose)
|
||||
print_nfc_iso14443b_info (const nfc_iso14443b_info nbi, bool verbose)
|
||||
{
|
||||
const int iMaxFrameSizes[] = { 16, 24, 32, 40, 48, 64, 96, 128, 256 };
|
||||
printf (" PUPI: ");
|
||||
|
|
@ -610,7 +610,7 @@ print_nfc_iso14443b_info (const nfc_iso14443b_info_t nbi, bool verbose)
|
|||
}
|
||||
|
||||
void
|
||||
print_nfc_iso14443bi_info (const nfc_iso14443bi_info_t nii, bool verbose)
|
||||
print_nfc_iso14443bi_info (const nfc_iso14443bi_info nii, bool verbose)
|
||||
{
|
||||
printf (" DIV: ");
|
||||
print_hex (nii.abtDIV, 4);
|
||||
|
|
@ -634,7 +634,7 @@ print_nfc_iso14443bi_info (const nfc_iso14443bi_info_t nii, bool verbose)
|
|||
}
|
||||
|
||||
void
|
||||
print_nfc_iso14443b2sr_info (const nfc_iso14443b2sr_info_t nsi, bool verbose)
|
||||
print_nfc_iso14443b2sr_info (const nfc_iso14443b2sr_info nsi, bool verbose)
|
||||
{
|
||||
(void) verbose;
|
||||
printf (" UID: ");
|
||||
|
|
@ -642,7 +642,7 @@ print_nfc_iso14443b2sr_info (const nfc_iso14443b2sr_info_t nsi, bool verbose)
|
|||
}
|
||||
|
||||
void
|
||||
print_nfc_iso14443b2ct_info (const nfc_iso14443b2ct_info_t nci, bool verbose)
|
||||
print_nfc_iso14443b2ct_info (const nfc_iso14443b2ct_info nci, bool verbose)
|
||||
{
|
||||
(void) verbose;
|
||||
uint32_t uid;
|
||||
|
|
@ -655,7 +655,7 @@ print_nfc_iso14443b2ct_info (const nfc_iso14443b2ct_info_t nci, bool verbose)
|
|||
}
|
||||
|
||||
void
|
||||
print_nfc_dep_info (const nfc_dep_info_t ndi, bool verbose)
|
||||
print_nfc_dep_info (const nfc_dep_info ndi, bool verbose)
|
||||
{
|
||||
(void) verbose;
|
||||
printf (" NFCID3: ");
|
||||
|
|
@ -670,53 +670,8 @@ print_nfc_dep_info (const nfc_dep_info_t ndi, bool verbose)
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Tries to parse arguments to find device descriptions.
|
||||
* @return Returns the list of found device descriptions.
|
||||
*/
|
||||
nfc_device_desc_t *
|
||||
parse_args (int argc, const char *argv[], size_t * szFound, bool * verbose)
|
||||
{
|
||||
nfc_device_desc_t *pndd = 0;
|
||||
int arg;
|
||||
*szFound = 0;
|
||||
|
||||
// Get commandline options
|
||||
for (arg = 1; arg < argc; arg++) {
|
||||
|
||||
if (0 == strcmp (argv[arg], "--device")) {
|
||||
// FIXME: this device selection by command line options is terrible & does not support USB/PCSC drivers
|
||||
if (argc > arg + 1) {
|
||||
char buffer[256];
|
||||
|
||||
pndd = malloc (sizeof (nfc_device_desc_t));
|
||||
|
||||
strncpy (buffer, argv[++arg], 256);
|
||||
|
||||
// Driver.
|
||||
pndd->pcDriver = (char *) malloc (256);
|
||||
strcpy (pndd->pcDriver, strtok (buffer, ":"));
|
||||
|
||||
// Port.
|
||||
strcpy (pndd->acPort, strtok (NULL, ":"));
|
||||
|
||||
// Speed.
|
||||
sscanf (strtok (NULL, ":"), "%u", &pndd->uiSpeed);
|
||||
|
||||
*szFound = 1;
|
||||
} else {
|
||||
errx (1, "usage: %s [--device driver:port:speed]", argv[0]);
|
||||
}
|
||||
}
|
||||
if ((0 == strcmp (argv[arg], "-v")) || (0 == strcmp (argv[arg], "--verbose"))) {
|
||||
*verbose = true;
|
||||
}
|
||||
}
|
||||
return pndd;
|
||||
}
|
||||
|
||||
const char *
|
||||
str_nfc_baud_rate (const nfc_baud_rate_t nbr)
|
||||
str_nfc_baud_rate (const nfc_baud_rate nbr)
|
||||
{
|
||||
switch(nbr) {
|
||||
case NBR_UNDEFINED:
|
||||
|
|
@ -739,7 +694,7 @@ str_nfc_baud_rate (const nfc_baud_rate_t nbr)
|
|||
}
|
||||
|
||||
void
|
||||
print_nfc_target (const nfc_target_t nt, bool verbose)
|
||||
print_nfc_target (const nfc_target nt, bool verbose)
|
||||
{
|
||||
switch(nt.nm.nmt) {
|
||||
case NMT_ISO14443A:
|
||||
|
|
@ -771,7 +726,7 @@ print_nfc_target (const nfc_target_t nt, bool verbose)
|
|||
print_nfc_iso14443b2ct_info (nt.nti.nci, verbose);
|
||||
break;
|
||||
case NMT_DEP:
|
||||
printf ("D.E.P. (%s) target:\n", str_nfc_baud_rate(nt.nm.nbr));
|
||||
printf ("D.E.P. (%s, %s) target:\n", str_nfc_baud_rate(nt.nm.nbr), (nt.nti.ndi.ndm == NDM_ACTIVE)? "active mode" : "passive mode");
|
||||
print_nfc_dep_info (nt.nti.ndi, verbose);
|
||||
break;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -79,24 +79,23 @@
|
|||
# define ERR(...) warnx ("ERROR: " __VA_ARGS__ )
|
||||
#endif
|
||||
|
||||
byte_t oddparity (const byte_t bt);
|
||||
void oddparity_byte_ts (const byte_t * pbtData, const size_t szLen, byte_t * pbtPar);
|
||||
uint8_t oddparity (const uint8_t bt);
|
||||
void oddparity_uint8_ts (const uint8_t *pbtData, const size_t szLen, uint8_t *pbtPar);
|
||||
|
||||
void print_hex (const byte_t * pbtData, const size_t szLen);
|
||||
void print_hex_bits (const byte_t * pbtData, const size_t szBits);
|
||||
void print_hex_par (const byte_t * pbtData, const size_t szBits, const byte_t * pbtDataPar);
|
||||
void print_hex (const uint8_t *pbtData, const size_t szLen);
|
||||
void print_hex_bits (const uint8_t *pbtData, const size_t szBits);
|
||||
void print_hex_par (const uint8_t *pbtData, const size_t szBits, const uint8_t *pbtDataPar);
|
||||
|
||||
void print_nfc_iso14443a_info (const nfc_iso14443a_info_t nai, bool verbose);
|
||||
void print_nfc_iso14443b_info (const nfc_iso14443b_info_t nbi, bool verbose);
|
||||
void print_nfc_iso14443bi_info (const nfc_iso14443bi_info_t nii, bool verbose);
|
||||
void print_nfc_iso14443b2sr_info (const nfc_iso14443b2sr_info_t nsi, bool verbose);
|
||||
void print_nfc_iso14443b2ct_info (const nfc_iso14443b2ct_info_t nci, bool verbose);
|
||||
void print_nfc_felica_info (const nfc_felica_info_t nfi, bool verbose);
|
||||
void print_nfc_jewel_info (const nfc_jewel_info_t nji, bool verbose);
|
||||
void print_nfc_dep_info (const nfc_dep_info_t ndi, bool verbose);
|
||||
void print_nfc_iso14443a_info (const nfc_iso14443a_info nai, bool verbose);
|
||||
void print_nfc_iso14443b_info (const nfc_iso14443b_info nbi, bool verbose);
|
||||
void print_nfc_iso14443bi_info (const nfc_iso14443bi_info nii, bool verbose);
|
||||
void print_nfc_iso14443b2sr_info (const nfc_iso14443b2sr_info nsi, bool verbose);
|
||||
void print_nfc_iso14443b2ct_info (const nfc_iso14443b2ct_info nci, bool verbose);
|
||||
void print_nfc_felica_info (const nfc_felica_info nfi, bool verbose);
|
||||
void print_nfc_jewel_info (const nfc_jewel_info nji, bool verbose);
|
||||
void print_nfc_dep_info (const nfc_dep_info ndi, bool verbose);
|
||||
const char * str_nfc_baud_rate (const nfc_baud_rate nbr);
|
||||
|
||||
void print_nfc_target (const nfc_target_t nt, bool verbose);
|
||||
|
||||
nfc_device_desc_t *parse_args (int argc, const char *argv[], size_t * szFound, bool * verbose);
|
||||
void print_nfc_target (const nfc_target nt, bool verbose);
|
||||
|
||||
#endif
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue