/** * @brief try to find a valid tag * @return pointer on a valid tag or NULL. */ nfc_target* ned_select_tag(nfc_device* nfc_device, nfc_target* tag) { nfc_target* rv = malloc( sizeof(nfc_target) ); nfc_modulation nm = { .nmt = NMT_ISO14443A, .nbr = NBR_106 }; if ( tag == NULL ) { // We are looking for any tag. // Poll for a ISO14443A (MIFARE) tag if ( nfc_initiator_select_passive_target ( nfc_device, nm, NULL, 0, rv ) < 0 ) { free (rv); rv = NULL; } } else { // tag is not NULL, we are looking for specific tag // debug_print_tag(tag); if ( nfc_initiator_select_passive_target ( nfc_device, tag->nm, tag->nti.nai.abtUid, tag->nti.nai.szUidLen, rv ) < 0 ) { free (rv); rv = NULL; } } if (rv != NULL) { nfc_initiator_deselect_target ( nfc_device ); } return rv; }
/* * call-seq: * deselect * * Deselect the current tag */ static VALUE dev_deselect(VALUE self) { nfc_device * dev; Data_Get_Struct(self, nfc_device, dev); nfc_initiator_deselect_target(dev); return self; }
/** * @brief Disconnect from a NFC device * @param pnd \a nfc_device_t struct pointer that represent currently used device * * Initiator's selected tag is disconnected and the device, including allocated \a nfc_device_t struct, is released. */ void nfc_disconnect (nfc_device_t * pnd) { if (pnd) { // Release and deselect all active communications nfc_initiator_deselect_target (pnd); // Disable RF field to avoid heating nfc_configure (pnd, NDO_ACTIVATE_FIELD, false); // Disconnect, clean up and release the device pnd->pdc->disconnect (pnd); } }
void NFCReaderUnit::disconnect() { if (d_insertedChip && d_chips.find(d_insertedChip) != d_chips.end()) { if (d_chips[d_insertedChip].nm.nmt == NMT_ISO14443A) { LOG(DEBUGS) << "Deselecting target"; nfc_initiator_deselect_target(d_device); LOG(DEBUGS) << "Target deselected"; } } d_chip_connected = false; }
/* * Terminate connection with the provided tag. */ int mifare_ultralight_disconnect (MifareTag tag) { ASSERT_ACTIVE (tag); ASSERT_MIFARE_ULTRALIGHT (tag); if (nfc_initiator_deselect_target (tag->device) >= 0) { tag->active = 0; } else { errno = EIO; return -1; } return 0; }
/* * Terminate connection with the provided tag. */ int mifare_desfire_disconnect (MifareTag tag) { ASSERT_ACTIVE (tag); ASSERT_MIFARE_DESFIRE (tag); free (MIFARE_DESFIRE (tag)->session_key); MIFARE_DESFIRE(tag)->session_key = NULL; if (nfc_initiator_deselect_target (tag->device)) { tag->active = 0; } return 0; }
/* * Callback for freefare_tag_new to test presence of a MIFARE UltralightC on the reader. */ bool is_mifare_ultralightc_on_reader (nfc_device *device, nfc_iso14443a_info nai) { int ret; uint8_t cmd_step1[2]; uint8_t res_step1[9]; cmd_step1[0] = 0x1A; cmd_step1[1] = 0x00; nfc_target pnti; nfc_modulation modulation = { .nmt = NMT_ISO14443A, .nbr = NBR_106 }; nfc_initiator_select_passive_target (device, modulation, nai.abtUid, nai.szUidLen, &pnti); nfc_device_set_property_bool (device, NP_EASY_FRAMING, false); ret = nfc_initiator_transceive_bytes (device, cmd_step1, sizeof (cmd_step1), res_step1, sizeof(res_step1), 0); nfc_device_set_property_bool (device, NP_EASY_FRAMING, true); nfc_initiator_deselect_target (device); return ret >= 0; }
void tag_get_uid(nfc_device* nfc_device, nfc_target* tag, char **dest) { debug_print_tag(tag); /// @TODO We don't need to reselect tag to get his UID: nfc_target contains this data. // Poll for a ISO14443A (MIFARE) tag if ( nfc_initiator_select_passive_target ( nfc_device, tag->nm, tag->nti.nai.abtUid, tag->nti.nai.szUidLen, tag ) ) { *dest = malloc(tag->nti.nai.szUidLen*sizeof(char)*2+1); size_t szPos; char *pcUid = *dest; for (szPos=0; szPos < tag->nti.nai.szUidLen; szPos++) { sprintf(pcUid, "%02x",tag->nti.nai.abtUid[szPos]); pcUid += 2; } pcUid[0]='\0'; DBG( "ISO14443A tag found: UID=0x%s", *dest ); nfc_initiator_deselect_target ( nfc_device ); } else { *dest = NULL; DBG("%s", "ISO14443A (MIFARE) tag not found" ); return; } }
/* * Get a list of the MIFARE targets near to the provided NFC initiator. * * The list has to be freed using the freefare_free_tags() function. */ MifareTag * freefare_get_tags (nfc_device_t *device) { MifareTag *tags = NULL; int tag_count = 0; nfc_initiator_init(device); // Drop the field for a while nfc_configure(device,NDO_ACTIVATE_FIELD,false); // Let the reader only try once to find a tag nfc_configure(device,NDO_INFINITE_SELECT,false); // Configure the CRC and Parity settings nfc_configure(device,NDO_HANDLE_CRC,true); nfc_configure(device,NDO_HANDLE_PARITY,true); // Enable field so more power consuming cards can power themselves up nfc_configure(device,NDO_ACTIVATE_FIELD,true); // Poll for a ISO14443A (MIFARE) tag nfc_target_info_t target_info; tags = malloc(sizeof (void *)); if(!tags) return NULL; tags[0] = NULL; while (nfc_initiator_select_passive_target(device,NM_ISO14443A_106,NULL,0,&target_info)) { bool found = false; struct supported_tag *tag_info; for (size_t i = 0; i < sizeof (supported_tags) / sizeof (struct supported_tag); i++) { if (((target_info.nai.szUidLen == 4) || (target_info.nai.abtUid[0] == NXP_MANUFACTURER_CODE)) && (target_info.nai.btSak == supported_tags[i].SAK) && (target_info.nai.szAtsLen == supported_tags[i].ATS_length) && (0 == memcmp (target_info.nai.abtAts, supported_tags[i].ATS, supported_tags[i].ATS_length))) { tag_info = &(supported_tags[i]); found = true; break; } } if (!found) goto deselect; tag_count++; /* (Re)Allocate memory for the found MIFARE targets array */ MifareTag *p = realloc (tags, (tag_count + 1) * sizeof (MifareTag)); if (p) tags = p; else return tags; // FAIL! Return what has been found so far. /* Allocate memory for the found MIFARE target */ switch (tag_info->type) { case CLASSIC_1K: case CLASSIC_4K: tags[tag_count-1] = mifare_classic_tag_new (); break; case DESFIRE: tags[tag_count-1] = mifare_desfire_tag_new (0); //JIM break; case ULTRALIGHT: tags[tag_count-1] = mifare_ultralight_tag_new (); break; } if (!tags[tag_count-1]) return tags; // FAIL! Return what has been found before. /* * Initialize common fields * (Target specific fields are initialized in mifare_*_tag_new()) */ (tags[tag_count-1])->device = device; (tags[tag_count-1])->info = target_info.nai; (tags[tag_count-1])->active = 0; (tags[tag_count-1])->tag_info = tag_info; tags[tag_count] = NULL; deselect: nfc_initiator_deselect_target (device); } return tags; }
/** * @brief List passive or emulated tags * @return Returns \c true if action was successfully performed; otherwise returns \c false. * * @param pnd \a nfc_device_t struct pointer that represent currently used device * @param nm desired modulation * @param[out] ant array of \a nfc_target_t that will be filled with targets info * @param szTargets size of \a ant (will be the max targets listed) * @param[out] pszTargetFound pointer where target found counter will be stored * * The NFC device will try to find the available passive tags. Some NFC devices * are capable to emulate passive tags. The standards (ISO18092 and ECMA-340) * describe the modulation that can be used for reader to passive * communications. The chip needs to know with what kind of tag it is dealing * with, therefore the initial modulation and speed (106, 212 or 424 kbps) * should be supplied. */ bool nfc_initiator_list_passive_targets (nfc_device_t * pnd, const nfc_modulation_t nm, nfc_target_t ant[], const size_t szTargets, size_t * pszTargetFound) { nfc_target_t nt; size_t szTargetFound = 0; byte_t *pbtInitData = NULL; size_t szInitDataLen = 0; pnd->iLastError = 0; // Drop the field for a while if (!nfc_configure (pnd, NDO_ACTIVATE_FIELD, false)) { return false; } // Let the reader only try once to find a tag if (!nfc_configure (pnd, NDO_INFINITE_SELECT, false)) { return false; } // Enable field so more power consuming cards can power themselves up if (!nfc_configure (pnd, NDO_ACTIVATE_FIELD, true)) { return false; } switch (nm.nmt) { case NMT_ISO14443B: { // Application Family Identifier (AFI) must equals 0x00 in order to wakeup all ISO14443-B PICCs (see ISO/IEC 14443-3) pbtInitData = (byte_t *) "\x00"; szInitDataLen = 1; } break; case NMT_FELICA: { // polling payload must be present (see ISO/IEC 18092 11.2.2.5) pbtInitData = (byte_t *) "\x00\xff\xff\x01\x00"; szInitDataLen = 5; } break; default: // nothing to do break; } while (nfc_initiator_select_passive_target (pnd, nm, pbtInitData, szInitDataLen, &nt)) { nfc_initiator_deselect_target (pnd); if (szTargets > szTargetFound) { memcpy (&(ant[szTargetFound]), &nt, sizeof (nfc_target_t)); } else { break; } szTargetFound++; // deselect has no effect on FeliCa and Jewel cards so we'll stop after one... if ((nm.nmt == NMT_FELICA) || (nm.nmt == NMT_JEWEL)) { break; } } *pszTargetFound = szTargetFound; return true; }