-include common/Makefile.common
-
+GZIP=gzip
+# Windows' echo echos its input verbatim, on Posix there is some
+# amount of shell command line parsing going on. echo "" on
+# Windows yields literal "", on Linux yields an empty line
+ifeq ($(shell echo ""),)
+# This is probably a proper system, so we can use uname
+DELETE=rm -rf
+FLASH_TOOL=client/flasher
+platform=$(shell uname)
+ifneq (,$(findstring MINGW,$(platform)))
+FLASH_PORT=com3
+PATHSEP=\\#
+else
FLASH_PORT=/dev/ttyACM0
+PATHSEP=/
+endif
+else
+# Assume that we are running on native Windows
+DELETE=del /q
+FLASH_TOOL=client/flasher.exe
+platform=Windows
+FLASH_PORT=com3
+PATHSEP=\\#
+endif
-all clean: %: client/% bootrom/% armsrc/% recovery/%
+all clean: %: client/% bootrom/% armsrc/% recovery/% mfkey/%
bootrom/%: FORCE
- $(MAKE) -C bootrom $(patsubst bootrom/%,%,$@)
+ $(MAKE) -C bootrom $(patsubst bootrom/%, %, $@)
armsrc/%: FORCE
- $(MAKE) -C armsrc $(patsubst armsrc/%,%,$@)
+ $(MAKE) -C armsrc $(patsubst armsrc/%, %, $@)
client/%: FORCE
- $(MAKE) -C client $(patsubst client/%,%,$@)
+ $(MAKE) -C client $(patsubst client/%, %, $@)
recovery/%: FORCE
- $(MAKE) -C recovery $(patsubst recovery/%,%,$@)
+ $(MAKE) -C recovery $(patsubst recovery/%, %, $@)
+mfkey/%: FORCE
+ $(MAKE) -C tools/mfkey $(patsubst mfkey/%, %, $@)
FORCE: # Dummy target to force remake in the subdirectories, even if files exist (this Makefile doesn't know about the prerequisites)
.PHONY: all clean help _test flash-bootrom flash-os flash-all FORCE
client: client/all
+mfkey: mfkey/all
+
flash-bootrom: bootrom/obj/bootrom.elf $(FLASH_TOOL)
$(FLASH_TOOL) $(FLASH_PORT) -b $(subst /,$(PATHSEP),$<)
irc.freenode.org #proxmark3
-or-
http://webchat.freenode.net/?channels=#proxmark3
+
+ * The Homebrew formula repository
+ https://github.com/Proxmark/homebrew-proxmark3
DEVELOPMENT:
SpinDelay(300);
}
}
- if (!iso14443a_select_card(uid, &hi14a_card[selected], &cuid))
+ if (!iso14443a_select_card(uid, &hi14a_card[selected], &cuid, true, 0))
continue;
else
{
// power up the field
iso14443a_setup(FPGA_HF_ISO14443A_READER_MOD);
// select the card
- return_code = iso14443a_select_card(uid, &card_select_info, NULL);
+ return_code = iso14443a_select_card(uid, &card_select_info, NULL, true, 0);
if (return_code == 1) {
// send the PPS request
ReaderTransmit((uint8_t *)pps, sizeof(pps), NULL);
// Routines to support ISO 14443 type A.
//-----------------------------------------------------------------------------
+#include "iso14443a.h"
+
#include "proxmark3.h"
#include "apps.h"
#include "util.h"
#include "string.h"
#include "cmd.h"
#include "iso14443crc.h"
-#include "iso14443a.h"
#include "crapto1/crapto1.h"
#include "mifareutil.h"
+#include "mifaresniff.h"
#include "BigBuf.h"
#include "protocols.h"
#include "parity.h"
+typedef struct {
+ enum {
+ DEMOD_UNSYNCD,
+ // DEMOD_HALF_SYNCD,
+ // DEMOD_MOD_FIRST_HALF,
+ // DEMOD_NOMOD_FIRST_HALF,
+ DEMOD_MANCHESTER_DATA
+ } state;
+ uint16_t twoBits;
+ uint16_t highCnt;
+ uint16_t bitCount;
+ uint16_t collisionPos;
+ uint16_t syncBit;
+ uint8_t parityBits;
+ uint8_t parityLen;
+ uint16_t shiftReg;
+ uint16_t samples;
+ uint16_t len;
+ uint32_t startTime, endTime;
+ uint8_t *output;
+ uint8_t *parity;
+} tDemod;
+
+typedef enum {
+ MOD_NOMOD = 0,
+ MOD_SECOND_HALF,
+ MOD_FIRST_HALF,
+ MOD_BOTH_HALVES
+ } Modulation_t;
+
+typedef struct {
+ enum {
+ STATE_UNSYNCD,
+ STATE_START_OF_COMMUNICATION,
+ STATE_MILLER_X,
+ STATE_MILLER_Y,
+ STATE_MILLER_Z,
+ // DROP_NONE,
+ // DROP_FIRST_HALF,
+ } state;
+ uint16_t shiftReg;
+ int16_t bitCount;
+ uint16_t len;
+ uint16_t byteCntMax;
+ uint16_t posCnt;
+ uint16_t syncBit;
+ uint8_t parityBits;
+ uint8_t parityLen;
+ uint32_t fourBits;
+ uint32_t startTime, endTime;
+ uint8_t *output;
+ uint8_t *parity;
+} tUart;
static uint32_t iso14a_timeout;
int rsamples = 0;
#define REQUEST_GUARD_TIME (7000/16 + 1)
// minimum time between last modulation of tag and next start bit from reader to tag: 1172 carrier cycles
#define FRAME_DELAY_TIME_PICC_TO_PCD (1172/16 + 1)
-// bool LastCommandWasRequest = FALSE;
+// bool LastCommandWasRequest = false;
//
// Total delays including SSC-Transfers between ARM and FPGA. These are in carrier clock cycles (1/13,56MHz)
#define SEC_Y 0x00
#define SEC_Z 0xc0
-
void iso14a_set_trigger(bool enable) {
trigger = enable;
}
// 0111 - a 2 tick wide pause shifted left
// 1001 - a 2 tick wide pause shifted right
const bool Mod_Miller_LUT[] = {
- FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE,
- FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE
+ false, true, false, true, false, false, false, true,
+ false, true, false, false, false, false, false, false
};
#define IsMillerModulationNibble1(b) (Mod_Miller_LUT[(b & 0x000000F0) >> 4])
#define IsMillerModulationNibble2(b) (Mod_Miller_LUT[(b & 0x0000000F)])
Uart.parityBits <<= 1; // add a (void) parity bit
Uart.parityBits <<= (8 - (Uart.len&0x0007)); // left align parity bits
Uart.parity[Uart.parityLen++] = Uart.parityBits; // and store it
- return TRUE;
+ return true;
} else if (Uart.len & 0x0007) { // there are some parity bits to store
Uart.parityBits <<= (8 - (Uart.len&0x0007)); // left align remaining parity bits
Uart.parity[Uart.parityLen++] = Uart.parityBits; // and store them
}
if (Uart.len) {
- return TRUE; // we are finished with decoding the raw data sequence
+ return true; // we are finished with decoding the raw data sequence
} else {
UartReset(); // Nothing received - start over
}
}
- return FALSE; // not finished yet, need more data
+ return false; // not finished yet, need more data
}
// Lookup-Table to decide if 4 raw bits are a modulation.
// We accept three or four "1" in any position
const bool Mod_Manchester_LUT[] = {
- FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE,
- FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE
+ false, false, false, false, false, false, false, true,
+ false, false, false, true, false, true, true, true
};
#define IsManchesterModulationNibble1(b) (Mod_Manchester_LUT[(b & 0x00F0) >> 4])
Demod.parityBits <<= 1; // add a (void) parity bit
Demod.parityBits <<= (8 - (Demod.len&0x0007)); // left align remaining parity bits
Demod.parity[Demod.parityLen++] = Demod.parityBits; // and store them
- return TRUE;
+ return true;
} else if (Demod.len & 0x0007) { // there are some parity bits to store
Demod.parityBits <<= (8 - (Demod.len&0x0007)); // left align remaining parity bits
Demod.parity[Demod.parityLen++] = Demod.parityBits; // and store them
}
if (Demod.len) {
- return TRUE; // we are finished with decoding the raw data sequence
+ return true; // we are finished with decoding the raw data sequence
} else { // nothing received. Start over
DemodReset();
}
}
- return FALSE; // not finished yet, need more data
+ return false; // not finished yet, need more data
}
//=============================================================================
// init trace buffer
clear_trace();
- set_tracing(TRUE);
+ set_tracing(true);
uint8_t *data = dmaBuf;
uint8_t previous_data = 0;
int maxDataLen = 0;
int dataLen = 0;
- bool TagIsActive = FALSE;
- bool ReaderIsActive = FALSE;
+ bool TagIsActive = false;
+ bool ReaderIsActive = false;
// Set up the demodulator for tag -> reader responses.
DemodInit(receivedResponse, receivedResponsePar);
// We won't start recording the frames that we acquire until we trigger;
// a good trigger condition to get started is probably when we see a
// response from the tag.
- // triggered == FALSE -- to wait first for card
+ // triggered == false -- to wait first for card
bool triggered = !(param & 0x03);
// And now we loop, receiving samples.
- for(uint32_t rsamples = 0; TRUE; ) {
+ for(uint32_t rsamples = 0; true; ) {
if(BUTTON_PRESS()) {
DbpString("cancelled by button");
LED_C_ON();
// check - if there is a short 7bit request from reader
- if ((!triggered) && (param & 0x02) && (Uart.len == 1) && (Uart.bitCount == 7)) triggered = TRUE;
+ if ((!triggered) && (param & 0x02) && (Uart.len == 1) && (Uart.bitCount == 7)) triggered = true;
if(triggered) {
if (!LogTrace(receivedCmd,
Uart.startTime*16 - DELAY_READER_AIR2ARM_AS_SNIFFER,
Uart.endTime*16 - DELAY_READER_AIR2ARM_AS_SNIFFER,
Uart.parity,
- TRUE)) break;
+ true)) break;
}
/* And ready to receive another command. */
UartReset();
Demod.startTime*16 - DELAY_TAG_AIR2ARM_AS_SNIFFER,
Demod.endTime*16 - DELAY_TAG_AIR2ARM_AS_SNIFFER,
Demod.parity,
- FALSE)) break;
+ false)) break;
- if ((!triggered) && (param & 0x01)) triggered = TRUE;
+ if ((!triggered) && (param & 0x01)) triggered = true;
// And ready to receive another response.
DemodReset();
//-----------------------------------------------------------------------------
// Wait for commands from reader
// Stop when button is pressed
-// Or return TRUE when command is captured
+// Or return true when command is captured
//-----------------------------------------------------------------------------
static int GetIso14443aCommandFromReader(uint8_t *received, uint8_t *parity, int *len)
{
for(;;) {
WDT_HIT();
- if(BUTTON_PRESS()) return FALSE;
+ if(BUTTON_PRESS()) return false;
if(AT91C_BASE_SSC->SSC_SR & (AT91C_SSC_RXRDY)) {
b = (uint8_t)AT91C_BASE_SSC->SSC_RHR;
if(MillerDecoding(b, 0)) {
*len = Uart.len;
- return TRUE;
+ return true;
}
}
}
// clear trace
clear_trace();
- set_tracing(TRUE);
+ set_tracing(true);
// Prepare the responses of the anticollision phase
// there will be not enough time to do this at the moment the reader sends it REQA
} else if(receivedCmd[0] == 0x50) { // Received a HALT
if (tracing) {
- LogTrace(receivedCmd, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(receivedCmd, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
}
p_response = NULL;
} else if(receivedCmd[0] == 0x60 || receivedCmd[0] == 0x61) { // Received an authentication request
}
} else if (order == 7 && len == 8) { // Received {nr] and {ar} (part of authentication)
if (tracing) {
- LogTrace(receivedCmd, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(receivedCmd, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
}
uint32_t nr = bytes_to_num(receivedCmd,4);
uint32_t ar = bytes_to_num(receivedCmd+4,4);
default: {
// Never seen this command before
if (tracing) {
- LogTrace(receivedCmd, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(receivedCmd, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
}
Dbprintf("Received unknown command (len=%d):",len);
Dbhexdump(len,receivedCmd,false);
if (prepare_tag_modulation(&dynamic_response_info,DYNAMIC_MODULATION_BUFFER_SIZE) == false) {
Dbprintf("Error preparing tag response");
if (tracing) {
- LogTrace(receivedCmd, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(receivedCmd, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
}
break;
}
// include correction bit if necessary
if (Uart.parityBits & 0x01) {
- correctionNeeded = TRUE;
+ correctionNeeded = true;
}
if(correctionNeeded) {
// 1236, so correction bit needed
uint16_t exact_fdt = (approx_fdt - 20 + 32)/64 * 64 + 20;
reader_EndTime = tag_StartTime - exact_fdt;
reader_StartTime = reader_EndTime - reader_modlen;
- if (!LogTrace(reader_data, reader_len, reader_StartTime, reader_EndTime, reader_Parity, TRUE)) {
- return FALSE;
- } else return(!LogTrace(tag_data, tag_len, tag_StartTime, tag_EndTime, tag_Parity, FALSE));
+ if (!LogTrace(reader_data, reader_len, reader_StartTime, reader_EndTime, reader_Parity, true)) {
+ return false;
+ } else return(!LogTrace(tag_data, tag_len, tag_StartTime, tag_EndTime, tag_Parity, false));
} else {
- return TRUE;
+ return true;
}
}
//-----------------------------------------------------------------------------
// Wait a certain time for tag response
-// If a response is captured return TRUE
-// If it takes too long return FALSE
+// If a response is captured return true
+// If it takes too long return false
//-----------------------------------------------------------------------------
static int GetIso14443aAnswerFromTag(uint8_t *receivedResponse, uint8_t *receivedResponsePar, uint16_t offset)
{
b = (uint8_t)AT91C_BASE_SSC->SSC_RHR;
if(ManchesterDecoding(b, offset, 0)) {
NextTransferTime = MAX(NextTransferTime, Demod.endTime - (DELAY_AIR2ARM_AS_READER + DELAY_ARM2AIR_AS_READER)/16 + FRAME_DELAY_TIME_PICC_TO_PCD);
- return TRUE;
+ return true;
} else if (c++ > iso14a_timeout && Demod.state == DEMOD_UNSYNCD) {
- return FALSE;
+ return false;
}
}
}
// Log reader command in trace buffer
if (tracing) {
- LogTrace(frame, nbytes(bits), LastTimeProxToAirStart*16 + DELAY_ARM2AIR_AS_READER, (LastTimeProxToAirStart + LastProxToAirDuration)*16 + DELAY_ARM2AIR_AS_READER, par, TRUE);
+ LogTrace(frame, nbytes(bits), LastTimeProxToAirStart*16 + DELAY_ARM2AIR_AS_READER, (LastTimeProxToAirStart + LastProxToAirDuration)*16 + DELAY_ARM2AIR_AS_READER, par, true);
}
}
int ReaderReceiveOffset(uint8_t* receivedAnswer, uint16_t offset, uint8_t *parity)
{
- if (!GetIso14443aAnswerFromTag(receivedAnswer, parity, offset)) return FALSE;
+ if (!GetIso14443aAnswerFromTag(receivedAnswer, parity, offset)) return false;
if (tracing) {
- LogTrace(receivedAnswer, Demod.len, Demod.startTime*16 - DELAY_AIR2ARM_AS_READER, Demod.endTime*16 - DELAY_AIR2ARM_AS_READER, parity, FALSE);
+ LogTrace(receivedAnswer, Demod.len, Demod.startTime*16 - DELAY_AIR2ARM_AS_READER, Demod.endTime*16 - DELAY_AIR2ARM_AS_READER, parity, false);
}
return Demod.len;
}
int ReaderReceive(uint8_t *receivedAnswer, uint8_t *parity)
{
- if (!GetIso14443aAnswerFromTag(receivedAnswer, parity, 0)) return FALSE;
+ if (!GetIso14443aAnswerFromTag(receivedAnswer, parity, 0)) return false;
if (tracing) {
- LogTrace(receivedAnswer, Demod.len, Demod.startTime*16 - DELAY_AIR2ARM_AS_READER, Demod.endTime*16 - DELAY_AIR2ARM_AS_READER, parity, FALSE);
+ LogTrace(receivedAnswer, Demod.len, Demod.startTime*16 - DELAY_AIR2ARM_AS_READER, Demod.endTime*16 - DELAY_AIR2ARM_AS_READER, parity, false);
}
return Demod.len;
}
-/* performs iso14443a anticollision procedure
- * fills the uid pointer unless NULL
- * fills resp_data unless NULL */
-int iso14443a_select_card(byte_t *uid_ptr, iso14a_card_select_t *p_hi14a_card, uint32_t *cuid_ptr) {
+// performs iso14443a anticollision (optional) and card select procedure
+// fills the uid and cuid pointer unless NULL
+// fills the card info record unless NULL
+// if anticollision is false, then the UID must be provided in uid_ptr[]
+// and num_cascades must be set (1: 4 Byte UID, 2: 7 Byte UID, 3: 10 Byte UID)
+int iso14443a_select_card(byte_t *uid_ptr, iso14a_card_select_t *p_hi14a_card, uint32_t *cuid_ptr, bool anticollision, uint8_t num_cascades) {
uint8_t wupa[] = { 0x52 }; // 0x26 - REQA 0x52 - WAKE-UP
uint8_t sel_all[] = { 0x93,0x20 };
uint8_t sel_uid[] = { 0x93,0x70,0x00,0x00,0x00,0x00,0x00,0x00,0x00};
int len;
// Broadcast for a card, WUPA (0x52) will force response from all cards in the field
- ReaderTransmitBitsPar(wupa,7,0, NULL);
+ ReaderTransmitBitsPar(wupa, 7, NULL, NULL);
// Receive the ATQA
if(!ReaderReceive(resp, resp_par)) return 0;
memset(p_hi14a_card->uid,0,10);
}
- // clear uid
- if (uid_ptr) {
- memset(uid_ptr,0,10);
+ if (anticollision) {
+ // clear uid
+ if (uid_ptr) {
+ memset(uid_ptr,0,10);
+ }
}
// check for proprietary anticollision:
// SELECT_* (L1: 0x93, L2: 0x95, L3: 0x97)
sel_uid[0] = sel_all[0] = 0x93 + cascade_level * 2;
- // SELECT_ALL
- ReaderTransmit(sel_all, sizeof(sel_all), NULL);
- if (!ReaderReceive(resp, resp_par)) return 0;
-
- if (Demod.collisionPos) { // we had a collision and need to construct the UID bit by bit
- memset(uid_resp, 0, 4);
- uint16_t uid_resp_bits = 0;
- uint16_t collision_answer_offset = 0;
- // anti-collision-loop:
- while (Demod.collisionPos) {
- Dbprintf("Multiple tags detected. Collision after Bit %d", Demod.collisionPos);
- for (uint16_t i = collision_answer_offset; i < Demod.collisionPos; i++, uid_resp_bits++) { // add valid UID bits before collision point
- uint16_t UIDbit = (resp[i/8] >> (i % 8)) & 0x01;
- uid_resp[uid_resp_bits / 8] |= UIDbit << (uid_resp_bits % 8);
+ if (anticollision) {
+ // SELECT_ALL
+ ReaderTransmit(sel_all, sizeof(sel_all), NULL);
+ if (!ReaderReceive(resp, resp_par)) return 0;
+
+ if (Demod.collisionPos) { // we had a collision and need to construct the UID bit by bit
+ memset(uid_resp, 0, 4);
+ uint16_t uid_resp_bits = 0;
+ uint16_t collision_answer_offset = 0;
+ // anti-collision-loop:
+ while (Demod.collisionPos) {
+ Dbprintf("Multiple tags detected. Collision after Bit %d", Demod.collisionPos);
+ for (uint16_t i = collision_answer_offset; i < Demod.collisionPos; i++, uid_resp_bits++) { // add valid UID bits before collision point
+ uint16_t UIDbit = (resp[i/8] >> (i % 8)) & 0x01;
+ uid_resp[uid_resp_bits / 8] |= UIDbit << (uid_resp_bits % 8);
+ }
+ uid_resp[uid_resp_bits/8] |= 1 << (uid_resp_bits % 8); // next time select the card(s) with a 1 in the collision position
+ uid_resp_bits++;
+ // construct anticollosion command:
+ sel_uid[1] = ((2 + uid_resp_bits/8) << 4) | (uid_resp_bits & 0x07); // length of data in bytes and bits
+ for (uint16_t i = 0; i <= uid_resp_bits/8; i++) {
+ sel_uid[2+i] = uid_resp[i];
+ }
+ collision_answer_offset = uid_resp_bits%8;
+ ReaderTransmitBits(sel_uid, 16 + uid_resp_bits, NULL);
+ if (!ReaderReceiveOffset(resp, collision_answer_offset, resp_par)) return 0;
}
- uid_resp[uid_resp_bits/8] |= 1 << (uid_resp_bits % 8); // next time select the card(s) with a 1 in the collision position
- uid_resp_bits++;
- // construct anticollosion command:
- sel_uid[1] = ((2 + uid_resp_bits/8) << 4) | (uid_resp_bits & 0x07); // length of data in bytes and bits
- for (uint16_t i = 0; i <= uid_resp_bits/8; i++) {
- sel_uid[2+i] = uid_resp[i];
+ // finally, add the last bits and BCC of the UID
+ for (uint16_t i = collision_answer_offset; i < (Demod.len-1)*8; i++, uid_resp_bits++) {
+ uint16_t UIDbit = (resp[i/8] >> (i%8)) & 0x01;
+ uid_resp[uid_resp_bits/8] |= UIDbit << (uid_resp_bits % 8);
}
- collision_answer_offset = uid_resp_bits%8;
- ReaderTransmitBits(sel_uid, 16 + uid_resp_bits, NULL);
- if (!ReaderReceiveOffset(resp, collision_answer_offset, resp_par)) return 0;
+
+ } else { // no collision, use the response to SELECT_ALL as current uid
+ memcpy(uid_resp, resp, 4);
}
- // finally, add the last bits and BCC of the UID
- for (uint16_t i = collision_answer_offset; i < (Demod.len-1)*8; i++, uid_resp_bits++) {
- uint16_t UIDbit = (resp[i/8] >> (i%8)) & 0x01;
- uid_resp[uid_resp_bits/8] |= UIDbit << (uid_resp_bits % 8);
+ } else {
+ if (cascade_level < num_cascades - 1) {
+ uid_resp[0] = 0x88;
+ memcpy(uid_resp+1, uid_ptr+cascade_level*3, 3);
+ } else {
+ memcpy(uid_resp, uid_ptr+cascade_level*3, 4);
}
-
- } else { // no collision, use the response to SELECT_ALL as current uid
- memcpy(uid_resp, resp, 4);
}
uid_resp_len = 4;
// Construct SELECT UID command
sel_uid[1] = 0x70; // transmitting a full UID (1 Byte cmd, 1 Byte NVB, 4 Byte UID, 1 Byte BCC, 2 Bytes CRC)
- memcpy(sel_uid+2, uid_resp, 4); // the UID
+ memcpy(sel_uid+2, uid_resp, 4); // the UID received during anticollision, or the provided UID
sel_uid[6] = sel_uid[2] ^ sel_uid[3] ^ sel_uid[4] ^ sel_uid[5]; // calculate and add BCC
AppendCrc14443a(sel_uid, 7); // calculate and add CRC
ReaderTransmit(sel_uid, sizeof(sel_uid), NULL);
// Receive the SAK
if (!ReaderReceive(resp, resp_par)) return 0;
sak = resp[0];
-
- // Test if more parts of the uid are coming
+
+ // Test if more parts of the uid are coming
if ((sak & 0x04) /* && uid_resp[0] == 0x88 */) {
// Remove first byte, 0x88 is not an UID byte, it CT, see page 3 of:
// http://www.nxp.com/documents/application_note/AN10927.pdf
uid_resp[0] = uid_resp[1];
uid_resp[1] = uid_resp[2];
uid_resp[2] = uid_resp[3];
-
uid_resp_len = 3;
}
- if(uid_ptr) {
+ if(uid_ptr && anticollision) {
memcpy(uid_ptr + (cascade_level*3), uid_resp, uid_resp_len);
}
clear_trace();
}
- set_tracing(TRUE);
+ set_tracing(true);
if(param & ISO14A_REQUEST_TRIGGER) {
- iso14a_set_trigger(TRUE);
+ iso14a_set_trigger(true);
}
if(param & ISO14A_CONNECT) {
iso14443a_setup(FPGA_HF_ISO14443A_READER_LISTEN);
if(!(param & ISO14A_NO_SELECT)) {
iso14a_card_select_t *card = (iso14a_card_select_t*)buf;
- arg0 = iso14443a_select_card(NULL,card,NULL);
+ arg0 = iso14443a_select_card(NULL, card, NULL, true, 0);
cmd_send(CMD_ACK,arg0,card->uidlen,0,buf,sizeof(iso14a_card_select_t));
}
}
}
if(param & ISO14A_REQUEST_TRIGGER) {
- iso14a_set_trigger(FALSE);
+ iso14a_set_trigger(false);
}
if(param & ISO14A_NO_DISCONNECT) {
BigBuf_free();
clear_trace();
- set_tracing(TRUE);
+ set_tracing(true);
byte_t nt_diff = 0;
uint8_t par[1] = {0}; // maximum 8 Bytes to be sent here, 1 byte parity is therefore enough
static byte_t par_low = 0;
- bool led_on = TRUE;
+ bool led_on = true;
uint8_t uid[10] ={0};
uint32_t cuid;
uint32_t select_time;
uint32_t halt_time;
- for(uint16_t i = 0; TRUE; i++) {
+ for(uint16_t i = 0; true; i++) {
LED_C_ON();
WDT_HIT();
SpinDelay(100);
}
- if(!iso14443a_select_card(uid, NULL, &cuid)) {
+ if(!iso14443a_select_card(uid, NULL, &cuid, true, 0)) {
if (MF_DBGLEVEL >= 1) Dbprintf("Mifare: Can't select card");
continue;
}
FpgaWriteConfWord(FPGA_MAJOR_MODE_OFF);
LEDsoff();
- set_tracing(FALSE);
+ set_tracing(false);
}
typedef struct {
// clear trace
clear_trace();
- set_tracing(TRUE);
+ set_tracing(true);
- bool finished = FALSE;
+ bool finished = false;
bool button_pushed = BUTTON_PRESS();
while (!button_pushed && !finished && !usb_poll_validate_length()) {
WDT_HIT();
case MFEMUL_NOFIELD:
case MFEMUL_HALTED:
case MFEMUL_IDLE:{
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
break;
}
case MFEMUL_SELECT1:{
}
case MFEMUL_SELECT3:{
if (!len) {
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
break;
}
// select all cl3 - 0x97 0x20
case MFEMUL_AUTH1:{
if( len != 8) {
cardSTATE_TO_IDLE();
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
break;
}
// reader to do a WUPA after a while. /Martin
// -- which is the correct response. /piwi
cardSTATE_TO_IDLE();
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
break;
}
}
case MFEMUL_SELECT2:{
if (!len) {
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
break;
}
// select all cl2 - 0x95 0x20
// i guess there is a command). go into the work state.
if (len != 4) {
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
break;
}
cardSTATE = MFEMUL_WORK;
case MFEMUL_WORK:{
if (len == 0) {
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
break;
}
}
if(len != 4) {
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
break;
}
LED_C_OFF();
cardSTATE = MFEMUL_HALTED;
if (MF_DBGLEVEL >= 4) Dbprintf("--> HALTED. Selected time: %d ms", GetTickCount() - selTimer);
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
break;
}
// RATS
cardSTATE = MFEMUL_WORK;
} else {
cardSTATE_TO_IDLE();
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
}
break;
}
cardSTATE_TO_IDLE();
break;
}
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
cardINTREG = cardINTREG + ans;
cardSTATE = MFEMUL_WORK;
break;
cardSTATE_TO_IDLE();
break;
}
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
cardINTREG = cardINTREG - ans;
cardSTATE = MFEMUL_WORK;
break;
cardSTATE_TO_IDLE();
break;
}
- LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, TRUE);
+ LogTrace(Uart.output, Uart.len, Uart.startTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.endTime*16 - DELAY_AIR2ARM_AS_TAG, Uart.parity, true);
cardSTATE = MFEMUL_WORK;
break;
}
LEDsoff();
// init trace buffer
clear_trace();
- set_tracing(TRUE);
+ set_tracing(true);
// The command (reader -> tag) that we're receiving.
// The length of a received command will in most cases be no more than 18 bytes.
uint8_t previous_data = 0;
int maxDataLen = 0;
int dataLen = 0;
- bool ReaderIsActive = FALSE;
- bool TagIsActive = FALSE;
+ bool ReaderIsActive = false;
+ bool TagIsActive = false;
// Set up the demodulator for tag -> reader responses.
DemodInit(receivedResponse, receivedResponsePar);
MfSniffInit();
// And now we loop, receiving samples.
- for(uint32_t sniffCounter = 0; TRUE; ) {
+ for(uint32_t sniffCounter = 0; true; ) {
if(BUTTON_PRESS()) {
DbpString("cancelled by button");
sniffCounter = 0;
data = dmaBuf;
maxDataLen = 0;
- ReaderIsActive = FALSE;
- TagIsActive = FALSE;
+ ReaderIsActive = false;
+ TagIsActive = false;
FpgaSetupSscDma((uint8_t *)dmaBuf, DMA_BUFFER_SIZE); // set transfer address and number of bytes. Start transfer.
}
}
uint8_t readerdata = (previous_data & 0xF0) | (*data >> 4);
if(MillerDecoding(readerdata, (sniffCounter-1)*4)) {
LED_C_INV();
- if (MfSniffLogic(receivedCmd, Uart.len, Uart.parity, Uart.bitCount, TRUE)) break;
+ if (MfSniffLogic(receivedCmd, Uart.len, Uart.parity, Uart.bitCount, true)) break;
/* And ready to receive another command. */
UartInit(receivedCmd, receivedCmdPar);
if(ManchesterDecoding(tagdata, 0, (sniffCounter-1)*4)) {
LED_C_INV();
- if (MfSniffLogic(receivedResponse, Demod.len, Demod.parity, Demod.bitCount, FALSE)) break;
+ if (MfSniffLogic(receivedResponse, Demod.len, Demod.parity, Demod.bitCount, false)) break;
// And ready to receive another response.
DemodReset();
#ifndef __ISO14443A_H
#define __ISO14443A_H
-#include "common.h"
-#include "mifaresniff.h"
-
-typedef struct {
- enum {
- DEMOD_UNSYNCD,
- // DEMOD_HALF_SYNCD,
- // DEMOD_MOD_FIRST_HALF,
- // DEMOD_NOMOD_FIRST_HALF,
- DEMOD_MANCHESTER_DATA
- } state;
- uint16_t twoBits;
- uint16_t highCnt;
- uint16_t bitCount;
- uint16_t collisionPos;
- uint16_t syncBit;
- uint8_t parityBits;
- uint8_t parityLen;
- uint16_t shiftReg;
- uint16_t samples;
- uint16_t len;
- uint32_t startTime, endTime;
- uint8_t *output;
- uint8_t *parity;
-} tDemod;
-
-typedef enum {
- MOD_NOMOD = 0,
- MOD_SECOND_HALF,
- MOD_FIRST_HALF,
- MOD_BOTH_HALVES
- } Modulation_t;
-
-typedef struct {
- enum {
- STATE_UNSYNCD,
- STATE_START_OF_COMMUNICATION,
- STATE_MILLER_X,
- STATE_MILLER_Y,
- STATE_MILLER_Z,
- // DROP_NONE,
- // DROP_FIRST_HALF,
- } state;
- uint16_t shiftReg;
- int16_t bitCount;
- uint16_t len;
- uint16_t byteCntMax;
- uint16_t posCnt;
- uint16_t syncBit;
- uint8_t parityBits;
- uint8_t parityLen;
- uint32_t fourBits;
- uint32_t startTime, endTime;
- uint8_t *output;
- uint8_t *parity;
-} tUart;
-
+#include <stdint.h>
+#include <stdbool.h>
+#include "mifare.h"
extern void GetParity(const uint8_t *pbtCmd, uint16_t len, uint8_t *par);
extern void AppendCrc14443a(uint8_t *data, int len);
extern void iso14443a_setup(uint8_t fpga_minor_mode);
extern int iso14_apdu(uint8_t *cmd, uint16_t cmd_len, void *data);
-extern int iso14443a_select_card(uint8_t *uid_ptr, iso14a_card_select_t *resp_data, uint32_t *cuid_ptr);
+extern int iso14443a_select_card(uint8_t *uid_ptr, iso14a_card_select_t *resp_data, uint32_t *cuid_ptr, bool anticollision, uint8_t num_cascades);
extern void iso14a_set_trigger(bool enable);
-
#endif /* __ISO14443A_H */
//-----------------------------------------------------------------------------\r
\r
#include "mifarecmd.h"\r
+\r
#include "apps.h"\r
#include "util.h"\r
#include "parity.h"\r
#include "crc.h"\r
\r
+#define AUTHENTICATION_TIMEOUT 848 // card times out 1ms after wrong authentication (according to NXP documentation)\r
+#define PRE_AUTHENTICATION_LEADTIME 400 // some (non standard) cards need a pause after select before they are ready for first authentication \r
+ \r
+\r
// the block number for the ISO14443-4 PCB\r
-uint8_t pcb_blocknum = 0;\r
+static uint8_t pcb_blocknum = 0;\r
// Deselect card by sending a s-block. the crc is precalced for speed\r
static uint8_t deselect_cmd[] = {0xc2,0xe0,0xb4};\r
\r
LED_C_OFF();\r
\r
while (true) {\r
- if(!iso14443a_select_card(uid, NULL, &cuid)) {\r
+ if(!iso14443a_select_card(uid, NULL, &cuid, true, 0)) {\r
if (MF_DBGLEVEL >= 1) Dbprintf("Can't select card");\r
break;\r
};\r
\r
clear_trace();\r
\r
- if(!iso14443a_select_card(NULL, NULL, NULL)) {\r
+ if(!iso14443a_select_card(NULL, NULL, NULL, true, 0)) {\r
if (MF_DBGLEVEL >= MF_DBG_ERROR) Dbprintf("Can't select card");\r
OnError(0);\r
return;\r
\r
clear_trace();\r
\r
- int len = iso14443a_select_card(NULL, NULL, NULL);\r
+ int len = iso14443a_select_card(NULL, NULL, NULL, true, 0);\r
if(!len) {\r
if (MF_DBGLEVEL >= MF_DBG_ERROR) Dbprintf("Can't select card (RC:%02X)",len);\r
OnError(1);\r
LED_C_OFF();\r
\r
isOK = 1;\r
- if(!iso14443a_select_card(uid, NULL, &cuid)) {\r
+ if(!iso14443a_select_card(uid, NULL, &cuid, true, 0)) {\r
isOK = 0;\r
if (MF_DBGLEVEL >= 1) Dbprintf("Can't select card");\r
}\r
return;\r
}\r
\r
- int len = iso14443a_select_card(NULL, NULL, NULL);\r
+ int len = iso14443a_select_card(NULL, NULL, NULL, true, 0);\r
if (!len) {\r
if (MF_DBGLEVEL >= MF_DBG_ERROR) Dbprintf("Can't select card (RC:%d)",len);\r
OnError(1);\r
LED_C_OFF();\r
\r
while (true) {\r
- if(!iso14443a_select_card(uid, NULL, &cuid)) {\r
+ if(!iso14443a_select_card(uid, NULL, &cuid, true, 0)) {\r
if (MF_DBGLEVEL >= 1) Dbprintf("Can't select card");\r
break;\r
};\r
clear_trace();\r
iso14443a_setup(FPGA_HF_ISO14443A_READER_LISTEN);\r
\r
- if(!iso14443a_select_card(uid, NULL, NULL)) {\r
+ if(!iso14443a_select_card(uid, NULL, NULL, true, 0)) {\r
if (MF_DBGLEVEL >= 1) Dbprintf("Can't select card");\r
OnError(0);\r
return;\r
\r
clear_trace();\r
\r
- if(!iso14443a_select_card(NULL, NULL, NULL)) {\r
+ if(!iso14443a_select_card(NULL, NULL, NULL, true, 0)) {\r
if (MF_DBGLEVEL >= 1) Dbprintf("Can't select card");\r
OnError(0);\r
return;\r
\r
clear_trace();\r
\r
- if(!iso14443a_select_card(NULL, NULL, NULL)) {\r
+ if(!iso14443a_select_card(NULL, NULL, NULL, true, 0)) {\r
if (MF_DBGLEVEL >= 1) Dbprintf("Can't select card");\r
OnError(0);\r
return;\r
}\r
\r
\r
+//-----------------------------------------------------------------------------\r
+// acquire encrypted nonces in order to perform the attack described in\r
+// Carlo Meijer, Roel Verdult, "Ciphertext-only Cryptanalysis on Hardened\r
+// Mifare Classic Cards" in Proceedings of the 22nd ACM SIGSAC Conference on \r
+// Computer and Communications Security, 2015\r
+//-----------------------------------------------------------------------------\r
+void MifareAcquireEncryptedNonces(uint32_t arg0, uint32_t arg1, uint32_t flags, uint8_t *datain)\r
+{\r
+ uint64_t ui64Key = 0;\r
+ uint8_t uid[10];\r
+ uint32_t cuid;\r
+ uint8_t cascade_levels = 0;\r
+ struct Crypto1State mpcs = {0, 0};\r
+ struct Crypto1State *pcs;\r
+ pcs = &mpcs;\r
+ uint8_t receivedAnswer[MAX_MIFARE_FRAME_SIZE];\r
+ int16_t isOK = 0;\r
+ uint8_t par_enc[1];\r
+ uint8_t nt_par_enc = 0;\r
+ uint8_t buf[USB_CMD_DATA_SIZE];\r
+ uint32_t timeout;\r
+ \r
+ uint8_t blockNo = arg0 & 0xff;\r
+ uint8_t keyType = (arg0 >> 8) & 0xff;\r
+ uint8_t targetBlockNo = arg1 & 0xff;\r
+ uint8_t targetKeyType = (arg1 >> 8) & 0xff;\r
+ ui64Key = bytes_to_num(datain, 6);\r
+ bool initialize = flags & 0x0001;\r
+ bool slow = flags & 0x0002;\r
+ bool field_off = flags & 0x0004;\r
+ \r
+ LED_A_ON();\r
+ LED_C_OFF();\r
+\r
+ if (initialize) {\r
+ iso14443a_setup(FPGA_HF_ISO14443A_READER_LISTEN);\r
+ clear_trace();\r
+ set_tracing(true);\r
+ }\r
+ \r
+ LED_C_ON();\r
+ \r
+ uint16_t num_nonces = 0;\r
+ bool have_uid = false;\r
+ for (uint16_t i = 0; i <= USB_CMD_DATA_SIZE - 9; ) {\r
+\r
+ // Test if the action was cancelled\r
+ if(BUTTON_PRESS()) {\r
+ isOK = 2;\r
+ field_off = true;\r
+ break;\r
+ }\r
+\r
+ if (!have_uid) { // need a full select cycle to get the uid first\r
+ iso14a_card_select_t card_info; \r
+ if(!iso14443a_select_card(uid, &card_info, &cuid, true, 0)) {\r
+ if (MF_DBGLEVEL >= 1) Dbprintf("AcquireNonces: Can't select card (ALL)");\r
+ continue;\r
+ }\r
+ switch (card_info.uidlen) {\r
+ case 4 : cascade_levels = 1; break;\r
+ case 7 : cascade_levels = 2; break;\r
+ case 10: cascade_levels = 3; break;\r
+ default: break;\r
+ }\r
+ have_uid = true; \r
+ } else { // no need for anticollision. We can directly select the card\r
+ if(!iso14443a_select_card(uid, NULL, NULL, false, cascade_levels)) {\r
+ if (MF_DBGLEVEL >= 1) Dbprintf("AcquireNonces: Can't select card (UID)");\r
+ continue;\r
+ }\r
+ }\r
+ \r
+ if (slow) {\r
+ timeout = GetCountSspClk() + PRE_AUTHENTICATION_LEADTIME;\r
+ while(GetCountSspClk() < timeout);\r
+ }\r
+\r
+ uint32_t nt1;\r
+ if (mifare_classic_authex(pcs, cuid, blockNo, keyType, ui64Key, AUTH_FIRST, &nt1, NULL)) {\r
+ if (MF_DBGLEVEL >= 1) Dbprintf("AcquireNonces: Auth1 error");\r
+ continue;\r
+ }\r
+\r
+ // nested authentication\r
+ uint16_t len = mifare_sendcmd_short(pcs, AUTH_NESTED, 0x60 + (targetKeyType & 0x01), targetBlockNo, receivedAnswer, par_enc, NULL);\r
+ if (len != 4) {\r
+ if (MF_DBGLEVEL >= 1) Dbprintf("AcquireNonces: Auth2 error len=%d", len);\r
+ continue;\r
+ }\r
+ \r
+ // send a dummy byte as reader response in order to trigger the cards authentication timeout\r
+ uint8_t dummy_answer = 0;\r
+ ReaderTransmit(&dummy_answer, 1, NULL);\r
+ timeout = GetCountSspClk() + AUTHENTICATION_TIMEOUT;\r
+ \r
+ num_nonces++;\r
+ if (num_nonces % 2) {\r
+ memcpy(buf+i, receivedAnswer, 4);\r
+ nt_par_enc = par_enc[0] & 0xf0;\r
+ } else {\r
+ nt_par_enc |= par_enc[0] >> 4;\r
+ memcpy(buf+i+4, receivedAnswer, 4);\r
+ memcpy(buf+i+8, &nt_par_enc, 1);\r
+ i += 9;\r
+ }\r
+\r
+ // wait for the card to become ready again\r
+ while(GetCountSspClk() < timeout);\r
+ \r
+ }\r
+\r
+ LED_C_OFF();\r
+ \r
+ crypto1_destroy(pcs);\r
+ \r
+ LED_B_ON();\r
+ cmd_send(CMD_ACK, isOK, cuid, num_nonces, buf, sizeof(buf));\r
+ LED_B_OFF();\r
+\r
+ if (MF_DBGLEVEL >= 3) DbpString("AcquireEncryptedNonces finished");\r
+\r
+ if (field_off) {\r
+ FpgaWriteConfWord(FPGA_MAJOR_MODE_OFF);\r
+ LEDsoff();\r
+ }\r
+}\r
+\r
+\r
//-----------------------------------------------------------------------------\r
// MIFARE nested authentication. \r
// \r
continue;\r
}\r
\r
- if(!iso14443a_select_card(uid, NULL, &cuid)) {\r
+ if(!iso14443a_select_card(uid, NULL, &cuid, true, 0)) {\r
if (MF_DBGLEVEL >= 1) Dbprintf("Nested: Can't select card");\r
rtr--;\r
continue;\r
continue;\r
}\r
\r
- if(!iso14443a_select_card(uid, NULL, &cuid)) {\r
+ if(!iso14443a_select_card(uid, NULL, &cuid, true, 0)) {\r
if (MF_DBGLEVEL >= 1) Dbprintf("Nested: Can't select card");\r
continue;\r
};\r
//-----------------------------------------------------------------------------\r
void MifareChkKeys(uint16_t arg0, uint8_t arg1, uint8_t arg2, uint8_t *datain)\r
{\r
- // params\r
uint8_t blockNo = arg0 & 0xff;\r
uint8_t keyType = (arg0 >> 8) & 0xff;\r
bool clearTrace = arg1;\r
uint8_t keyCount = arg2;\r
uint64_t ui64Key = 0;\r
\r
- // variables\r
+ bool have_uid = false;\r
+ uint8_t cascade_levels = 0;\r
+ uint32_t timeout = 0;\r
int i;\r
byte_t isOK = 0;\r
uint8_t uid[10];\r
iso14443a_setup(FPGA_HF_ISO14443A_READER_LISTEN);\r
\r
if (clearTrace) clear_trace();\r
- set_tracing(TRUE);\r
+ set_tracing(true);\r
\r
for (i = 0; i < keyCount; i++) {\r
- if(mifare_classic_halt(pcs, cuid)) {\r
- if (MF_DBGLEVEL >= 1) Dbprintf("ChkKeys: Halt error");\r
+// if(mifare_classic_halt(pcs, cuid)) {\r
+// if (MF_DBGLEVEL >= 1) Dbprintf("ChkKeys: Halt error");\r
+// }\r
+\r
+ // Iceman: use piwi's faster nonce collecting part in hardnested.\r
+ if (!have_uid) { // need a full select cycle to get the uid first\r
+ iso14a_card_select_t card_info; \r
+ if(!iso14443a_select_card(uid, &card_info, &cuid, true, 0)) {\r
+ if (OLD_MF_DBGLEVEL >= 1) Dbprintf("ChkKeys: Can't select card");\r
+ --i; // try same key once again\r
+ continue;\r
+ }\r
+ switch (card_info.uidlen) {\r
+ case 4 : cascade_levels = 1; break;\r
+ case 7 : cascade_levels = 2; break;\r
+ case 10: cascade_levels = 3; break;\r
+ default: break;\r
+ }\r
+ have_uid = true; \r
+ } else { // no need for anticollision. We can directly select the card\r
+ if(!iso14443a_select_card(uid, NULL, NULL, false, cascade_levels)) {\r
+ if (OLD_MF_DBGLEVEL >= 1) Dbprintf("ChkKeys: Can't select card (UID)");\r
+ --i; // try same key once again\r
+ continue;\r
+ }\r
}\r
\r
- if(!iso14443a_select_card(uid, NULL, &cuid)) {\r
- if (OLD_MF_DBGLEVEL >= 1) Dbprintf("ChkKeys: Can't select card");\r
- break;\r
- };\r
-\r
ui64Key = bytes_to_num(datain + i * 6, 6);\r
if(mifare_classic_auth(pcs, cuid, blockNo, keyType, ui64Key, AUTH_FIRST)) {\r
+ uint8_t dummy_answer = 0;\r
+ ReaderTransmit(&dummy_answer, 1, NULL);\r
+ timeout = GetCountSspClk() + AUTHENTICATION_TIMEOUT;\r
+ \r
+ // wait for the card to become ready again\r
+ while(GetCountSspClk() < timeout);\r
continue;\r
- };\r
+ }\r
\r
isOK = 1;\r
break;\r
}\r
\r
- // ----------------------------- crypto1 destroy\r
- crypto1_destroy(pcs);\r
- \r
LED_B_ON();\r
cmd_send(CMD_ACK,isOK,0,0,datain + i * 6,6);\r
LED_B_OFF();\r
\r
bool isOK = true;\r
\r
- if(!iso14443a_select_card(uid, NULL, &cuid)) {\r
+ if(!iso14443a_select_card(uid, NULL, &cuid, true, 0)) {\r
isOK = false;\r
if (MF_DBGLEVEL >= 1) Dbprintf("Can't select card");\r
}\r
iso14443a_setup(FPGA_HF_ISO14443A_READER_LISTEN);\r
\r
clear_trace();\r
- set_tracing(TRUE);\r
+ set_tracing(true);\r
}\r
\r
while (true) {\r
\r
// get UID from chip\r
if (workFlags & 0x01) {\r
- if(!iso14443a_select_card(uid, NULL, &cuid)) {\r
+ if(!iso14443a_select_card(uid, NULL, &cuid, true, 0)) {\r
if (MF_DBGLEVEL >= 1) Dbprintf("Can't select card");\r
break;\r
};\r
iso14443a_setup(FPGA_HF_ISO14443A_READER_LISTEN);\r
\r
clear_trace();\r
- set_tracing(TRUE);\r
+ set_tracing(true);\r
}\r
\r
while (true) {\r
iso14443a_setup(FPGA_HF_ISO14443A_READER_LISTEN);\r
clear_trace();\r
\r
- int len = iso14443a_select_card(uid, NULL, &cuid);\r
+ int len = iso14443a_select_card(uid, NULL, &cuid, true, 0);\r
if(!len) {\r
if (MF_DBGLEVEL >= MF_DBG_ERROR) Dbprintf("Can't select card");\r
OnError(1);\r
# at your option, any later version. See the LICENSE.txt file for the text of
# the license.
#-----------------------------------------------------------------------------
-include ../common/Makefile.common
+CC = gcc
+CXX = g++
+LD = g++
+TAR = tar
+TARFLAGS = -C .. --ignore-failed-read -rvf
+RM = rm -f
+MV = mv
-CC=gcc
-CXX=g++
#COMMON_FLAGS = -m32
VPATH = ../common ../zlib
OBJDIR = obj
LDLIBS = -L/opt/local/lib -L/usr/local/lib -lreadline -lpthread -lm
LUALIB = ../liblua/liblua.a
LDFLAGS = $(COMMON_FLAGS)
-CFLAGS = -std=c99 -D_ISOC99_SOURCE -I. -I../include -I../common -I../tools -I../zlib -I/opt/local/include -I../liblua -Wall $(COMMON_FLAGS) -g -O4
+CFLAGS = -std=c99 -D_ISOC99_SOURCE -I. -I../include -I../common -I../zlib -I/opt/local/include -I../liblua -Wall $(COMMON_FLAGS) -g -O4
LUAPLATFORM = generic
+platform = $(shell uname)
ifneq (,$(findstring MINGW,$(platform)))
CXXFLAGS = -I$(QTDIR)/include -I$(QTDIR)/include/QtCore -I$(QTDIR)/include/QtGui
- MOC = $(QTDIR)/bin/moc
- LUAPLATFORM = mingw
ifneq ($(wildcard $(QTDIR)/include/QtWidgets),)
CXXFLAGS += -I$(QTDIR)/include/QtWidgets
QTLDLIBS = -L$(QTDIR)/lib -lQt5Core -lQt5Gui -lQt5Widgets
else
QTLDLIBS = -L$(QTDIR)/lib -lQtCore4 -lQtGui4
endif
-else ifeq ($(platform),Darwin)
- CXXFLAGS = $(shell pkg-config --cflags QtCore QtGui 2>/dev/null) -Wall -O4
- QTLDLIBS = $(shell pkg-config --libs QtCore QtGui 2>/dev/null)
- MOC = $(shell pkg-config --variable=moc_location QtCore)
- LUAPLATFORM = macosx
+ MOC = $(QTDIR)/bin/moc
+ LUAPLATFORM = mingw
else
- CXXFLAGS = $(shell pkg-config --cflags QtCore QtGui 2>/dev/null) -Wall -O4
- QTLDLIBS = $(shell pkg-config --libs QtCore QtGui 2>/dev/null)
- LUALIB += -ldl
- LDLIBS += -ltermcap -lncurses
- MOC = $(shell pkg-config --variable=moc_location QtCore)
- # Below is a variant you can use if you have problems compiling with QT5 on ubuntu. see http://www.proxmark.org/forum/viewtopic.php?id=1661 for more info.
- #MOC = /usr/lib/x86_64-linux-gnu/qt4/bin/moc
- LUAPLATFORM = linux
+ CXXFLAGS = $(shell pkg-config --cflags Qt5Core Qt5Widgets 2>/dev/null) -Wall -O4
+ QTLDLIBS = $(shell pkg-config --libs Qt5Core Qt5Widgets 2>/dev/null)
+ MOC = $(shell pkg-config --variable=host_bins Qt5Core)/moc
+ ifeq ($(QTLDLIBS), )
+ CXXFLAGS = $(shell pkg-config --cflags QtCore QtGui 2>/dev/null) -Wall -O4
+ QTLDLIBS = $(shell pkg-config --libs QtCore QtGui 2>/dev/null)
+ MOC = $(shell pkg-config --variable=moc_location QtCore)
+ endif
+ ifeq ($(platform),Darwin)
+ LUAPLATFORM = macosx
+ else
+ LUALIB += -ldl
+ LDLIBS += -ltermcap -lncurses
+ LUAPLATFORM = linux
+ endif
endif
ifneq ($(QTLDLIBS),)
- QTGUI = $(OBJDIR)/proxgui.o $(OBJDIR)/proxguiqt.o $(OBJDIR)/proxguiqt.moc.o
+ QTGUIOBJS = $(OBJDIR)/proxgui.o $(OBJDIR)/proxguiqt.o $(OBJDIR)/proxguiqt.moc.o
CFLAGS += -DHAVE_GUI
- LINK.o = $(LINK.cpp)
else
- QTGUI = guidummy.o
+ QTGUIOBJS = $(OBJDIR)/guidummy.o
endif
-CORESRCS = uart.c \
- util.c \
+# Flags to generate temporary dependency files
+DEPFLAGS = -MT $@ -MMD -MP -MF $(OBJDIR)/$*.Td
+# make temporary to final dependeny files after successful compilation
+POSTCOMPILE = $(MV) -f $(OBJDIR)/$*.Td $(OBJDIR)/$*.d
+CORESRCS = uart.c \
+ util.c
CMDSRCS = crapto1/crapto1.c\
crapto1/crypto1.c\
reveng/getopt.c\
ZLIBSRCS = deflate.c adler32.c trees.c zutil.c inflate.c inffast.c inftrees.c
-ZLIB_FLAGS = -DZ_SOLO -DZ_PREFIX -DNO_GZIP -DZLIB_PM3_TUNED
+ZLIBFLAGS = -DZ_SOLO -DZ_PREFIX -DNO_GZIP -DZLIB_PM3_TUNED
#-DDEBUG -Dverbose=1
+QTGUISRCS = proxgui.cpp proxguiqt.cpp proxguiqt.moc.cpp guidummy.cpp
COREOBJS = $(CORESRCS:%.c=$(OBJDIR)/%.o)
CMDOBJS = $(CMDSRCS:%.c=$(OBJDIR)/%.o)
ZLIBOBJS = $(ZLIBSRCS:%.c=$(OBJDIR)/%.o)
-RM = rm -f
-BINS = proxmark3 flasher fpga_compress #snooper cli
-CLEAN = cli cli.exe flasher flasher.exe proxmark3 proxmark3.exe fpga_compress fpga_compress.exe snooper snooper.exe $(CMDOBJS) $(OBJDIR)/*.o *.o *.moc.cpp
+BINS = proxmark3 flasher fpga_compress
+WINBINS = $(patsubst %, %.exe, $(BINS))
+CLEAN = $(BINS) $(WINBINS) $(COREOBJS) $(CMDOBJS) $(ZLIBOBJS) $(QTGUIOBJS) $(OBJDIR)/*.o *.moc.cpp
-all: lua_build $(BINS)
+all: lua_build $(BINS)
all-static: LDLIBS:=-static $(LDLIBS)
-all-static: snooper cli flasher fpga_compress
+all-static: proxmark3 flasher fpga_compress
proxmark3: LDLIBS+=$(LUALIB) $(QTLDLIBS)
-proxmark3: $(OBJDIR)/proxmark3.o $(COREOBJS) $(CMDOBJS) $(QTGUI)
- $(CXX) $(CXXFLAGS) $^ $(LDLIBS) -o $@
-
-snooper: $(OBJDIR)/snooper.o $(COREOBJS) $(CMDOBJS) $(OBJDIR)/guidummy.o
- $(CXX) $(CXXFLAGS) $^ $(LDLIBS) -o $@
-
-cli: $(OBJDIR)/cli.o $(COREOBJS) $(CMDOBJS) $(OBJDIR)/guidummy.o
- $(CXX) $(CXXFLAGS) $^ $(LDLIBS) -o $@
+proxmark3: $(OBJDIR)/proxmark3.o $(COREOBJS) $(CMDOBJS) $(QTGUIOBJS) lualibs/usb_cmd.lua
+ $(LD) $(LDFLAGS) $(OBJDIR)/proxmark3.o $(COREOBJS) $(CMDOBJS) $(QTGUIOBJS) $(LDLIBS) -o $@
flasher: $(OBJDIR)/flash.o $(OBJDIR)/flasher.o $(COREOBJS)
- $(CXX) $(CXXFLAGS) $^ $(LDLIBS) -o $@
+ $(LD) $(LDFLAGS) $^ $(LDLIBS) -o $@
fpga_compress: $(OBJDIR)/fpga_compress.o $(ZLIBOBJS)
- $(CXX) $(CXXFLAGS) $(ZLIB_FLAGS) $^ $(LDLIBS) -o $@
-
-$(OBJDIR)/%.o: %.c
- $(CC) $(CFLAGS) $(ZLIB_FLAGS) -c -o $@ $<
-
-$(OBJDIR)/%.o: %.cpp
- $(CXX) $(CXXFLAGS) -c -o $@ $<
+ $(LD) $(LDFLAGS) $(ZLIBFLAGS) $^ $(LDLIBS) -o $@
proxguiqt.moc.cpp: proxguiqt.h
$(MOC) -o$@ $^
+lualibs/usb_cmd.lua: ../include/usb_cmd.h
+ awk -f usb_cmd_h2lua.awk $^ > $@
+
clean:
$(RM) $(CLEAN)
cd ../liblua && make clean
tarbin: $(BINS)
- $(TAR) $(TARFLAGS) ../proxmark3-$(platform)-bin.tar $(BINS:%=client/%)
+ $(TAR) $(TARFLAGS) ../proxmark3-$(platform)-bin.tar $(BINS:%=client/%) $(WINBINS:%=client/%)
lua_build:
@echo Compiling liblua, using platform $(LUAPLATFORM)
cd ../liblua && make $(LUAPLATFORM)
.PHONY: all clean
+
+%.o: %.c
+$(OBJDIR)/%.o : %.c $(OBJDIR)/%.d
+ $(CC) $(DEPFLAGS) $(CFLAGS) $(ZLIBFLAGS) -c -o $@ $<
+ $(POSTCOMPILE)
+
+%.o: %.cpp
+$(OBJDIR)/%.o : %.cpp $(OBJDIR)/%.d
+ $(CXX) $(DEPFLAGS) $(CXXFLAGS) -c -o $@ $<
+ $(POSTCOMPILE)
+
+
+#$(CMDOBJS) $(COREOBJS): $(notdir $(%.c)) %.d
+# $(CC) $(DEPFLAGS) $(CFLAGS) -c -o $@ $<
+# $(POSTCOMPILE)
+
+#$(ZLIBOBJS): $(notdir $(%.c)) %.d
+# $(CC) $(DEPFLAGS) $(CFLAGS) $(ZLIBFLAGS) -c -o $@ $<
+# $(POSTCOMPILE)
+
+#$(QTGUIOBJS): $(notdir $(%.cpp)) %.d
+# $(CXX) $(DEPFLAGS) $(CXXFLAGS) -c -o $@ $<
+# $(POSTCOMPILE)
+
+DEPENDENCY_FILES = $(patsubst %.c, $(OBJDIR)/%.d, $(CORESRCS) $(CMDSRCS) $(ZLIBSRCS)) \
+ $(patsubst %.cpp, $(OBJDIR)/%.d, $(QTGUISRCS)) \
+ $(OBJDIR)/proxmark3.d $(OBJDIR)/flash.d $(OBJDIR)/flasher.d $(OBJDIR)/fpga_compress.d
+
+$(DEPENDENCY_FILES): ;
+.PRECIOUS: $(DEPENDENCY_FILES)
+
+-include $(DEPENDENCY_FILES)
+
+++ /dev/null
-//-----------------------------------------------------------------------------
-// This code is licensed to you under the terms of the GNU GPL, version 2 or,
-// at your option, any later version. See the LICENSE.txt file for the text of
-// the license.
-//-----------------------------------------------------------------------------
-// Command line binary
-//-----------------------------------------------------------------------------
-
-#include <stdio.h>
-#include "sleep.h"
-#include "ui.h"
-#include "proxusb.h"
-#include "cmdmain.h"
-
-#define HANDLE_ERROR if (error_occured) { \
- error_occured = 0;\
- break;\
-}
-
-int main(int argc, char **argv)
-{
- if (argc != 3 && argc != 4)
- {
- printf("\n\tusage: cli <command 1> <command 2> [logfile (default cli.log)]\n");
- printf("\n");
- printf("\texample: cli hi14asnoop hi14alist h14a.log\n");
- printf("\n");
- return -1;
- }
-
- usb_init();
- if (argc == 4)
- SetLogFilename(argv[3]);
- else
- SetLogFilename("cli.log");
-
- return_on_error = 1;
-
- while (1) {
- while (!OpenProxmark(0)) { sleep(1); }
- while (1) {
- UsbCommand cmdbuf;
- CommandReceived(argv[1]);
- HANDLE_ERROR;
- ReceiveCommand(&cmdbuf);
- HANDLE_ERROR;
- for (int i = 0; i < 5; ++i) {
- ReceiveCommandPoll(&cmdbuf);
- }
- HANDLE_ERROR;
- CommandReceived(argv[2]);
- HANDLE_ERROR;
- }
- }
-
- CloseProxmark();
- return 0;
-}
+++ /dev/null
-//-----------------------------------------------------------------------------
-// Copyright (C) 2009 Michael Gernoth <michael at gernoth.net>
-//
-// This code is licensed to you under the terms of the GNU GPL, version 2 or,
-// at your option, any later version. See the LICENSE.txt file for the text of
-// the license.
-//-----------------------------------------------------------------------------
-// GUI dummy file
-//-----------------------------------------------------------------------------
-
-#include <stdio.h>
-
-void ShowGraphWindow(void)
-{
- static int warned = 0;
-
- if (!warned) {
- printf("No GUI in this build!\n");
- warned = 1;
- }
-}
-
-void HideGraphWindow(void) {}
-void RepaintGraphWindow(void) {}
-void MainGraphics() {}
-void InitGraphics(int argc, char **argv) {}
-void ExitGraphics(void) {}
--- /dev/null
+//-----------------------------------------------------------------------------
+// Copyright (C) 2009 Michael Gernoth <michael at gernoth.net>
+//
+// This code is licensed to you under the terms of the GNU GPL, version 2 or,
+// at your option, any later version. See the LICENSE.txt file for the text of
+// the license.
+//-----------------------------------------------------------------------------
+// GUI dummy file
+//-----------------------------------------------------------------------------
+
+#include <stdio.h>
+
+extern "C" void ShowGraphWindow(void)
+{
+ static int warned = 0;
+
+ if (!warned) {
+ printf("No GUI in this build!\n");
+ warned = 1;
+ }
+}
+
+extern "C" void HideGraphWindow(void) {}
+extern "C" void RepaintGraphWindow(void) {}
+extern "C" void MainGraphics() {}
+extern "C" void InitGraphics(int argc, char **argv) {}
+extern "C" void ExitGraphics(void) {}
--[[
-These are command definitions. This file should correspond exactly to usb_cmd.h.
+Handle Proxmark USB Commands
--]]
---// For the bootloader
-local _commands = {
- CMD_DEVICE_INFO = 0x0000,
- CMD_SETUP_WRITE = 0x0001,
- CMD_FINISH_WRITE = 0x0003,
- CMD_HARDWARE_RESET = 0x0004,
- CMD_START_FLASH = 0x0005,
- CMD_NACK = 0x00fe,
- CMD_ACK = 0x00ff,
-
- --// For general mucking around
- CMD_DEBUG_PRINT_STRING = 0x0100,
- CMD_DEBUG_PRINT_INTEGERS = 0x0101,
- CMD_DEBUG_PRINT_BYTES = 0x0102,
- CMD_LCD_RESET = 0x0103,
- CMD_LCD = 0x0104,
- CMD_BUFF_CLEAR = 0x0105,
- CMD_READ_MEM = 0x0106,
- CMD_VERSION = 0x0107,
- CMD_STATUS = 0x0108,
- CMD_PING = 0x0109,
- --// For low-frequency tags
- CMD_READ_TI_TYPE = 0x0202,
- CMD_WRITE_TI_TYPE = 0x0203,
- CMD_DOWNLOADED_RAW_BITS_TI_TYPE = 0x0204,
- CMD_ACQUIRE_RAW_ADC_SAMPLES_125K = 0x0205,
- CMD_MOD_THEN_ACQUIRE_RAW_ADC_SAMPLES_125K = 0x0206,
- CMD_DOWNLOAD_RAW_ADC_SAMPLES_125K = 0x0207,
- CMD_DOWNLOADED_RAW_ADC_SAMPLES_125K = 0x0208,
- CMD_DOWNLOADED_SIM_SAMPLES_125K = 0x0209,
- CMD_SIMULATE_TAG_125K = 0x020A,
- CMD_HID_DEMOD_FSK = 0x020B,
- CMD_HID_SIM_TAG = 0x020C,
- CMD_SET_LF_DIVISOR = 0x020D,
- CMD_LF_SIMULATE_BIDIR = 0x020E,
- CMD_SET_ADC_MUX = 0x020F,
- CMD_HID_CLONE_TAG = 0x0210,
- CMD_EM410X_WRITE_TAG = 0x0211,
- CMD_INDALA_CLONE_TAG = 0x0212,
- --// for 224 bits UID
- CMD_INDALA_CLONE_TAG_L = 0x0213,
- CMD_T55XX_READ_BLOCK = 0x0214,
- CMD_T55XX_WRITE_BLOCK = 0x0215,
- CMD_T55XX_RESET_READ = 0x0216,
- CMD_PCF7931_READ = 0x0217,
- CMD_EM4X_READ_WORD = 0x0218,
- CMD_EM4X_WRITE_WORD = 0x0219,
- CMD_IO_DEMOD_FSK = 0x021A,
- CMD_IO_CLONE_TAG = 0x021B,
- CMD_EM410X_DEMOD = 0x021c,
- CMD_SET_LF_SAMPLING_CONFIG = 0x021d,
- CMD_FSK_SIM_TAG = 0x021E,
- CMD_ASK_SIM_TAG = 0x021F,
- CMD_PSK_SIM_TAG = 0x0220,
- CMD_AWID_DEMOD_FSK = 0x0221,
- CMD_VIKING_CLONE_TAG = 0x0223,
- CMD_T55XX_WAKEUP = 0x0224,
- CMD_COTAG = 0x0225,
- --/* CMD_SET_ADC_MUX: ext1 is 0 for lopkd, 1 for loraw, 2 for hipkd, 3 for hiraw */
-
- --// For the 13.56 MHz tags
- CMD_ACQUIRE_RAW_ADC_SAMPLES_ISO_15693 = 0x0300,
- CMD_READ_SRI512_TAG = 0x0303,
- CMD_READ_SRIX4K_TAG = 0x0304,
- CMD_READER_ISO_15693 = 0x0310,
- CMD_SIMTAG_ISO_15693 = 0x0311,
- CMD_RECORD_RAW_ADC_SAMPLES_ISO_15693 = 0x0312,
- CMD_ISO_15693_COMMAND = 0x0313,
- CMD_ISO_15693_COMMAND_DONE = 0x0314,
- CMD_ISO_15693_FIND_AFI = 0x0315,
- CMD_ISO_15693_DEBUG = 0x0316,
- CMD_LF_SNOOP_RAW_ADC_SAMPLES = 0x0317,
-
- --// For Hitag2 transponders
- CMD_SNOOP_HITAG = 0x0370,
- CMD_SIMULATE_HITAG = 0x0371,
- CMD_READER_HITAG = 0x0372,
-
- CMD_SIMULATE_TAG_ISO_14443B = 0x0381,
- CMD_SNOOP_ISO_14443B = 0x0382,
- CMD_SNOOP_ISO_14443a = 0x0383,
- CMD_SIMULATE_TAG_ISO_14443a = 0x0384,
- CMD_READER_ISO_14443a = 0x0385,
- CMD_SIMULATE_TAG_LEGIC_RF = 0x0387,
- CMD_READER_LEGIC_RF = 0x0388,
- CMD_WRITER_LEGIC_RF = 0x0389,
- CMD_EPA_PACE_COLLECT_NONCE = 0x038A,
- --//CMD_EPA_ = 0x038B,
-
- CMD_ICLASS_READCHECK = 0x038F,
- CMD_ICLASS_CLONE = 0x0390,
- CMD_ICLASS_DUMP = 0x0391,
- CMD_SNOOP_ICLASS = 0x0392,
- CMD_SIMULATE_TAG_ICLASS = 0x0393,
- CMD_READER_ICLASS = 0x0394,
- CMD_READER_ICLASS_REPLAY = 0x0395,
- CMD_ICLASS_READBLOCK = 0x0396,
- CMD_ICLASS_WRITEBLOCK = 0x0397,
- CMD_ICLASS_EML_MEMSET = 0x0398,
- CMD_ICLASS_AUTHENTICATION = 0x0399,
-
- --// For measurements of the antenna tuning
- CMD_MEASURE_ANTENNA_TUNING = 0x0400,
- CMD_MEASURE_ANTENNA_TUNING_HF = 0x0401,
- CMD_MEASURED_ANTENNA_TUNING = 0x0410,
- CMD_LISTEN_READER_FIELD = 0x0420,
-
- --// For direct FPGA control
- CMD_FPGA_MAJOR_MODE_OFF = 0x0500,
-
- --// For mifare commands
- CMD_MIFARE_SET_DBGMODE = 0x0600,
- CMD_MIFARE_EML_MEMCLR = 0x0601,
- CMD_MIFARE_EML_MEMSET = 0x0602,
- CMD_MIFARE_EML_MEMGET = 0x0603,
- CMD_MIFARE_EML_CARDLOAD = 0x0604,
-
- --// magic chinese card commands
- CMD_MIFARE_CSETBLOCK = 0x0605,
- CMD_MIFARE_CGETBLOCK = 0x0606,
- CMD_MIFARE_CIDENT = 0x0607,
-
- CMD_SIMULATE_MIFARE_CARD = 0x0610,
-
- CMD_READER_MIFARE = 0x0611,
- CMD_MIFARE_NESTED = 0x0612,
-
- CMD_MIFARE_READBL = 0x0620,
- CMD_MIFAREU_READBL = 0x0720,
-
- CMD_MIFARE_READSC = 0x0621,
- CMD_MIFAREU_READCARD = 0x0721,
-
- CMD_MIFARE_WRITEBL = 0x0622,
- CMD_MIFAREU_WRITEBL = 0x0722,
- CMD_MIFAREU_WRITEBL_COMPAT = 0x0723,
-
- CMD_MIFARE_CHKKEYS = 0x0623,
-
- CMD_MIFARE_SNIFFER = 0x0630,
-
- --//ultralightC
- CMD_MIFAREUC_AUTH = 0x0724,
- CMD_MIFAREUC_SETPWD = 0x0727,
- CMD_MIFAREU_SETUID = 0x0728,
-
- --// mifare desfire
- CMD_MIFARE_DESFIRE_READBL = 0x0728,
- CMD_MIFARE_DESFIRE_WRITEBL = 0x0729,
- CMD_MIFARE_DESFIRE_AUTH1 = 0x072a,
- CMD_MIFARE_DESFIRE_AUTH2 = 0x072b,
- CMD_MIFARE_DES_READER = 0x072c,
- CMD_MIFARE_DESFIRE_INFO = 0x072d,
- CMD_MIFARE_DESFIRE = 0x072e,
-
- CMD_UNKNOWN = 0xFFFF,
-}
+local _commands = require('usb_cmd')
local _reverse_lookup,k,v = {}
for k, v in pairs(_commands) do
--- /dev/null
+--[[
+These are Proxmark command definitions.
+This file is automatically generated from usb_cmd.h - DON'T EDIT MANUALLY.
+--]]
+local __commands = {
+CMD_DEVICE_INFO = 0x0000,
+CMD_SETUP_WRITE = 0x0001,
+CMD_FINISH_WRITE = 0x0003,
+CMD_HARDWARE_RESET = 0x0004,
+CMD_START_FLASH = 0x0005,
+CMD_NACK = 0x00fe,
+CMD_ACK = 0x00ff,
+CMD_DEBUG_PRINT_STRING = 0x0100,
+CMD_DEBUG_PRINT_INTEGERS = 0x0101,
+CMD_DEBUG_PRINT_BYTES = 0x0102,
+CMD_LCD_RESET = 0x0103,
+CMD_LCD = 0x0104,
+CMD_BUFF_CLEAR = 0x0105,
+CMD_READ_MEM = 0x0106,
+CMD_VERSION = 0x0107,
+CMD_STATUS = 0x0108,
+CMD_PING = 0x0109,
+CMD_READ_TI_TYPE = 0x0202,
+CMD_WRITE_TI_TYPE = 0x0203,
+CMD_DOWNLOADED_RAW_BITS_TI_TYPE = 0x0204,
+CMD_ACQUIRE_RAW_ADC_SAMPLES_125K = 0x0205,
+CMD_MOD_THEN_ACQUIRE_RAW_ADC_SAMPLES_125K = 0x0206,
+CMD_DOWNLOAD_RAW_ADC_SAMPLES_125K = 0x0207,
+CMD_DOWNLOADED_RAW_ADC_SAMPLES_125K = 0x0208,
+CMD_DOWNLOADED_SIM_SAMPLES_125K = 0x0209,
+CMD_SIMULATE_TAG_125K = 0x020A,
+CMD_HID_DEMOD_FSK = 0x020B,
+CMD_HID_SIM_TAG = 0x020C,
+CMD_SET_LF_DIVISOR = 0x020D,
+CMD_LF_SIMULATE_BIDIR = 0x020E,
+CMD_SET_ADC_MUX = 0x020F,
+CMD_HID_CLONE_TAG = 0x0210,
+CMD_EM410X_WRITE_TAG = 0x0211,
+CMD_INDALA_CLONE_TAG = 0x0212,
+CMD_INDALA_CLONE_TAG_L = 0x0213,
+CMD_T55XX_READ_BLOCK = 0x0214,
+CMD_T55XX_WRITE_BLOCK = 0x0215,
+CMD_T55XX_RESET_READ = 0x0216,
+CMD_PCF7931_READ = 0x0217,
+CMD_PCF7931_WRITE = 0x0222,
+CMD_EM4X_READ_WORD = 0x0218,
+CMD_EM4X_WRITE_WORD = 0x0219,
+CMD_IO_DEMOD_FSK = 0x021A,
+CMD_IO_CLONE_TAG = 0x021B,
+CMD_EM410X_DEMOD = 0x021c,
+CMD_SET_LF_SAMPLING_CONFIG = 0x021d,
+CMD_FSK_SIM_TAG = 0x021E,
+CMD_ASK_SIM_TAG = 0x021F,
+CMD_PSK_SIM_TAG = 0x0220,
+CMD_AWID_DEMOD_FSK = 0x0221,
+CMD_VIKING_CLONE_TAG = 0x0223,
+CMD_T55XX_WAKEUP = 0x0224,
+CMD_COTAG = 0x0225,
+CMD_ACQUIRE_RAW_ADC_SAMPLES_ISO_15693 = 0x0300,
+CMD_READ_SRI512_TAG = 0x0303,
+CMD_READ_SRIX4K_TAG = 0x0304,
+CMD_ISO_14443B_COMMAND = 0x0305,
+CMD_READER_ISO_15693 = 0x0310,
+CMD_SIMTAG_ISO_15693 = 0x0311,
+CMD_RECORD_RAW_ADC_SAMPLES_ISO_15693 = 0x0312,
+CMD_ISO_15693_COMMAND = 0x0313,
+CMD_ISO_15693_COMMAND_DONE = 0x0314,
+CMD_ISO_15693_FIND_AFI = 0x0315,
+CMD_ISO_15693_DEBUG = 0x0316,
+CMD_LF_SNOOP_RAW_ADC_SAMPLES = 0x0317,
+CMD_SNOOP_HITAG = 0x0370,
+CMD_SIMULATE_HITAG = 0x0371,
+CMD_READER_HITAG = 0x0372,
+CMD_SIMULATE_HITAG_S = 0x0368,
+CMD_TEST_HITAGS_TRACES = 0x0367,
+CMD_READ_HITAG_S = 0x0373,
+CMD_WR_HITAG_S = 0x0375,
+CMD_EMU_HITAG_S = 0x0376,
+CMD_SIMULATE_TAG_ISO_14443B = 0x0381,
+CMD_SNOOP_ISO_14443B = 0x0382,
+CMD_SNOOP_ISO_14443a = 0x0383,
+CMD_SIMULATE_TAG_ISO_14443a = 0x0384,
+CMD_READER_ISO_14443a = 0x0385,
+CMD_SIMULATE_TAG_LEGIC_RF = 0x0387,
+CMD_READER_LEGIC_RF = 0x0388,
+CMD_WRITER_LEGIC_RF = 0x0389,
+CMD_EPA_PACE_COLLECT_NONCE = 0x038A,
+CMD_EPA_PACE_REPLAY = 0x038B,
+CMD_ICLASS_READCHECK = 0x038F,
+CMD_ICLASS_CLONE = 0x0390,
+CMD_ICLASS_DUMP = 0x0391,
+CMD_SNOOP_ICLASS = 0x0392,
+CMD_SIMULATE_TAG_ICLASS = 0x0393,
+CMD_READER_ICLASS = 0x0394,
+CMD_READER_ICLASS_REPLAY = 0x0395,
+CMD_ICLASS_READBLOCK = 0x0396,
+CMD_ICLASS_WRITEBLOCK = 0x0397,
+CMD_ICLASS_EML_MEMSET = 0x0398,
+CMD_ICLASS_AUTHENTICATION = 0x0399,
+CMD_MEASURE_ANTENNA_TUNING = 0x0400,
+CMD_MEASURE_ANTENNA_TUNING_HF = 0x0401,
+CMD_MEASURED_ANTENNA_TUNING = 0x0410,
+CMD_LISTEN_READER_FIELD = 0x0420,
+CMD_FPGA_MAJOR_MODE_OFF = 0x0500,
+CMD_MIFARE_SET_DBGMODE = 0x0600,
+CMD_MIFARE_EML_MEMCLR = 0x0601,
+CMD_MIFARE_EML_MEMSET = 0x0602,
+CMD_MIFARE_EML_MEMGET = 0x0603,
+CMD_MIFARE_EML_CARDLOAD = 0x0604,
+CMD_MIFARE_CSETBLOCK = 0x0605,
+CMD_MIFARE_CGETBLOCK = 0x0606,
+CMD_MIFARE_CIDENT = 0x0607,
+CMD_SIMULATE_MIFARE_CARD = 0x0610,
+CMD_READER_MIFARE = 0x0611,
+CMD_MIFARE_NESTED = 0x0612,
+CMD_MIFARE_READBL = 0x0620,
+CMD_MIFAREU_READBL = 0x0720,
+CMD_MIFARE_READSC = 0x0621,
+CMD_MIFAREU_READCARD = 0x0721,
+CMD_MIFARE_WRITEBL = 0x0622,
+CMD_MIFAREU_WRITEBL = 0x0722,
+CMD_MIFAREU_WRITEBL_COMPAT = 0x0723,
+CMD_MIFARE_CHKKEYS = 0x0623,
+CMD_MIFARE_SNIFFER = 0x0630,
+CMD_MIFAREUC_AUTH = 0x0724,
+CMD_MIFAREUC_SETPWD = 0x0727,
+CMD_MIFARE_DESFIRE_READBL = 0x0728,
+CMD_MIFARE_DESFIRE_WRITEBL = 0x0729,
+CMD_MIFARE_DESFIRE_AUTH1 = 0x072a,
+CMD_MIFARE_DESFIRE_AUTH2 = 0x072b,
+CMD_MIFARE_DES_READER = 0x072c,
+CMD_MIFARE_DESFIRE_INFO = 0x072d,
+CMD_MIFARE_DESFIRE = 0x072e,
+CMD_HF_SNIFFER = 0x0800,
+CMD_UNKNOWN = 0xFFFF,
+}
+return __commands
+++ /dev/null
-//-----------------------------------------------------------------------------
-// Copyright (C) 2009 Michael Gernoth <michael at gernoth.net>
-//
-// This code is licensed to you under the terms of the GNU GPL, version 2 or,
-// at your option, any later version. See the LICENSE.txt file for the text of
-// the license.
-//-----------------------------------------------------------------------------
-// Snooper binary
-//-----------------------------------------------------------------------------
-
-#include "ui.h"
-#include "proxusb.h"
-#include "cmdmain.h"
-
-#define HANDLE_ERROR if (error_occured) { \
- error_occured = 0;\
- break;\
-}
-
-int main()
-{
- usb_init();
- SetLogFilename("snooper.log");
-
- return_on_error = 1;
-
- while(1) {
- while (!OpenProxmark(0)) { sleep(1); }
- while (1) {
- UsbCommand cmdbuf;
- CommandReceived("hf 14a snoop");
- HANDLE_ERROR;
- ReceiveCommand(&cmdbuf);
- HANDLE_ERROR;
- for (int i = 0; i < 5; ++i) {
- ReceiveCommandPoll(&cmdbuf);
- }
- HANDLE_ERROR;
- CommandReceived("hf 14a list");
- HANDLE_ERROR;
- }
- }
-
- CloseProxmark();
- return 0;
-}
--- /dev/null
+BEGIN {
+ print "--[["
+ print "These are Proxmark command definitions."
+ print "This file is automatically generated from usb_cmd.h - DON'T EDIT MANUALLY."
+ print "--]]"
+ print "local __commands = {"
+}
+
+#$1 ~ /#define/ && $2 ~ /^CMD_([[:alnum:]_])+/ { print $2, "=", $3, "," }
+$1 ~ /#define/ && $2 ~ /^CMD_[A-Za-z0-9_]+/ { sub(/\r/, ""); print $2, "=", $3 "," }
+
+END {
+ print "}"
+ print "return __commands"
+}
// a milliseconds timer for performance measurement
uint64_t msclock() {
#if defined(_WIN32)
-#include <sys/types.h>
- struct _timeb t;
- if (_ftime_s(&t)) {
- return 0;
- } else {
- return 1000 * t.time + t.millitm;
- }
+ #include <sys/types.h>
+
+ // WORKAROUND FOR MinGW (some versions - use if normal code does not compile)
+ // It has no _ftime_s and needs explicit inclusion of timeb.h
+ #include <sys/timeb.h>
+ struct _timeb t;
+ _ftime(&t);
+ return 1000 * t.time + t.millitm;
+
+ // NORMAL CODE (use _ftime_s)
+ //struct _timeb t;
+ //if (_ftime_s(&t)) {
+ // return 0;
+ //} else {
+ // return 1000 * t.time + t.millitm;
+ //}
#else
struct timespec t;
clock_gettime(CLOCK_MONOTONIC, &t);