From: iceman1001 Date: Sun, 14 Sep 2014 15:36:00 +0000 (+0200) Subject: Merge branch 'master' of https://github.com/Proxmark/proxmark3 X-Git-Url: http://git.zerfleddert.de/cgi-bin/gitweb.cgi/proxmark3-svn/commitdiff_plain/35147d51e3961db75a852368fffa31006da90199?ds=inline;hp=-c Merge branch 'master' of https://github.com/Proxmark/proxmark3 --- 35147d51e3961db75a852368fffa31006da90199 diff --combined client/cmdhfmf.c index 0d4813dd,b66aa3a6..e892b377 --- a/client/cmdhfmf.c +++ b/client/cmdhfmf.c @@@ -7,7 -7,7 +7,7 @@@ //----------------------------------------------------------------------------- // High frequency MIFARE commands //----------------------------------------------------------------------------- - +#include "../include/mifare.h" #include "cmdhfmf.h" static int CmdHelp(const char *Cmd); @@@ -140,7 -140,6 +140,7 @@@ int CmdHF14AMfWrBl(const char *Cmd return 0; } +/* dublett finns i CMDHFMFU.C int CmdHF14AMfUWrBl(const char *Cmd) { uint8_t blockNo = 0; @@@ -250,7 -249,8 +250,7 @@@ } return 0; } - - +*/ int CmdHF14AMfRdBl(const char *Cmd) { uint8_t blockNo = 0; @@@ -299,7 -299,6 +299,7 @@@ return 0; } +/* dublett finns i CMDHFMFU.C int CmdHF14AMfURdBl(const char *Cmd) { uint8_t blockNo = 0; @@@ -331,9 -330,8 +331,9 @@@ return 0; } +*/ - +/* dublett finns i CMDHFMFU.C int CmdHF14AMfURdCard(const char *Cmd) { int i; @@@ -424,7 -422,7 +424,7 @@@ } return 0; } - +*/ int CmdHF14AMfRdSc(const char *Cmd) { @@@ -519,16 -517,7 +519,16 @@@ int CmdHF14AMfDump(const char *Cmd UsbCommand resp; + int size = GetCardSize(); char cmdp = param_getchar(Cmd, 0); + + PrintAndLog("Got %d",size); + + return; + + if ( size > -1) + cmdp = (char)48+size; + switch (cmdp) { case '0' : numSectors = 5; break; case '1' : @@@ -552,7 -541,8 +552,7 @@@ return 1; } - // Read key file - + // Read keys A from file for (sectorNo=0; sectorNo>4) | ((data[8] & 0x1)<<1) | ((data[8] & 0x10)>>2); - rights[sectorNo][1] = ((data[7] & 0x20)>>5) | ((data[8] & 0x2)<<0) | ((data[8] & 0x20)>>3); - rights[sectorNo][2] = ((data[7] & 0x40)>>6) | ((data[8] & 0x4)>>1) | ((data[8] & 0x40)>>4); - rights[sectorNo][3] = ((data[7] & 0x80)>>7) | ((data[8] & 0x8)>>2) | ((data[8] & 0x80)>>5); + rights[sectorNo][0] = ((data[7] & 0x10)>>2) | ((data[8] & 0x1)<<1) | ((data[8] & 0x10)>>4); // C1C2C3 for data area 0 + rights[sectorNo][1] = ((data[7] & 0x20)>>3) | ((data[8] & 0x2)<<0) | ((data[8] & 0x20)>>5); // C1C2C3 for data area 1 + rights[sectorNo][2] = ((data[7] & 0x40)>>4) | ((data[8] & 0x4)>>1) | ((data[8] & 0x40)>>6); // C1C2C3 for data area 2 + rights[sectorNo][3] = ((data[7] & 0x80)>>5) | ((data[8] & 0x8)>>2) | ((data[8] & 0x80)>>7); // C1C2C3 for sector trailer } else { PrintAndLog("Could not get access rights for sector %2d. Trying with defaults...", sectorNo); - rights[sectorNo][0] = rights[sectorNo][1] = rights[sectorNo][2] = rights[sectorNo][3] = 0x01; + rights[sectorNo][0] = rights[sectorNo][1] = rights[sectorNo][2] = 0x00; + rights[sectorNo][3] = 0x01; } } else { PrintAndLog("Command execute timeout when trying to read access rights for sector %2d. Trying with defaults...", sectorNo); - rights[sectorNo][0] = rights[sectorNo][1] = rights[sectorNo][2] = rights[sectorNo][3] = 0x01; + rights[sectorNo][0] = rights[sectorNo][1] = rights[sectorNo][2] = 0x00; + rights[sectorNo][3] = 0x01; } } - // Read blocks and print to file - PrintAndLog("|-----------------------------------------|"); PrintAndLog("|----- Dumping all blocks to file... -----|"); PrintAndLog("|-----------------------------------------|"); @@@ -603,7 -598,6 +605,7 @@@ for (sectorNo = 0; isOK && sectorNo < numSectors; sectorNo++) { for (blockNo = 0; isOK && blockNo < NumBlocksPerSector(sectorNo); blockNo++) { bool received = false; + if (blockNo == NumBlocksPerSector(sectorNo) - 1) { // sector trailer. At least the Access Conditions can always be read with key A. UsbCommand c = {CMD_MIFARE_READBL, {FirstBlockOfSector(sectorNo) + blockNo, 0, 0}}; memcpy(c.d.asBytes, keyA[sectorNo], 6); @@@ -611,19 -605,19 +613,19 @@@ received = WaitForResponseTimeout(CMD_ACK,&resp,1500); } else { // data block. Check if it can be read with key A or key B uint8_t data_area = sectorNo<32?blockNo:blockNo/5; - if ((rights[sectorNo][data_area] == 3) || (rights[sectorNo][data_area] == 5)) { // only key B would work + if ((rights[sectorNo][data_area] == 0x03) || (rights[sectorNo][data_area] == 0x05)) { // only key B would work UsbCommand c = {CMD_MIFARE_READBL, {FirstBlockOfSector(sectorNo) + blockNo, 1, 0}}; memcpy(c.d.asBytes, keyB[sectorNo], 6); SendCommand(&c); received = WaitForResponseTimeout(CMD_ACK,&resp,1500); - } else if (rights[sectorNo][data_area] == 7) { // no key would work + } else if (rights[sectorNo][data_area] == 0x07) { // no key would work isOK = false; - PrintAndLog("Access rights do not allow reading of sector %2d block %3d", sectorNo, blockNo); + PrintAndLog("Access rights do not allow reading of sector %2d block %3d", sectorNo, blockNo); } else { // key A would work - UsbCommand c = {CMD_MIFARE_READBL, {FirstBlockOfSector(sectorNo) + blockNo, 0, 0}}; - memcpy(c.d.asBytes, keyA[sectorNo], 6); - SendCommand(&c); - received = WaitForResponseTimeout(CMD_ACK,&resp,1500); + UsbCommand c = {CMD_MIFARE_READBL, {FirstBlockOfSector(sectorNo) + blockNo, 0, 0}}; + memcpy(c.d.asBytes, keyA[sectorNo], 6); + SendCommand(&c); + received = WaitForResponseTimeout(CMD_ACK,&resp,1500); } } @@@ -658,6 -652,7 +660,6 @@@ break; } } - } if (isOK) { @@@ -670,7 -665,7 +672,7 @@@ fclose(fout); PrintAndLog("Dumped %d blocks (%d bytes) to file dumpdata.bin", numblocks, 16*numblocks); } - + fclose(fin); return 0; } @@@ -790,7 -785,7 +792,7 @@@ int CmdHF14AMfNested(const char *Cmd uint8_t trgKeyType = 0; uint8_t SectorsCnt = 0; uint8_t key[6] = {0, 0, 0, 0, 0, 0}; - uint8_t keyBlock[6*6]; + uint8_t keyBlock[13*6]; uint64_t key64 = 0; bool transferToEml = false; @@@ -820,15 -815,11 +822,15 @@@ cmdp = param_getchar(Cmd, 0); blockNo = param_get8(Cmd, 1); ctmp = param_getchar(Cmd, 2); + if (ctmp != 'a' && ctmp != 'A' && ctmp != 'b' && ctmp != 'B') { PrintAndLog("Key type must be A or B"); return 1; } - if (ctmp != 'A' && ctmp != 'a') keyType = 1; + + if (ctmp != 'A' && ctmp != 'a') + keyType = 1; + if (param_gethex(Cmd, 3, key, 12)) { PrintAndLog("Key must include 12 HEX symbols"); return 1; @@@ -842,12 -833,8 +844,12 @@@ PrintAndLog("Target key type must be A or B"); return 1; } - if (ctmp != 'A' && ctmp != 'a') trgKeyType = 1; + if (ctmp != 'A' && ctmp != 'a') + trgKeyType = 1; } else { + + + switch (cmdp) { case '0': SectorsCnt = 05; break; case '1': SectorsCnt = 16; break; @@@ -909,14 -896,6 +911,14 @@@ num_to_bytes(0xa0a1a2a3a4a5, 6, (uint8_t*)(keyBlock + 3 * 6)); num_to_bytes(0xb0b1b2b3b4b5, 6, (uint8_t*)(keyBlock + 4 * 6)); num_to_bytes(0xaabbccddeeff, 6, (uint8_t*)(keyBlock + 5 * 6)); + num_to_bytes(0x4d3a99c351dd, 6, (uint8_t*)(keyBlock + 6 * 6)); + num_to_bytes(0x1a982c7e459a, 6, (uint8_t*)(keyBlock + 7 * 6)); + num_to_bytes(0xd3f7d3f7d3f7, 6, (uint8_t*)(keyBlock + 8 * 6)); + num_to_bytes(0x714c5c886e97, 6, (uint8_t*)(keyBlock + 9 * 6)); + num_to_bytes(0x587ee5f9350f, 6, (uint8_t*)(keyBlock + 10 * 6)); + num_to_bytes(0xa0478cc39091, 6, (uint8_t*)(keyBlock + 11 * 6)); + num_to_bytes(0x533cb6c723f6, 6, (uint8_t*)(keyBlock + 12 * 6)); + num_to_bytes(0x8fd0a4f256e9, 6, (uint8_t*)(keyBlock + 13 * 6)); PrintAndLog("Testing known keys. Sector count=%d", SectorsCnt); for (i = 0; i < SectorsCnt; i++) { @@@ -1178,8 -1157,8 +1180,8 @@@ int CmdHF14AMfChk(const char *Cmd PrintAndLog("No key specified, trying default keys"); for (;keycnt < defaultKeysSize; keycnt++) PrintAndLog("chk default key[%2d] %02x%02x%02x%02x%02x%02x", keycnt, - (keyBlock + 6*keycnt)[0],(keyBlock + 6*keycnt)[1], (keyBlock + 6*keycnt)[2], - (keyBlock + 6*keycnt)[3], (keyBlock + 6*keycnt)[4], (keyBlock + 6*keycnt)[5], 6); + (keyBlock + 6*keycnt)[0],(keyBlock + 6*keycnt)[1], (keyBlock + 6*keycnt)[2], + (keyBlock + 6*keycnt)[3], (keyBlock + 6*keycnt)[4], (keyBlock + 6*keycnt)[5], 6); } // initialize storage for found keys @@@ -1224,13 -1203,13 +1226,13 @@@ for (uint16_t t = 0; t < 2; t++) { if (validKey[t][sectorNo]) { memcpy(block + t*10, foundKey[t][sectorNo], 6); - } - } + } + } mfEmlSetMem(block, FirstBlockOfSector(sectorNo) + NumBlocksPerSector(sectorNo) - 1, 1); } } PrintAndLog("Found keys have been transferred to the emulator memory"); - } + } if (createDumpFile) { FILE *fkeys = fopen("dumpkeys.bin","wb"); @@@ -1238,7 -1217,7 +1240,7 @@@ PrintAndLog("Could not create file dumpkeys.bin"); free(keyBlock); return 1; - } + } for (uint16_t t = 0; t < 2; t++) { fwrite(foundKey[t], 1, 6*SectorsCnt, fkeys); } @@@ -1248,7 -1227,7 +1250,7 @@@ free(keyBlock); - return 0; + return 0; } @@@ -1342,6 -1321,7 +1344,6 @@@ int CmdHF14AMfDbg(const char *Cmd return 0; } - int CmdHF14AMfEGet(const char *Cmd) { uint8_t blockNo = 0; @@@ -1638,6 -1618,7 +1640,6 @@@ int CmdHF14AMfCSetUID(const char *Cmd return 0; } - int CmdHF14AMfCSetBlk(const char *Cmd) { uint8_t uid[8]; @@@ -1763,7 -1744,7 +1765,7 @@@ int CmdHF14AMfCLoad(const char *Cmd } fclose(f); - if (blockNum != 16 * 4){ + if (blockNum != 16 * 4 && blockNum != 32 * 4 + 8 * 16){ PrintAndLog("File content error. There must be 64 blocks"); return 4; } @@@ -1772,6 -1753,7 +1774,6 @@@ } } - int CmdHF14AMfCGetBlk(const char *Cmd) { uint8_t memBlock[16]; uint8_t blockNo = 0; @@@ -2033,121 -2015,30 +2035,121 @@@ int CmdHF14AMfSniff(const char *Cmd) FillFileNameByUID(logHexFileName, uid + (7 - uid_len), ".log", uid_len); AddLogCurrentDT(logHexFileName); } - if (wantDecrypt) mfTraceInit(uid, atqa, sak, wantSaveToEmlFile); + if (wantDecrypt) + mfTraceInit(uid, atqa, sak, wantSaveToEmlFile); } else { PrintAndLog("%s(%d):%s", isTag ? "TAG":"RDR", num, sprint_hex(bufPtr, len)); - if (wantLogToFile) AddLogHex(logHexFileName, isTag ? "TAG: ":"RDR: ", bufPtr, len); - if (wantDecrypt) mfTraceDecode(bufPtr, len, parity, wantSaveToEmlFile); + if (wantLogToFile) + AddLogHex(logHexFileName, isTag ? "TAG: ":"RDR: ", bufPtr, len); + if (wantDecrypt) + mfTraceDecode(bufPtr, len, parity, wantSaveToEmlFile); } bufPtr += len; num++; } } - } // resp not NILL + } // resp not NULL } // while (true) return 0; } +// Tries to identify cardsize. +// Returns where num is: +// -1 unidentified +// 0 - MINI (320bytes) +// 1 - 1K +// 2 - 2K +// 4 - 4K +int GetCardSize() +{ + UsbCommand c = {CMD_READER_ISO_14443a, {ISO14A_CONNECT, 0, 0}}; + SendCommand(&c); + + UsbCommand resp; + WaitForResponse(CMD_ACK,&resp); + + if(resp.arg[0] == 0) { + PrintAndLog("iso14443a card select failed"); + return -1; + } + + iso14a_card_select_t *card = (iso14a_card_select_t *)resp.d.asBytes; + + PrintAndLog("Trying to detect card size."); + + uint16_t atqa = 0; + uint8_t sak = 0; + atqa = (card->atqa[1] & 0xff) << 8; + atqa += card->atqa[0] & 0xff; + sak = card->sak; + + // https://code.google.com/p/libnfc/source/browse/libnfc/target-subr.c + + PrintAndLog("found ATAQ: %04X SAK: %02X", atqa, sak); + + + // NXP MIFARE Mini 0.3k + if ( (atqa && 0xff0f == 0x0004) && (sak == 0x09) ) return 0; + + // MIFARE Classic 1K + if ( (atqa && 0xff0f == 0x0004) && (sak == 0x08) ) return 1; + + // MIFARE Classik 4K + if ( (atqa && 0xff0f == 0x0002) && (sak == 0x18) ) return 4; + + // SmartMX with MIFARE 1K emulation + if ( (atqa && 0xf0ff == 0x0004) ) return 1; + + // SmartMX with MIFARE 4K emulation + if ( (atqa && 0xf0ff == 0x0002) ) return 4; + + // Infineon MIFARE CLASSIC 1K + if ( (atqa && 0xffff == 0x0004) && (sak == 0x88) ) return 1; + + // MFC 4K emulated by Nokia 6212 Classic + if ( (atqa && 0xffff == 0x0002) && (sak == 0x38) ) return 4; + + // MFC 4K emulated by Nokia 6131 NFC + if ( (atqa && 0xffff == 0x0008) && (sak == 0x38) ) return 4; + + // MIFARE Plus (4 Byte UID or 4 Byte RID) + // MIFARE Plus (7 Byte UID) + if ( + (atqa && 0xffff == 0x0002) || + (atqa && 0xffff == 0x0004) || + (atqa && 0xffff == 0x0042) || + (atqa && 0xffff == 0x0044) + ) + { + switch(sak){ + case 0x08: + case 0x10: + //case 0x20: + return 2; + break; + case 0x11: + case 0x18: + //case 0x20: + return 4; + break; + } + } + + return -1; +} + + + + static command_t CommandTable[] = { {"help", CmdHelp, 1, "This help"}, {"dbg", CmdHF14AMfDbg, 0, "Set default debug mode"}, {"rdbl", CmdHF14AMfRdBl, 0, "Read MIFARE classic block"}, - {"urdbl", CmdHF14AMfURdBl, 0, "Read MIFARE Ultralight block"}, - {"urdcard", CmdHF14AMfURdCard, 0,"Read MIFARE Ultralight Card"}, - {"uwrbl", CmdHF14AMfUWrBl, 0,"Write MIFARE Ultralight block"}, + //{"urdbl", CmdHF14AMfURdBl, 0, "Read MIFARE Ultralight block"}, + //{"urdcard", CmdHF14AMfURdCard, 0,"Read MIFARE Ultralight Card"}, + //{"uwrbl", CmdHF14AMfUWrBl, 0,"Write MIFARE Ultralight block"}, {"rdsc", CmdHF14AMfRdSc, 0, "Read MIFARE classic sector"}, {"dump", CmdHF14AMfDump, 0, "Dump MIFARE classic tag to binary file"}, {"restore", CmdHF14AMfRestore, 0, "Restore MIFARE classic binary file to BLANK tag"},