From 33715f768543f5c1f9d45d2877fdae39189608e0 Mon Sep 17 00:00:00 2001 From: merlokk Date: Fri, 6 Oct 2017 21:45:52 +0300 Subject: [PATCH] hf mf chk. Added text output and smal refactoring arm part --- armsrc/mifarecmd.c | 71 ++++++++++++++++++++++++++++++++++++++++------ client/cmdhfmf.c | 16 +++++++++++ 2 files changed, 79 insertions(+), 8 deletions(-) diff --git a/armsrc/mifarecmd.c b/armsrc/mifarecmd.c index a3f0d374..f9793d4b 100644 --- a/armsrc/mifarecmd.c +++ b/armsrc/mifarecmd.c @@ -961,6 +961,48 @@ void MifareNested(uint32_t arg0, uint32_t arg1, uint32_t calibrate, uint8_t *dat // MIFARE check keys. key count up to 85. // //----------------------------------------------------------------------------- +// one key check +int MifareChkKey(uint8_t *uid, uint32_t *cuid, uint8_t *cascade_levels, uint64_t ui64Key, uint8_t blockNo, uint8_t keyType, uint8_t debugLevel) { + + uint32_t timeout = 0; + struct Crypto1State mpcs = {0, 0}; + struct Crypto1State *pcs; + pcs = &mpcs; + + // Iceman: use piwi's faster nonce collecting part in hardnested. + if (*cascade_levels == 0) { // need a full select cycle to get the uid first + iso14a_card_select_t card_info; + if(!iso14443a_select_card(uid, &card_info, cuid, true, 0, true)) { + if (debugLevel >= 1) Dbprintf("ChkKeys: Can't select card"); + return 1; + } + switch (card_info.uidlen) { + case 4 : *cascade_levels = 1; break; + case 7 : *cascade_levels = 2; break; + case 10: *cascade_levels = 3; break; + default: break; + } + } else { // no need for anticollision. We can directly select the card + if(!iso14443a_select_card(uid, NULL, NULL, false, *cascade_levels, true)) { + if (debugLevel >= 1) Dbprintf("ChkKeys: Can't select card (UID) %d", *cascade_levels); + return 1; + } + } + + if(mifare_classic_auth(pcs, *cuid, blockNo, keyType, ui64Key, AUTH_FIRST)) { + uint8_t dummy_answer = 0; + ReaderTransmit(&dummy_answer, 1, NULL); + timeout = GetCountSspClk() + AUTHENTICATION_TIMEOUT; + + // wait for the card to become ready again + while(GetCountSspClk() < timeout); + return 1; + } + + return 0; +} + +// multi key check void MifareChkKeys(uint16_t arg0, uint8_t arg1, uint8_t arg2, uint8_t *datain) { uint8_t blockNo = arg0 & 0xff; @@ -969,16 +1011,12 @@ void MifareChkKeys(uint16_t arg0, uint8_t arg1, uint8_t arg2, uint8_t *datain) uint8_t keyCount = arg2; uint64_t ui64Key = 0; - bool have_uid = false; +// bool have_uid = false; uint8_t cascade_levels = 0; - uint32_t timeout = 0; int i; byte_t isOK = 0; uint8_t uid[10]; - uint32_t cuid; - struct Crypto1State mpcs = {0, 0}; - struct Crypto1State *pcs; - pcs = &mpcs; + uint32_t cuid = 0; // clear debug level int OLD_MF_DBGLEVEL = MF_DBGLEVEL; @@ -997,7 +1035,24 @@ void MifareChkKeys(uint16_t arg0, uint8_t arg1, uint8_t arg2, uint8_t *datain) // if (MF_DBGLEVEL >= 1) Dbprintf("ChkKeys: Halt error"); // } - // Iceman: use piwi's faster nonce collecting part in hardnested. + // Allow button press / usb cmd to interrupt device + if (BUTTON_PRESS()) { // && !usb_poll_validate_length() + Dbprintf("ChkKeys: Cancel operation. Exit..."); + break; + } + + ui64Key = bytes_to_num(datain + i * 6, 6); + switch (MifareChkKey(uid, &cuid, &cascade_levels, ui64Key, blockNo, keyType, OLD_MF_DBGLEVEL)) { + case 1: + //--i; // can't select. try same key once again + case 2: + continue; // can't auth. wrong key. + break; + default: + break; + } + +/* // Iceman: use piwi's faster nonce collecting part in hardnested. if (!have_uid) { // need a full select cycle to get the uid first iso14a_card_select_t card_info; if(!iso14443a_select_card(uid, &card_info, &cuid, true, 0, true)) { @@ -1030,7 +1085,7 @@ void MifareChkKeys(uint16_t arg0, uint8_t arg1, uint8_t arg2, uint8_t *datain) while(GetCountSspClk() < timeout); continue; } - +*/ isOK = 1; break; } diff --git a/client/cmdhfmf.c b/client/cmdhfmf.c index 295f22b7..c42bfb7f 100644 --- a/client/cmdhfmf.c +++ b/client/cmdhfmf.c @@ -1189,6 +1189,7 @@ int CmdHF14AMfChk(const char *Cmd) } } + bool foundAKey = false; for ( int t = !keyType; t < 2; keyType==2?(t++):(t=2) ) { int b=blockNo; for (int i = 0; i < SectorsCnt; ++i) { @@ -1202,6 +1203,7 @@ int CmdHF14AMfChk(const char *Cmd) PrintAndLog("Found valid key:[%012" PRIx64 "]",key64); num_to_bytes(key64, 6, foundKey[t][i]); validKey[t][i] = true; + foundAKey = true; } } else { PrintAndLog("Command execute timeout"); @@ -1211,6 +1213,20 @@ int CmdHF14AMfChk(const char *Cmd) } } + // print result + if (foundAKey) { + PrintAndLog(""); + PrintAndLog("|---|----------------|---|----------------|---|"); + PrintAndLog("|sec|key A |res|key B |res|"); + PrintAndLog("|---|----------------|---|----------------|---|"); + for (i = 0; i < SectorsCnt; i++) { + PrintAndLog("|%03d| %012" PRIx64 " | %d | %012" PRIx64 " | %d |", i, + bytes_to_num(foundKey[0][i], 6), validKey[0][i]?1:0, bytes_to_num(foundKey[1][i], 6), validKey[0][i]?1:0); + } + PrintAndLog("|---|----------------|---|----------------|---|"); + } + + if (transferToEml) { uint8_t block[16]; for (uint16_t sectorNo = 0; sectorNo < SectorsCnt; sectorNo++) {