mirror of
https://github.com/RfidResearchGroup/proxmark3.git
synced 2025-08-21 05:43:48 -07:00
added "hf mf supercard" , to extract key from card
This commit is contained in:
parent
748f067143
commit
257358ac12
1 changed files with 123 additions and 4 deletions
|
@ -18,13 +18,16 @@
|
|||
#include "cmdtrace.h"
|
||||
#include "emv/dump.h"
|
||||
#include "mifare/mifaredefault.h" // mifare default key array
|
||||
#include "cliparser.h" // argtable
|
||||
#include "cliparser.h" // argtable
|
||||
#include "hardnested_bf_core.h" // SetSIMDInstr
|
||||
#include "mifare/mad.h"
|
||||
#include "mifare/ndef.h"
|
||||
#include "protocols.h"
|
||||
#include "util_posix.h" // msclock
|
||||
#include "util_posix.h" // msclock
|
||||
#include "cmdhfmfhard.h"
|
||||
#include "des.h" // des ecb
|
||||
#include "crapto1/crapto1.h" // prng_successor
|
||||
#include "cmdhf14a.h" // exchange APDU
|
||||
|
||||
#define MFBLOCK_SIZE 16
|
||||
|
||||
|
@ -627,7 +630,6 @@ static void decode_print_st(uint16_t blockno, uint8_t *data) {
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
static uint16_t NumOfBlocks(char card) {
|
||||
switch (card) {
|
||||
case '0' :
|
||||
|
@ -3691,7 +3693,6 @@ static int CmdHF14AMfEGetSc(const char *Cmd) {
|
|||
return PM3_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
static int CmdHF14AMfEClear(const char *Cmd) {
|
||||
char c = tolower(param_getchar(Cmd, 0));
|
||||
if (c == 'h') return usage_hf14_eclr();
|
||||
|
@ -5265,6 +5266,123 @@ static int CmdHf14AGen3Freeze(const char *Cmd) {
|
|||
return PM3_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
static void des_decrypt(void *out, const void *in, const void *key) {
|
||||
mbedtls_des_context ctx;
|
||||
mbedtls_des_setkey_dec(&ctx, key);
|
||||
mbedtls_des_crypt_ecb(&ctx, in, out);
|
||||
}
|
||||
|
||||
static int CmdHf14AMfSuperCard(const char *Cmd) {
|
||||
|
||||
CLIParserContext *ctx;
|
||||
CLIParserInit(&ctx, "hf mf supercard",
|
||||
"Extract info from a `super card`",
|
||||
"hf mf supercard");
|
||||
|
||||
void *argtable[] = {
|
||||
arg_param_begin,
|
||||
arg_param_end
|
||||
};
|
||||
CLIExecWithReturn(ctx, Cmd, argtable, true);
|
||||
CLIParserFree(ctx);
|
||||
/*
|
||||
uint8_t reset[] = { 0x02, 0x00, 0xa6, 0xc0, 0x00 };
|
||||
*/
|
||||
|
||||
bool activate_field = true;
|
||||
bool keep_field_on = true;
|
||||
uint8_t responseA[22];
|
||||
uint8_t responseB[22];
|
||||
int respAlen = 0;
|
||||
int respBlen = 0;
|
||||
|
||||
// --------------- First ----------------
|
||||
uint8_t aFIRST[] = { 0x00, 0xa6, 0xb0, 0x00, 0x10 };
|
||||
int res = ExchangeAPDU14a(aFIRST, sizeof(aFIRST), activate_field, keep_field_on, responseA, sizeof(responseA), &respAlen);
|
||||
if (res) {
|
||||
DropField();
|
||||
return res;
|
||||
}
|
||||
|
||||
// --------------- Second ----------------
|
||||
activate_field = false;
|
||||
keep_field_on = false;
|
||||
|
||||
uint8_t aSECOND[] = { 0x00, 0xa6, 0xb0, 0x01, 0x10 };
|
||||
res = ExchangeAPDU14a(aSECOND, sizeof(aSECOND), activate_field, keep_field_on, responseB, sizeof(responseB), &respBlen);
|
||||
if (res) {
|
||||
DropField();
|
||||
return res;
|
||||
}
|
||||
|
||||
// uint8_t inA[] = { 0x72, 0xD7, 0xF4, 0x3E, 0xFD, 0xAB, 0xF2, 0x35, 0xFD, 0x49, 0xEE, 0xDC, 0x44, 0x95, 0x43, 0xC4};
|
||||
// uint8_t inB[] = { 0xF0, 0xA2, 0x67, 0x6A, 0x04, 0x6A, 0x72, 0x12, 0x76, 0xA4, 0x1D, 0x02, 0x1F, 0xEA, 0x20, 0x85};
|
||||
|
||||
uint8_t outA[16] = {0};
|
||||
uint8_t outB[16] = {0};
|
||||
|
||||
uint8_t key[] = {0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88};
|
||||
for (uint8_t i=0; i < 16; i += 8) {
|
||||
des_decrypt(outA + i, responseA + i, key);
|
||||
des_decrypt(outB + i, responseB + i, key);
|
||||
}
|
||||
|
||||
PrintAndLogEx(INFO, " in : %s", sprint_hex_inrow(responseA, respAlen));
|
||||
PrintAndLogEx(INFO, "out : %s", sprint_hex_inrow(outA, sizeof(outA)));
|
||||
|
||||
PrintAndLogEx(INFO, " in : %s", sprint_hex_inrow(responseB, respAlen));
|
||||
PrintAndLogEx(INFO, "out : %s", sprint_hex_inrow(outB, sizeof(outB)));
|
||||
|
||||
if (memcmp(outA, "\x01\x01\x01\x01\x01\x01\x01\x01", 8) == 0) {
|
||||
PrintAndLogEx(INFO, "No trace recorded");
|
||||
return PM3_SUCCESS;
|
||||
}
|
||||
|
||||
// second trace?
|
||||
if (memcmp(outB, "\x01\x01\x01\x01\x01\x01\x01\x01", 8) == 0) {
|
||||
PrintAndLogEx(INFO, "Only one trace recorded");
|
||||
return PM3_SUCCESS;
|
||||
}
|
||||
|
||||
nonces_t data;
|
||||
|
||||
// first
|
||||
uint16_t NT0 = (outA[6] << 8) | outA[7];
|
||||
data.cuid = bytes_to_num(outA, 4);
|
||||
data.nonce = prng_successor(NT0, 31);
|
||||
data.nr = bytes_to_num(outA + 8, 4);
|
||||
data.ar = bytes_to_num(outA + 12, 4);
|
||||
data.at = 0;
|
||||
|
||||
// second
|
||||
NT0 = (outB[6] << 8) | outB[7];
|
||||
data.nonce2 = prng_successor(NT0, 31);;
|
||||
data.nr2 = bytes_to_num(outB + 8, 4);
|
||||
data.ar2 = bytes_to_num(outB + 12, 4);
|
||||
data.sector = 0;
|
||||
data.keytype = outA[4];
|
||||
data.state = FIRST;
|
||||
|
||||
PrintAndLogEx(DEBUG, "A NT %08x", data.nonce);
|
||||
PrintAndLogEx(DEBUG, "A NR %08x", data.nr);
|
||||
PrintAndLogEx(DEBUG, "A AR %08x", data.ar);
|
||||
PrintAndLogEx(DEBUG, "");
|
||||
PrintAndLogEx(DEBUG, "B NT %08x", data.nonce2);
|
||||
PrintAndLogEx(DEBUG, "B NR %08x", data.nr2);
|
||||
PrintAndLogEx(DEBUG, "B AR %08x", data.ar2);
|
||||
|
||||
uint64_t key64 = -1;
|
||||
res = mfkey32_moebius(&data, &key64);
|
||||
|
||||
if (res)
|
||||
PrintAndLogEx(SUCCESS, "recovered key [ " _GREEN_("%12" PRIX64) " ]", key64);
|
||||
else
|
||||
PrintAndLogEx(FAILED, "failed to recover any key");
|
||||
|
||||
return PM3_SUCCESS;
|
||||
}
|
||||
|
||||
static command_t CommandTable[] = {
|
||||
{"help", CmdHelp, AlwaysAvailable, "This help"},
|
||||
{"list", CmdHF14AMfList, AlwaysAvailable, "List MIFARE history"},
|
||||
|
@ -5279,6 +5397,7 @@ static command_t CommandTable[] = {
|
|||
{"chk", CmdHF14AMfChk, IfPm3Iso14443a, "Check keys"},
|
||||
{"fchk", CmdHF14AMfChk_fast, IfPm3Iso14443a, "Check keys fast, targets all keys on card"},
|
||||
{"decrypt", CmdHf14AMfDecryptBytes, AlwaysAvailable, "[nt] [ar_enc] [at_enc] [data] - to decrypt sniff or trace"},
|
||||
{"supercard", CmdHf14AMfSuperCard, IfPm3Iso14443a, "Extract info from a `super card`"},
|
||||
{"-----------", CmdHelp, IfPm3Iso14443a, "----------------------- " _CYAN_("operations") " -----------------------"},
|
||||
{"auth4", CmdHF14AMfAuth4, IfPm3Iso14443a, "ISO14443-4 AES authentication"},
|
||||
{"dump", CmdHF14AMfDump, IfPm3Iso14443a, "Dump MIFARE Classic tag to binary file"},
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue