mirror of
https://github.com/RfidResearchGroup/proxmark3.git
synced 2025-08-20 13:23:51 -07:00
commit
15d584e060
52 changed files with 1903 additions and 629 deletions
|
@ -3,6 +3,12 @@ All notable changes to this project will be documented in this file.
|
||||||
This project uses the changelog in accordance with [keepchangelog](http://keepachangelog.com/). Please use this to write notable changes, which is not the same as git commit log...
|
This project uses the changelog in accordance with [keepchangelog](http://keepachangelog.com/). Please use this to write notable changes, which is not the same as git commit log...
|
||||||
|
|
||||||
## [unreleased][unreleased]
|
## [unreleased][unreleased]
|
||||||
|
- Updated helptext layout in all luascripts (@iceman1001)
|
||||||
|
- Change `hf mfdes info` - output and logging (@brkeler)
|
||||||
|
- Updated texts in legic commands (@ikarus23)
|
||||||
|
- Fix timing bug inside 40x5 (@mwalker33)
|
||||||
|
- Refactored all Hitag2 attacks (@doegox)
|
||||||
|
- Added two new Hitag2 attacks (@doegox)
|
||||||
- Change `hf search` - now continue to search in case of dual tech cards (@iceman1001) Thanks to @ikarus23 for the suggestion!
|
- Change `hf search` - now continue to search in case of dual tech cards (@iceman1001) Thanks to @ikarus23 for the suggestion!
|
||||||
- Added `hf topas info` - old reader command, now also prints NDEF (@iceman1001)
|
- Added `hf topas info` - old reader command, now also prints NDEF (@iceman1001)
|
||||||
- Change `hf topaz reader` - now only prints lighter info, like UID. (@iceman1001)
|
- Change `hf topaz reader` - now only prints lighter info, like UID. (@iceman1001)
|
||||||
|
|
|
@ -205,6 +205,7 @@ CMDSRCS = crapto1/crapto1.c \
|
||||||
cmdhffido.c \
|
cmdhffido.c \
|
||||||
cmdhffelica.c \
|
cmdhffelica.c \
|
||||||
cmdhfthinfilm.c \
|
cmdhfthinfilm.c \
|
||||||
|
cmdhfcryptorf.c \
|
||||||
cmdhflto.c \
|
cmdhflto.c \
|
||||||
cmdhw.c \
|
cmdhw.c \
|
||||||
cmdlf.c \
|
cmdlf.c \
|
||||||
|
@ -251,7 +252,8 @@ CMDSRCS = crapto1/crapto1.c \
|
||||||
flash.c \
|
flash.c \
|
||||||
wiegand_formats.c \
|
wiegand_formats.c \
|
||||||
wiegand_formatutils.c \
|
wiegand_formatutils.c \
|
||||||
cardhelper.c
|
cardhelper.c \
|
||||||
|
settings.c
|
||||||
|
|
||||||
cpu_arch = $(shell uname -m)
|
cpu_arch = $(shell uname -m)
|
||||||
ifneq ($(findstring 86, $(cpu_arch)), )
|
ifneq ($(findstring 86, $(cpu_arch)), )
|
||||||
|
|
|
@ -34,6 +34,7 @@
|
||||||
#include "cmdhffido.h" // FIDO authenticators
|
#include "cmdhffido.h" // FIDO authenticators
|
||||||
#include "cmdhfthinfilm.h" // Thinfilm
|
#include "cmdhfthinfilm.h" // Thinfilm
|
||||||
#include "cmdhflto.h" // LTO-CM
|
#include "cmdhflto.h" // LTO-CM
|
||||||
|
#include "cmdhfcryptorf.h" // CryptoRF
|
||||||
#include "cmdtrace.h" // trace list
|
#include "cmdtrace.h" // trace list
|
||||||
#include "ui.h"
|
#include "ui.h"
|
||||||
#include "cmddata.h"
|
#include "cmddata.h"
|
||||||
|
@ -149,11 +150,22 @@ int CmdHFSearch(const char *Cmd) {
|
||||||
res = PM3_SUCCESS;
|
res = PM3_SUCCESS;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
/*
|
||||||
|
// 14b and iclass is the longest test (put last)
|
||||||
|
PROMPT_CLEARLINE;
|
||||||
|
PrintAndLogEx(INPLACE, "Searching for CryptoRF tag...");
|
||||||
|
if (IfPm3Iso14443b()) {
|
||||||
|
if (readHFCryptoRF(false) == PM3_SUCCESS) {
|
||||||
|
PrintAndLogEx(SUCCESS, "\nValid " _GREEN_("CryptoRF tag") "found\n");
|
||||||
|
res = PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
// 14b and iclass is the longest test (put last)
|
// 14b and iclass is the longest test (put last)
|
||||||
PROMPT_CLEARLINE;
|
PROMPT_CLEARLINE;
|
||||||
PrintAndLogEx(INPLACE, "Searching for ISO14443-B tag...");
|
PrintAndLogEx(INPLACE, "Searching for ISO14443-B tag...");
|
||||||
if (IfPm3Iso14443a()) {
|
if (IfPm3Iso14443b()) {
|
||||||
if (readHF14B(false) == 1) {
|
if (readHF14B(false) == 1) {
|
||||||
PrintAndLogEx(SUCCESS, "\nValid " _GREEN_("ISO14443-B tag") "found\n");
|
PrintAndLogEx(SUCCESS, "\nValid " _GREEN_("ISO14443-B tag") "found\n");
|
||||||
res = PM3_SUCCESS;
|
res = PM3_SUCCESS;
|
||||||
|
@ -281,6 +293,7 @@ static command_t CommandTable[] = {
|
||||||
{"14a", CmdHF14A, AlwaysAvailable, "{ ISO14443A RFIDs... }"},
|
{"14a", CmdHF14A, AlwaysAvailable, "{ ISO14443A RFIDs... }"},
|
||||||
{"14b", CmdHF14B, AlwaysAvailable, "{ ISO14443B RFIDs... }"},
|
{"14b", CmdHF14B, AlwaysAvailable, "{ ISO14443B RFIDs... }"},
|
||||||
{"15", CmdHF15, AlwaysAvailable, "{ ISO15693 RFIDs... }"},
|
{"15", CmdHF15, AlwaysAvailable, "{ ISO15693 RFIDs... }"},
|
||||||
|
// {"cryptorf", CmdHFCryptoRF, AlwaysAvailable, "{ CryptoRF RFIDs... }"},
|
||||||
{"epa", CmdHFEPA, AlwaysAvailable, "{ German Identification Card... }"},
|
{"epa", CmdHFEPA, AlwaysAvailable, "{ German Identification Card... }"},
|
||||||
{"felica", CmdHFFelica, AlwaysAvailable, "{ ISO18092 / Felica RFIDs... }"},
|
{"felica", CmdHFFelica, AlwaysAvailable, "{ ISO18092 / Felica RFIDs... }"},
|
||||||
{"fido", CmdHFFido, AlwaysAvailable, "{ FIDO and FIDO2 authenticators... }"},
|
{"fido", CmdHFFido, AlwaysAvailable, "{ FIDO and FIDO2 authenticators... }"},
|
||||||
|
|
|
@ -1245,6 +1245,135 @@ int CmdHF14A(const char *Cmd) {
|
||||||
return CmdsParse(CommandTable, Cmd);
|
return CmdsParse(CommandTable, Cmd);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void printTag(char *tag) {
|
||||||
|
PrintAndLogEx(SUCCESS, _YELLOW_(" %s"), tag);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
typedef enum {
|
||||||
|
mtNone = 0,
|
||||||
|
mtClassic = 1,
|
||||||
|
mtMini = 2,
|
||||||
|
mtDESFire = 4,
|
||||||
|
mtPlus = 8,
|
||||||
|
mtUltralight = 16,
|
||||||
|
mtOther = 32
|
||||||
|
} nxp_mifare_type;
|
||||||
|
|
||||||
|
// According to NXP AN10833 Rev 3.6 MIFARE Type Identification, Table 6
|
||||||
|
int detect_nxp_card(uint8_t sak, uint16_t atqa) {
|
||||||
|
int type = mtNone;
|
||||||
|
|
||||||
|
if (sak == 0x00) {
|
||||||
|
printTag("MIFARE Ultralight C / Ultralight CL2");
|
||||||
|
type = mtUltralight;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (sak == 0x01) {
|
||||||
|
printTag("TNP3xxx (Activision Game Appliance)");
|
||||||
|
type = mtOther;
|
||||||
|
}
|
||||||
|
if ((sak & 0x04) == 0x04) {
|
||||||
|
printTag("Any MIFARE CL1");
|
||||||
|
type |= mtDESFire;
|
||||||
|
}
|
||||||
|
if ((sak & 0x08) == 0x08) {
|
||||||
|
printTag("MIFARE Classic 1K / Classic 1K CL2");
|
||||||
|
printTag("MIFARE Plus 2K / Plus EV1 2K");
|
||||||
|
printTag("MIFARE Plus CL2 2K / Plus CL2 EV1 2K");
|
||||||
|
type |= mtClassic;
|
||||||
|
type |= mtPlus;
|
||||||
|
}
|
||||||
|
if ((sak & 0x09) == 0x09) {
|
||||||
|
printTag("MIFARE Mini 0.3K / Mini CL2 0.3K");
|
||||||
|
type |= mtMini;
|
||||||
|
}
|
||||||
|
if ((sak & 0x10) == 0x10) {
|
||||||
|
printTag("MIFARE Plus 2K / Plus CL2 2K");
|
||||||
|
type |= mtPlus;
|
||||||
|
}
|
||||||
|
if ((sak & 0x11) == 0x11) {
|
||||||
|
printTag("MIFARE Plus 4K / Plus CL2 4K");
|
||||||
|
type |= mtPlus;
|
||||||
|
}
|
||||||
|
if ((sak & 0x18) == 0x18) {
|
||||||
|
if (atqa == 0x0042) {
|
||||||
|
printTag("MIFARE Plus 4K / Plus EV1 4K");
|
||||||
|
printTag("MIFARE Plus CL2 4K / Plus CL2 EV1 4K");
|
||||||
|
type |= mtPlus;
|
||||||
|
} else {
|
||||||
|
printTag("MIFARE Classic 4K / Classic 4K CL2");
|
||||||
|
type |= mtClassic;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
if ((sak & 0x20) == 0x20) {
|
||||||
|
if (atqa == 0x0344) {
|
||||||
|
printTag("MIFARE DESFire EV1 2K/4K/8K / DESFire EV1 CL2 2K/4K/8K");
|
||||||
|
type |= mtDESFire;
|
||||||
|
} else {
|
||||||
|
printTag("MIFARE Plus 2K / Plus EV1 2K");
|
||||||
|
printTag("MIFARE Plus 4K / Plus EV1 4K");
|
||||||
|
printTag("MIFARE Plus CL2 2K / Plus CL2 EV1 4K");
|
||||||
|
printTag("MIFARE Plus CL2 4K / Plus CL2 EV1 4K");
|
||||||
|
type |= mtPlus;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if ((sak & 0x24) == 0x24) {
|
||||||
|
if (atqa == 0x0344) {
|
||||||
|
printTag("MIFARE DESFire CL1 / DESFire EV1 CL1");
|
||||||
|
type |= mtDESFire;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if ((sak & 0x28) == 0x28) {
|
||||||
|
if (atqa == 0x0344) {
|
||||||
|
printTag("MIFARE DESFire CL1 / DESFire EV1 CL1");
|
||||||
|
type |= mtDESFire;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return type;
|
||||||
|
}
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
uint8_t uid0;
|
||||||
|
uint8_t uid1;
|
||||||
|
char *desc;
|
||||||
|
} uidname;
|
||||||
|
|
||||||
|
const uidname uidmap[] = {
|
||||||
|
// UID0, UID1, TEXT
|
||||||
|
{0x02, 0x00, "SR176"},
|
||||||
|
{0x02, 0x03, "SRIX4K"},
|
||||||
|
{0x02, 0x0C, "SRT512"},
|
||||||
|
{0x02, 0x0F, "SRI2K"},
|
||||||
|
{0x02, 0x1B, "25TB512-AC"},
|
||||||
|
{0x02, 0x3D, "SRIX4K"},
|
||||||
|
{0x02, 0x3F, "25TB02K"},
|
||||||
|
{0x02, 0x4D, "SRIX512"},
|
||||||
|
{0x02, 0x6D, "SRI512"},
|
||||||
|
{0x02, 0x7D, "SRI4K"},
|
||||||
|
{0x02, 0x84, "M24SR64-Y"},
|
||||||
|
{0x02, 0xA3, "25TA02KB-P"},
|
||||||
|
{0x02, 0xC4, "25TA64K"},
|
||||||
|
{0x02, 0xE3, "25TA02KB"},
|
||||||
|
{0x02, 0xE4, "25TA512B"},
|
||||||
|
{0x02, 0xF3, "25TA02KB-D"},
|
||||||
|
{0x11, 0x22, "NTAG21x Modifiable"},
|
||||||
|
{0x00, 0x00, "None"}
|
||||||
|
};
|
||||||
|
|
||||||
|
void getTagLabel(uint8_t uid0, uint8_t uid1) {
|
||||||
|
int i = 0;
|
||||||
|
while (uidmap[i].uid0 != 0x00) {
|
||||||
|
if ((uidmap[i].uid0 == uid0) && (uidmap[i].uid1 == uid1)) {
|
||||||
|
PrintAndLogEx(SUCCESS, _YELLOW_(" %s"), uidmap[i].desc);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
i += 1;
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
int infoHF14A(bool verbose, bool do_nack_test, bool do_aid_search) {
|
int infoHF14A(bool verbose, bool do_nack_test, bool do_aid_search) {
|
||||||
clearCommandBuffer();
|
clearCommandBuffer();
|
||||||
SendCommandMIX(CMD_HF_ISO14443A_READER, ISO14A_CONNECT | ISO14A_NO_DISCONNECT, 0, 0, NULL, 0);
|
SendCommandMIX(CMD_HF_ISO14443A_READER, ISO14A_CONNECT | ISO14A_NO_DISCONNECT, 0, 0, NULL, 0);
|
||||||
|
@ -1290,97 +1419,114 @@ int infoHF14A(bool verbose, bool do_nack_test, bool do_aid_search) {
|
||||||
PrintAndLogEx(SUCCESS, " SAK: " _GREEN_("%02x [%" PRIu64 "]"), card.sak, resp.oldarg[0]);
|
PrintAndLogEx(SUCCESS, " SAK: " _GREEN_("%02x [%" PRIu64 "]"), card.sak, resp.oldarg[0]);
|
||||||
|
|
||||||
bool isMifareClassic = true;
|
bool isMifareClassic = true;
|
||||||
bool isMifareDesfire = false;
|
bool isMifareDESFire = false;
|
||||||
bool isMifarePlus = false;
|
bool isMifarePlus = false;
|
||||||
bool isMifareUltralight = false;
|
bool isMifareUltralight = false;
|
||||||
|
int nxptype = mtNone;
|
||||||
switch (card.sak) {
|
|
||||||
case 0x00:
|
|
||||||
isMifareClassic = false;
|
|
||||||
|
|
||||||
// ******** is card of the MFU type (UL/ULC/NTAG/ etc etc)
|
|
||||||
DropField();
|
|
||||||
|
|
||||||
uint32_t tagT = GetHF14AMfU_Type();
|
|
||||||
if (tagT != UL_ERROR) {
|
|
||||||
ul_print_type(tagT, 0);
|
|
||||||
isMifareUltralight = true;
|
|
||||||
} else {
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: Possible AZTEK (iso14443a compliant)");
|
|
||||||
}
|
|
||||||
|
|
||||||
// reconnect for further tests
|
|
||||||
clearCommandBuffer();
|
|
||||||
SendCommandMIX(CMD_HF_ISO14443A_READER, ISO14A_CONNECT | ISO14A_NO_DISCONNECT, 0, 0, NULL, 0);
|
|
||||||
WaitForResponse(CMD_ACK, &resp);
|
|
||||||
|
|
||||||
memcpy(&card, (iso14a_card_select_t *)resp.data.asBytes, sizeof(iso14a_card_select_t));
|
|
||||||
|
|
||||||
select_status = resp.oldarg[0]; // 0: couldn't read, 1: OK, with ATS, 2: OK, no ATS
|
|
||||||
|
|
||||||
if (select_status == 0) {
|
|
||||||
DropField();
|
|
||||||
return select_status;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 0x01:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("NXP TNP3xxx Activision Game Appliance"));
|
|
||||||
break;
|
|
||||||
case 0x04:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("NXP MIFARE (various !DESFire !DESFire EV1)"));
|
|
||||||
isMifareClassic = false;
|
|
||||||
isMifareDesfire = true;
|
|
||||||
break;
|
|
||||||
case 0x08:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("NXP MIFARE CLASSIC 1k | Plus 2k SL1 | 1k Ev1"));
|
|
||||||
break;
|
|
||||||
case 0x09:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("NXP MIFARE Mini 0.3k"));
|
|
||||||
break;
|
|
||||||
case 0x0A:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("FM11RF005SH (Shanghai Metro)"));
|
|
||||||
break;
|
|
||||||
case 0x10:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("NXP MIFARE Plus 2k SL2"));
|
|
||||||
isMifarePlus = true;
|
|
||||||
break;
|
|
||||||
case 0x11:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("NXP MIFARE Plus 4k SL2"));
|
|
||||||
isMifarePlus = true;
|
|
||||||
break;
|
|
||||||
case 0x18:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("NXP MIFARE Classic 4k | Plus 4k SL1 | 4k Ev1"));
|
|
||||||
break;
|
|
||||||
case 0x20:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("NXP MIFARE DESFire 4k | DESFire EV1 2k/4k/8k | Plus 2k/4k SL3 | JCOP 31/41"));
|
|
||||||
isMifareClassic = false;
|
|
||||||
isMifareDesfire = true;
|
|
||||||
isMifarePlus = true;
|
|
||||||
break;
|
|
||||||
case 0x24:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("NXP MIFARE DESFire | DESFire EV1"));
|
|
||||||
isMifareClassic = false;
|
|
||||||
isMifareDesfire = true;
|
|
||||||
break;
|
|
||||||
case 0x28:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("JCOP31 or JCOP41 v2.3.1"));
|
|
||||||
break;
|
|
||||||
case 0x38:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("Nokia 6212 or 6131 MIFARE CLASSIC 4K"));
|
|
||||||
break;
|
|
||||||
case 0x88:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("Infineon MIFARE CLASSIC 1K"));
|
|
||||||
break;
|
|
||||||
case 0x98:
|
|
||||||
PrintAndLogEx(SUCCESS, "TYPE: " _YELLOW_("Gemplus MPCOS"));
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Double & triple sized UID, can be mapped to a manufacturer.
|
// Double & triple sized UID, can be mapped to a manufacturer.
|
||||||
|
if (card.uidlen <= 4) {
|
||||||
|
nxptype = detect_nxp_card(card.sak, ((card.atqa[1] << 8) + card.atqa[0]));
|
||||||
|
if ((nxptype & mtClassic) == mtClassic) isMifareClassic = true;
|
||||||
|
else isMifareClassic = false;
|
||||||
|
if ((nxptype & mtDESFire) == mtDESFire) {
|
||||||
|
isMifareDESFire = true;
|
||||||
|
} else {
|
||||||
|
isMifareDESFire = false;
|
||||||
|
}
|
||||||
|
if ((nxptype & mtPlus) == mtPlus) isMifarePlus = true;
|
||||||
|
else isMifarePlus = false;
|
||||||
|
if ((nxptype & mtUltralight) == mtUltralight) isMifareUltralight = true;
|
||||||
|
else isMifareUltralight = false;
|
||||||
|
if ((nxptype & mtOther) == mtOther) isMifareClassic = true;
|
||||||
|
}
|
||||||
if (card.uidlen > 4) {
|
if (card.uidlen > 4) {
|
||||||
PrintAndLogEx(SUCCESS, "MANUFACTURER: " _YELLOW_("%s"), getTagInfo(card.uid[0]));
|
PrintAndLogEx(SUCCESS, "MANUFACTURER: " _YELLOW_("%s"), getTagInfo(card.uid[0]));
|
||||||
|
|
||||||
|
PrintAndLogEx(SUCCESS, "Possible Type:");
|
||||||
|
switch (card.uid[0]) {
|
||||||
|
case 0x04: // NXP
|
||||||
|
nxptype = detect_nxp_card(card.sak, ((card.atqa[1] << 8) + card.atqa[0]));
|
||||||
|
if ((nxptype & mtClassic) == mtClassic) isMifareClassic = true;
|
||||||
|
else isMifareClassic = false;
|
||||||
|
if ((nxptype & mtDESFire) == mtDESFire) {
|
||||||
|
isMifareDESFire = true;
|
||||||
|
} else {
|
||||||
|
isMifareDESFire = false;
|
||||||
|
}
|
||||||
|
if ((nxptype & mtPlus) == mtPlus) isMifarePlus = true;
|
||||||
|
else isMifarePlus = false;
|
||||||
|
if ((nxptype & mtUltralight) == mtUltralight) isMifareUltralight = true;
|
||||||
|
else isMifareUltralight = false;
|
||||||
|
if ((nxptype & mtOther) == mtOther) isMifareClassic = true;
|
||||||
|
break;
|
||||||
|
case 0x05: // Infineon
|
||||||
|
if ((card.uid[1] & 0xF0) == 0x10) {
|
||||||
|
printTag("my-d(tm) command set SLE 66R04/16/32P, SLE 66R04/16/32S");
|
||||||
|
} else if ((card.uid[1] & 0xF0) == 0x20) {
|
||||||
|
printTag("my-d(tm) command set SLE 66R01/16/32P (Type 2 Tag)");
|
||||||
|
} else if ((card.uid[1] & 0xF0) == 0x30) {
|
||||||
|
printTag("my-d(tm) move lean SLE 66R01P/66R01PN");
|
||||||
|
} else if ((card.uid[1] & 0xF0) == 0x70) {
|
||||||
|
printTag("my-d(tm) move lean SLE 66R01L");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (card.sak == 0x88) {
|
||||||
|
printTag("Infineon MIFARE CLASSIC 1K");
|
||||||
|
}
|
||||||
|
getTagLabel(card.uid[0], card.uid[1]);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
getTagLabel(card.uid[0], card.uid[1]);
|
||||||
|
switch (card.sak) {
|
||||||
|
case 0x00:
|
||||||
|
isMifareClassic = false;
|
||||||
|
|
||||||
|
// ******** is card of the MFU type (UL/ULC/NTAG/ etc etc)
|
||||||
|
DropField();
|
||||||
|
|
||||||
|
uint32_t tagT = GetHF14AMfU_Type();
|
||||||
|
if (tagT != UL_ERROR) {
|
||||||
|
ul_print_type(tagT, 0);
|
||||||
|
isMifareUltralight = true;
|
||||||
|
printTag("MIFARE Ultralight/C/NTAG Compatible");
|
||||||
|
} else {
|
||||||
|
printTag("Possible AZTEK (iso14443a compliant)");
|
||||||
|
}
|
||||||
|
|
||||||
|
// reconnect for further tests
|
||||||
|
clearCommandBuffer();
|
||||||
|
SendCommandMIX(CMD_HF_ISO14443A_READER, ISO14A_CONNECT | ISO14A_NO_DISCONNECT, 0, 0, NULL, 0);
|
||||||
|
WaitForResponse(CMD_ACK, &resp);
|
||||||
|
|
||||||
|
memcpy(&card, (iso14a_card_select_t *)resp.data.asBytes, sizeof(iso14a_card_select_t));
|
||||||
|
|
||||||
|
select_status = resp.oldarg[0]; // 0: couldn't read, 1: OK, with ATS, 2: OK, no ATS
|
||||||
|
|
||||||
|
if (select_status == 0) {
|
||||||
|
DropField();
|
||||||
|
return select_status;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case 0x0A:
|
||||||
|
printTag("FM11RF005SH (Shanghai Metro)");
|
||||||
|
break;
|
||||||
|
case 0x20:
|
||||||
|
printTag("JCOP 31/41");
|
||||||
|
break;
|
||||||
|
case 0x28:
|
||||||
|
printTag("JCOP31 or JCOP41 v2.3.1");
|
||||||
|
break;
|
||||||
|
case 0x38:
|
||||||
|
printTag("Nokia 6212 or 6131");
|
||||||
|
break;
|
||||||
|
case 0x98:
|
||||||
|
printTag("Gemplus MPCOS");
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// try to request ATS even if tag claims not to support it
|
// try to request ATS even if tag claims not to support it
|
||||||
|
@ -1455,12 +1601,14 @@ int infoHF14A(bool verbose, bool do_nack_test, bool do_aid_search) {
|
||||||
);
|
);
|
||||||
pos++;
|
pos++;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (tc1) {
|
if (tc1) {
|
||||||
PrintAndLogEx(SUCCESS, " - TC1 : NAD is%s supported, CID is%s supported",
|
PrintAndLogEx(SUCCESS, " - TC1 : NAD is%s supported, CID is%s supported",
|
||||||
(card.ats[pos] & 0x01) ? "" : " NOT",
|
(card.ats[pos] & 0x01) ? "" : " NOT",
|
||||||
(card.ats[pos] & 0x02) ? "" : " NOT");
|
(card.ats[pos] & 0x02) ? "" : " NOT");
|
||||||
pos++;
|
pos++;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (card.ats[0] > pos && card.ats[0] < card.ats_len - 2) {
|
if (card.ats[0] > pos && card.ats[0] < card.ats_len - 2) {
|
||||||
const char *tip = "";
|
const char *tip = "";
|
||||||
if (card.ats[0] - pos >= 7) {
|
if (card.ats[0] - pos >= 7) {
|
||||||
|
@ -1477,14 +1625,14 @@ int infoHF14A(bool verbose, bool do_nack_test, bool do_aid_search) {
|
||||||
switch (card.ats[pos + 2] & 0xf0) {
|
switch (card.ats[pos + 2] & 0xf0) {
|
||||||
case 0x10:
|
case 0x10:
|
||||||
PrintAndLogEx(SUCCESS, " 1x -> MIFARE DESFire");
|
PrintAndLogEx(SUCCESS, " 1x -> MIFARE DESFire");
|
||||||
isMifareDesfire = true;
|
isMifareDESFire = true;
|
||||||
isMifareClassic = false;
|
isMifareClassic = false;
|
||||||
isMifarePlus = false;
|
isMifarePlus = false;
|
||||||
break;
|
break;
|
||||||
case 0x20:
|
case 0x20:
|
||||||
PrintAndLogEx(SUCCESS, " 2x -> MIFARE Plus");
|
PrintAndLogEx(SUCCESS, " 2x -> MIFARE Plus");
|
||||||
isMifarePlus = true;
|
isMifarePlus = true;
|
||||||
isMifareDesfire = false;
|
isMifareDESFire = false;
|
||||||
isMifareClassic = false;
|
isMifareClassic = false;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -1607,37 +1755,39 @@ int infoHF14A(bool verbose, bool do_nack_test, bool do_aid_search) {
|
||||||
PrintAndLogEx(INFO, "proprietary non iso14443-4 card found, RATS not supported");
|
PrintAndLogEx(INFO, "proprietary non iso14443-4 card found, RATS not supported");
|
||||||
}
|
}
|
||||||
|
|
||||||
detect_classic_magic();
|
|
||||||
|
|
||||||
if (isMifareClassic) {
|
|
||||||
int res = detect_classic_prng();
|
|
||||||
if (res == 1)
|
|
||||||
PrintAndLogEx(SUCCESS, "Prng detection: " _GREEN_("weak"));
|
|
||||||
else if (res == 0)
|
|
||||||
PrintAndLogEx(SUCCESS, "Prng detection: " _YELLOW_("hard"));
|
|
||||||
else
|
|
||||||
PrintAndLogEx(FAILED, "prng detection: " _RED_("fail"));
|
|
||||||
|
|
||||||
if (do_nack_test)
|
|
||||||
detect_classic_nackbug(false);
|
|
||||||
|
|
||||||
res = detect_classic_static_nonce();
|
|
||||||
if (res == 1)
|
|
||||||
PrintAndLogEx(SUCCESS, "Static nonce: " _YELLOW_("yes") );
|
|
||||||
if (res == 2 && verbose)
|
|
||||||
PrintAndLogEx(SUCCESS, "Static nonce: " _RED_("fail"));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (isMifareUltralight) {
|
if (isMifareUltralight) {
|
||||||
PrintAndLogEx(HINT, "Hint: try " _YELLOW_("`hf mfu info`"));
|
PrintAndLogEx(HINT, "Hint: try " _YELLOW_("`hf mfu info`"));
|
||||||
}
|
}
|
||||||
if (isMifarePlus) {
|
if (isMifarePlus) {
|
||||||
PrintAndLogEx(HINT, "Hint: try " _YELLOW_("`hf mfp info`"));
|
PrintAndLogEx(HINT, "Hint: try " _YELLOW_("`hf mfp info`"));
|
||||||
}
|
}
|
||||||
if (isMifareDesfire) {
|
if (isMifareDESFire) {
|
||||||
PrintAndLogEx(HINT, "Hint: try " _YELLOW_("`hf mfdes info`"));
|
PrintAndLogEx(HINT, "Hint: try " _YELLOW_("`hf mfdes info`"));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (((card.sak & 0x08) == 0x08) || ((card.sak & 0x18) == 0x18)) {
|
||||||
|
detect_classic_magic();
|
||||||
|
|
||||||
|
if (isMifareClassic) {
|
||||||
|
int res = detect_classic_prng();
|
||||||
|
if (res == 1)
|
||||||
|
PrintAndLogEx(SUCCESS, "Prng detection: " _GREEN_("weak"));
|
||||||
|
else if (res == 0)
|
||||||
|
PrintAndLogEx(SUCCESS, "Prng detection: " _YELLOW_("hard"));
|
||||||
|
else
|
||||||
|
PrintAndLogEx(FAILED, "prng detection: " _RED_("fail"));
|
||||||
|
|
||||||
|
if (do_nack_test)
|
||||||
|
detect_classic_nackbug(false);
|
||||||
|
|
||||||
|
res = detect_classic_static_nonce();
|
||||||
|
if (res == 1)
|
||||||
|
PrintAndLogEx(SUCCESS, "Static nonce: " _YELLOW_("yes"));
|
||||||
|
if (res == 2 && verbose)
|
||||||
|
PrintAndLogEx(SUCCESS, "Static nonce: " _RED_("fail"));
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return select_status;
|
return select_status;
|
||||||
}
|
}
|
||||||
|
|
609
client/cmdhfcryptorf.c
Normal file
609
client/cmdhfcryptorf.c
Normal file
|
@ -0,0 +1,609 @@
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
// Copyright (C) 2020 iceman
|
||||||
|
//
|
||||||
|
// 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.
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
// High frequency CryptoRF commands (ISO14443B)
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
#include "cmdhfcryptorf.h"
|
||||||
|
|
||||||
|
#include <ctype.h>
|
||||||
|
#include "fileutils.h"
|
||||||
|
|
||||||
|
#include "cmdparser.h" // command_t
|
||||||
|
#include "comms.h" // clearCommandBuffer
|
||||||
|
#include "cmdtrace.h"
|
||||||
|
#include "crc16.h"
|
||||||
|
#include "cmdhf14a.h"
|
||||||
|
#include "protocols.h" // definitions of ISO14B protocol
|
||||||
|
|
||||||
|
#define TIMEOUT 2000
|
||||||
|
static int CmdHelp(const char *Cmd);
|
||||||
|
|
||||||
|
static int usage_hf_cryptorf_info(void) {
|
||||||
|
PrintAndLogEx(NORMAL, "Usage: hf cryptorf info [h] [v]\n"
|
||||||
|
"Options:\n"
|
||||||
|
" h this help\n"
|
||||||
|
" v verbose\n"
|
||||||
|
"\n"
|
||||||
|
"Example:\n"
|
||||||
|
_YELLOW_(" hf cryptorf info")
|
||||||
|
);
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
static int usage_hf_cryptorf_reader(void) {
|
||||||
|
PrintAndLogEx(NORMAL, "Usage: hf cryptorf reader [h] [v]\n"
|
||||||
|
"Options:\n"
|
||||||
|
" h this help\n"
|
||||||
|
" v verbose\n"
|
||||||
|
"\n"
|
||||||
|
"Example:\n"
|
||||||
|
_YELLOW_(" hf cryptorf reader")
|
||||||
|
);
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
static int usage_hf_cryptorf_sniff(void) {
|
||||||
|
PrintAndLogEx(NORMAL, "It get data from the field and saves it into command buffer\n"
|
||||||
|
"Buffer accessible from command " _YELLOW_("'hf list cryptorf'") "\n"
|
||||||
|
"Usage: hf cryptorf sniff [h]\n"
|
||||||
|
"Options:\n"
|
||||||
|
" h this help\n"
|
||||||
|
"\n"
|
||||||
|
"Example:\n"
|
||||||
|
_YELLOW_(" hf cryptorf sniff")
|
||||||
|
);
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
static int usage_hf_cryptorf_sim(void) {
|
||||||
|
PrintAndLogEx(NORMAL, "Emulating CryptoRF tag with 4 UID / PUPI\n"
|
||||||
|
"Usage: hf cryptorf sim [h] [u <uid>]\n"
|
||||||
|
"Options:\n"
|
||||||
|
" h this help\n"
|
||||||
|
" u 4byte UID/PUPI\n"
|
||||||
|
"\n"
|
||||||
|
"Example:\n"
|
||||||
|
_YELLOW_(" hf cryptorf sim")
|
||||||
|
);
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
static int usage_hf_cryptorf_dump(void) {
|
||||||
|
PrintAndLogEx(NORMAL, "This command dumps the contents of a ISO-14443-B tag and save it to file\n"
|
||||||
|
"\n"
|
||||||
|
"Usage: hf cryptorf dump [h] [card memory] <f filname> \n"
|
||||||
|
"Options:\n"
|
||||||
|
" h this help\n"
|
||||||
|
" f <name> filename, if no <name> UID will be used as filename\n"
|
||||||
|
"\n"
|
||||||
|
"Examples:\n"
|
||||||
|
"\thf cryptorf dump\n"
|
||||||
|
"\thf cryptorf dump f mydump");
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
static int usage_hf_cryptorf_eload(void) {
|
||||||
|
PrintAndLogEx(NORMAL, "It loads a binary dump into emulator memory\n"
|
||||||
|
"Usage: hf cryptorf eload [f <file name w/o `.eml`>]\n"
|
||||||
|
"Options:\n"
|
||||||
|
" h this help\n"
|
||||||
|
" f <name> filename, if no <name> UID will be used as filename\n"
|
||||||
|
"\n"
|
||||||
|
"Examples:\n"
|
||||||
|
_YELLOW_(" hf cryptorf eload f filename")
|
||||||
|
);
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
static int usage_hf_cryptorf_esave(void) {
|
||||||
|
PrintAndLogEx(NORMAL, "It saves bin/eml/json dump file of emulator memory\n"
|
||||||
|
" Usage: hf cryptorf esave [f <file name w/o `.eml`>]\n"
|
||||||
|
"Options:\n"
|
||||||
|
" h this help\n"
|
||||||
|
" f <name> filename, if no <name> UID will be used as filename\n"
|
||||||
|
"\n"
|
||||||
|
"Examples:\n"
|
||||||
|
_YELLOW_(" hf cryptorf esave ")
|
||||||
|
_YELLOW_(" hf cryptorf esave f filename")
|
||||||
|
);
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int switch_off_field_cryptorf(void) {
|
||||||
|
clearCommandBuffer();
|
||||||
|
SendCommandMIX(CMD_HF_ISO14443B_COMMAND, ISO14B_DISCONNECT, 0, 0, NULL, 0);
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int CmdHFCryptoRFList(const char *Cmd) {
|
||||||
|
(void)Cmd; // Cmd is not used so far
|
||||||
|
CmdTraceList("14b");
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int CmdHFCryptoRFSim(const char *Cmd) {
|
||||||
|
char cmdp = tolower(param_getchar(Cmd, 0));
|
||||||
|
if (cmdp == 'h') return usage_hf_cryptorf_sim();
|
||||||
|
|
||||||
|
uint32_t pupi = 0;
|
||||||
|
if (cmdp == 'u') {
|
||||||
|
pupi = param_get32ex(Cmd, 1, 0, 16);
|
||||||
|
}
|
||||||
|
|
||||||
|
clearCommandBuffer();
|
||||||
|
SendCommandMIX(CMD_HF_ISO14443B_SIMULATE, pupi, 0, 0, NULL, 0);
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int CmdHFCryptoRFSniff(const char *Cmd) {
|
||||||
|
|
||||||
|
char cmdp = tolower(param_getchar(Cmd, 0));
|
||||||
|
if (cmdp == 'h') return usage_hf_cryptorf_sniff();
|
||||||
|
|
||||||
|
clearCommandBuffer();
|
||||||
|
SendCommandNG(CMD_HF_ISO14443B_SNIFF, NULL, 0);
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool get_14b_UID(iso14b_card_select_t *card) {
|
||||||
|
|
||||||
|
if (!card)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
int8_t retry = 3;
|
||||||
|
PacketResponseNG resp;
|
||||||
|
|
||||||
|
// test for 14b SR
|
||||||
|
while (retry--) {
|
||||||
|
|
||||||
|
clearCommandBuffer();
|
||||||
|
SendCommandMIX(CMD_HF_ISO14443B_COMMAND, ISO14B_CONNECT | ISO14B_SELECT_SR | ISO14B_DISCONNECT, 0, 0, NULL, 0);
|
||||||
|
if (WaitForResponseTimeout(CMD_ACK, &resp, TIMEOUT)) {
|
||||||
|
|
||||||
|
uint8_t status = resp.oldarg[0];
|
||||||
|
if (status == 0) {
|
||||||
|
memcpy(card, (iso14b_card_select_t *)resp.data.asBytes, sizeof(iso14b_card_select_t));
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} // retry
|
||||||
|
|
||||||
|
// test 14b standard
|
||||||
|
retry = 3;
|
||||||
|
while (retry--) {
|
||||||
|
|
||||||
|
clearCommandBuffer();
|
||||||
|
SendCommandMIX(CMD_HF_ISO14443B_COMMAND, ISO14B_CONNECT | ISO14B_SELECT_STD | ISO14B_DISCONNECT, 0, 0, NULL, 0);
|
||||||
|
if (WaitForResponseTimeout(CMD_ACK, &resp, TIMEOUT)) {
|
||||||
|
|
||||||
|
uint8_t status = resp.oldarg[0];
|
||||||
|
if (status == 0) {
|
||||||
|
memcpy(card, (iso14b_card_select_t *)resp.data.asBytes, sizeof(iso14b_card_select_t));
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} // retry
|
||||||
|
|
||||||
|
if (retry <= 0)
|
||||||
|
PrintAndLogEx(WARNING, "timeout while waiting for reply.");
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int CmdHFCryptoRFInfo(const char *Cmd) {
|
||||||
|
char cmdp = tolower(param_getchar(Cmd, 0));
|
||||||
|
if (cmdp == 'h') return usage_hf_cryptorf_info();
|
||||||
|
|
||||||
|
bool verbose = (cmdp == 'v');
|
||||||
|
|
||||||
|
int res = infoHFCryptoRF(verbose);
|
||||||
|
if (res != PM3_SUCCESS && verbose) {
|
||||||
|
PrintAndLogEx(FAILED, "no 14443-B tag found");
|
||||||
|
}
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int CmdHFCryptoRFReader(const char *Cmd) {
|
||||||
|
char cmdp = tolower(param_getchar(Cmd, 0));
|
||||||
|
if (cmdp == 'h') return usage_hf_cryptorf_reader();
|
||||||
|
|
||||||
|
bool verbose = (cmdp == 'v');
|
||||||
|
|
||||||
|
int res = readHFCryptoRF(verbose);
|
||||||
|
if (res != PM3_SUCCESS && verbose) {
|
||||||
|
PrintAndLogEx(FAILED, "no 14443-B tag found");
|
||||||
|
}
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
// need to write to file
|
||||||
|
static int CmdHFCryptoRFDump(const char *Cmd) {
|
||||||
|
|
||||||
|
uint8_t fileNameLen = 0;
|
||||||
|
char filename[FILE_PATH_SIZE] = {0};
|
||||||
|
char *fptr = filename;
|
||||||
|
bool errors = false;
|
||||||
|
uint8_t cmdp = 0, cardtype = 1;
|
||||||
|
uint16_t cardsize = 0;
|
||||||
|
uint8_t blocks = 0;
|
||||||
|
iso14b_card_select_t card;
|
||||||
|
|
||||||
|
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
|
||||||
|
switch (tolower(param_getchar(Cmd, cmdp))) {
|
||||||
|
case 'h':
|
||||||
|
return usage_hf_cryptorf_dump();
|
||||||
|
case 'f':
|
||||||
|
fileNameLen = param_getstr(Cmd, cmdp + 1, filename, FILE_PATH_SIZE);
|
||||||
|
cmdp += 2;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
if (cmdp == 0) {
|
||||||
|
cardtype = param_get8ex(Cmd, cmdp, 1, 10);
|
||||||
|
cmdp++;
|
||||||
|
} else {
|
||||||
|
PrintAndLogEx(WARNING, "Unknown parameter '%c'\n", param_getchar(Cmd, cmdp));
|
||||||
|
errors = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//Validations
|
||||||
|
if (errors) return usage_hf_cryptorf_dump();
|
||||||
|
|
||||||
|
switch (cardtype) {
|
||||||
|
case 2:
|
||||||
|
cardsize = (512 / 8) + 4;
|
||||||
|
blocks = 0x0F;
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
default:
|
||||||
|
cardsize = (4096 / 8) + 4;
|
||||||
|
blocks = 0x7F;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!get_14b_UID(&card)) {
|
||||||
|
PrintAndLogEx(WARNING, "No tag found.");
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (fileNameLen < 1) {
|
||||||
|
PrintAndLogEx(INFO, "Using UID as filename");
|
||||||
|
fptr += sprintf(fptr, "hf-cryptorf-");
|
||||||
|
FillFileNameByUID(fptr, card.uid, "-dump", card.uidlen);
|
||||||
|
}
|
||||||
|
|
||||||
|
// detect blocksize from card :)
|
||||||
|
PrintAndLogEx(NORMAL, "Reading memory from tag UID %s", sprint_hex(card.uid, card.uidlen));
|
||||||
|
|
||||||
|
uint8_t data[cardsize];
|
||||||
|
memset(data, 0, sizeof(data));
|
||||||
|
|
||||||
|
int blocknum = 0;
|
||||||
|
uint8_t *recv = NULL;
|
||||||
|
|
||||||
|
PacketResponseNG resp;
|
||||||
|
clearCommandBuffer();
|
||||||
|
SendCommandMIX(CMD_HF_ISO14443B_COMMAND, ISO14B_CONNECT | ISO14B_SELECT_SR, 0, 0, NULL, 0);
|
||||||
|
|
||||||
|
//select
|
||||||
|
if (WaitForResponseTimeout(CMD_ACK, &resp, 2000)) {
|
||||||
|
if (resp.oldarg[0]) {
|
||||||
|
PrintAndLogEx(INFO, "failed to select %" PRId64 " | %" PRId64, resp.oldarg[0], resp.oldarg[1]);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
uint8_t req[2] = {ISO14443B_READ_BLK};
|
||||||
|
|
||||||
|
for (int retry = 0; retry < 5; retry++) {
|
||||||
|
|
||||||
|
req[1] = blocknum;
|
||||||
|
|
||||||
|
clearCommandBuffer();
|
||||||
|
SendCommandOLD(CMD_HF_ISO14443B_COMMAND, ISO14B_APPEND_CRC | ISO14B_RAW, 2, 0, req, sizeof(req));
|
||||||
|
|
||||||
|
if (WaitForResponseTimeout(CMD_ACK, &resp, 2000)) {
|
||||||
|
|
||||||
|
uint8_t status = resp.oldarg[0] & 0xFF;
|
||||||
|
if (status > 0) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint16_t len = (resp.oldarg[1] & 0xFFFF);
|
||||||
|
recv = resp.data.asBytes;
|
||||||
|
|
||||||
|
if (!check_crc(CRC_14443_B, recv, len)) {
|
||||||
|
PrintAndLogEx(FAILED, "crc fail, retrying one more time");
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
memcpy(data + (blocknum * 4), resp.data.asBytes, 4);
|
||||||
|
|
||||||
|
if (blocknum == 0xFF) {
|
||||||
|
//last read.
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
retry = 0;
|
||||||
|
blocknum++;
|
||||||
|
if (blocknum > blocks) {
|
||||||
|
// read config block
|
||||||
|
blocknum = 0xFF;
|
||||||
|
}
|
||||||
|
|
||||||
|
printf(".");
|
||||||
|
fflush(stdout);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (blocknum != 0xFF) {
|
||||||
|
PrintAndLogEx(NORMAL, "\n Dump failed");
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
PrintAndLogEx(NORMAL, "\n");
|
||||||
|
PrintAndLogEx(NORMAL, "block# | data | ascii");
|
||||||
|
PrintAndLogEx(NORMAL, "---------+--------------+----------");
|
||||||
|
|
||||||
|
for (int i = 0; i <= blocks; i++) {
|
||||||
|
PrintAndLogEx(NORMAL,
|
||||||
|
"%3d/0x%02X | %s | %s",
|
||||||
|
i,
|
||||||
|
i,
|
||||||
|
sprint_hex(data + (i * 4), 4),
|
||||||
|
sprint_ascii(data + (i * 4), 4)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
PrintAndLogEx(NORMAL, "\n");
|
||||||
|
|
||||||
|
|
||||||
|
size_t datalen = (blocks + 1) * 4;
|
||||||
|
saveFileEML(filename, data, datalen, 4);
|
||||||
|
saveFile(filename, ".bin", data, datalen);
|
||||||
|
out:
|
||||||
|
return switch_off_field_cryptorf();
|
||||||
|
}
|
||||||
|
|
||||||
|
static int CmdHFCryptoRFELoad(const char *Cmd) {
|
||||||
|
|
||||||
|
size_t datalen = 1024;
|
||||||
|
char filename[FILE_PATH_SIZE] = {0x00};
|
||||||
|
bool errors = false, has_filename = false;
|
||||||
|
uint8_t cmdp = 0;
|
||||||
|
|
||||||
|
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
|
||||||
|
switch (tolower(param_getchar(Cmd, cmdp))) {
|
||||||
|
case 'h' :
|
||||||
|
return usage_hf_cryptorf_eload();
|
||||||
|
case 'f' :
|
||||||
|
if (param_getstr(Cmd, cmdp + 1, filename, FILE_PATH_SIZE) >= FILE_PATH_SIZE) {
|
||||||
|
PrintAndLogEx(FAILED, "Filename too long");
|
||||||
|
errors = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
has_filename = true;
|
||||||
|
cmdp += 2;
|
||||||
|
break;
|
||||||
|
default :
|
||||||
|
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
|
||||||
|
errors = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (has_filename == false)
|
||||||
|
errors = true;
|
||||||
|
|
||||||
|
//Validations
|
||||||
|
if (errors || strlen(Cmd) == 0) return usage_hf_cryptorf_eload();
|
||||||
|
|
||||||
|
// set up buffer
|
||||||
|
uint8_t *data = calloc(datalen, sizeof(uint8_t));
|
||||||
|
if (!data) {
|
||||||
|
PrintAndLogEx(WARNING, "Fail, cannot allocate memory");
|
||||||
|
return PM3_EMALLOC;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (loadFile_safe(filename, ".bin", (void **)&data, &datalen) != PM3_SUCCESS) {
|
||||||
|
free(data);
|
||||||
|
PrintAndLogEx(WARNING, "Error, reading file");
|
||||||
|
return PM3_EFILE;
|
||||||
|
}
|
||||||
|
|
||||||
|
PrintAndLogEx(SUCCESS, "Uploading to emulator memory");
|
||||||
|
|
||||||
|
/*
|
||||||
|
// fast push mode
|
||||||
|
conn.block_after_ACK = true;
|
||||||
|
|
||||||
|
//Send to device
|
||||||
|
uint32_t bytes_sent = 0;
|
||||||
|
uint32_t bytes_remaining = bytes_read;
|
||||||
|
|
||||||
|
while (bytes_remaining > 0) {
|
||||||
|
uint32_t bytes_in_packet = MIN(PM3_CMD_DATA_SIZE, bytes_remaining);
|
||||||
|
if (bytes_in_packet == bytes_remaining) {
|
||||||
|
// Disable fast mode on last packet
|
||||||
|
conn.block_after_ACK = false;
|
||||||
|
}
|
||||||
|
clearCommandBuffer();
|
||||||
|
SendCommandOLD(CMD_HF_CRYPTORF_EML_MEMSET, bytes_sent, bytes_in_packet, 0, data + bytes_sent, bytes_in_packet);
|
||||||
|
bytes_remaining -= bytes_in_packet;
|
||||||
|
bytes_sent += bytes_in_packet;
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
free(data);
|
||||||
|
PrintAndLogEx(NORMAL, "");
|
||||||
|
PrintAndLogEx(SUCCESS, "Done");
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int CmdHFCryptoRFESave(const char *Cmd) {
|
||||||
|
|
||||||
|
char filename[FILE_PATH_SIZE] = {0};
|
||||||
|
char *fptr = filename;
|
||||||
|
int fileNameLen = 0;
|
||||||
|
size_t numofbytes = 1024;
|
||||||
|
bool errors = false;
|
||||||
|
uint8_t cmdp = 0;
|
||||||
|
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
|
||||||
|
switch (tolower(param_getchar(Cmd, cmdp))) {
|
||||||
|
case 'h' :
|
||||||
|
return usage_hf_cryptorf_esave();
|
||||||
|
case 'f' :
|
||||||
|
fileNameLen = param_getstr(Cmd, cmdp + 1, filename, FILE_PATH_SIZE);
|
||||||
|
if (!fileNameLen)
|
||||||
|
errors = true;
|
||||||
|
if (fileNameLen > FILE_PATH_SIZE - 5)
|
||||||
|
fileNameLen = FILE_PATH_SIZE - 5;
|
||||||
|
cmdp += 2;
|
||||||
|
break;
|
||||||
|
default :
|
||||||
|
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
|
||||||
|
errors = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
//Validations
|
||||||
|
if (errors || strlen(Cmd) == 0) return usage_hf_cryptorf_esave();
|
||||||
|
|
||||||
|
// set up buffer
|
||||||
|
uint8_t *data = calloc(numofbytes, sizeof(uint8_t));
|
||||||
|
if (!data) {
|
||||||
|
PrintAndLogEx(WARNING, "Fail, cannot allocate memory");
|
||||||
|
return PM3_EMALLOC;
|
||||||
|
}
|
||||||
|
|
||||||
|
// download emulator memory
|
||||||
|
PrintAndLogEx(SUCCESS, "Reading emulator memory...");
|
||||||
|
if (!GetFromDevice(BIG_BUF_EML, data, numofbytes, 0, NULL, 0, NULL, 2500, false)) {
|
||||||
|
PrintAndLogEx(WARNING, "Fail, transfer from device time-out");
|
||||||
|
free(data);
|
||||||
|
return PM3_ETIMEOUT;
|
||||||
|
}
|
||||||
|
|
||||||
|
// user supplied filename?
|
||||||
|
if (fileNameLen < 1) {
|
||||||
|
PrintAndLogEx(INFO, "Using UID as filename");
|
||||||
|
fptr += sprintf(fptr, "hf-cryptorf-");
|
||||||
|
FillFileNameByUID(fptr, data, "-dump", 4);
|
||||||
|
}
|
||||||
|
|
||||||
|
saveFile(filename, ".bin", data, numofbytes);
|
||||||
|
//needs to change
|
||||||
|
saveFileEML(filename, data, numofbytes, 8);
|
||||||
|
//needs to change
|
||||||
|
saveFileJSON(filename, jsfRaw, data, numofbytes);
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
static command_t CommandTable[] = {
|
||||||
|
{"help", CmdHelp, AlwaysAvailable, "This help"},
|
||||||
|
{"dump", CmdHFCryptoRFDump, IfPm3Iso14443b, "Read all memory pages of an CryptoRF tag, save to file"},
|
||||||
|
{"info", CmdHFCryptoRFInfo, IfPm3Iso14443b, "Tag information"},
|
||||||
|
{"list", CmdHFCryptoRFList, AlwaysAvailable, "List ISO 14443B history"},
|
||||||
|
{"reader", CmdHFCryptoRFReader, IfPm3Iso14443b, "Act as a CryptoRF reader to identify a tag"},
|
||||||
|
{"sim", CmdHFCryptoRFSim, IfPm3Iso14443b, "Fake CryptoRF tag"},
|
||||||
|
{"sniff", CmdHFCryptoRFSniff, IfPm3Iso14443b, "Eavesdrop CryptoRF"},
|
||||||
|
{"eload", CmdHFCryptoRFELoad, AlwaysAvailable, "Load binary dump to emulator memory"},
|
||||||
|
{"esave", CmdHFCryptoRFESave, AlwaysAvailable, "Save emulator memory to binary file"},
|
||||||
|
|
||||||
|
{NULL, NULL, NULL, NULL}
|
||||||
|
};
|
||||||
|
|
||||||
|
static int CmdHelp(const char *Cmd) {
|
||||||
|
(void)Cmd; // Cmd is not used so far
|
||||||
|
CmdsHelp(CommandTable);
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
int CmdHFCryptoRF(const char *Cmd) {
|
||||||
|
clearCommandBuffer();
|
||||||
|
return CmdsParse(CommandTable, Cmd);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Print extented information about tag.
|
||||||
|
int infoHFCryptoRF(bool verbose) {
|
||||||
|
|
||||||
|
int res = PM3_ESOFT;
|
||||||
|
|
||||||
|
// 14b get and print UID only (general info)
|
||||||
|
clearCommandBuffer();
|
||||||
|
SendCommandMIX(CMD_HF_ISO14443B_COMMAND, ISO14B_CONNECT | ISO14B_SELECT_STD | ISO14B_DISCONNECT, 0, 0, NULL, 0);
|
||||||
|
PacketResponseNG resp;
|
||||||
|
|
||||||
|
if (!WaitForResponseTimeout(CMD_ACK, &resp, TIMEOUT)) {
|
||||||
|
if (verbose) PrintAndLogEx(WARNING, "command execution timeout");
|
||||||
|
switch_off_field_cryptorf();
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
iso14b_card_select_t card;
|
||||||
|
memcpy(&card, (iso14b_card_select_t *)resp.data.asBytes, sizeof(iso14b_card_select_t));
|
||||||
|
|
||||||
|
uint64_t status = resp.oldarg[0];
|
||||||
|
|
||||||
|
switch (status) {
|
||||||
|
case 0:
|
||||||
|
PrintAndLogEx(NORMAL, "");
|
||||||
|
PrintAndLogEx(SUCCESS, " UID : %s", sprint_hex(card.uid, card.uidlen));
|
||||||
|
PrintAndLogEx(SUCCESS, " ATQB : %s", sprint_hex(card.atqb, sizeof(card.atqb)));
|
||||||
|
PrintAndLogEx(SUCCESS, " CHIPID : %02X", card.chipid);
|
||||||
|
res = PM3_SUCCESS;
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
if (verbose) PrintAndLogEx(FAILED, "ISO 14443-3 ATTRIB fail");
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
if (verbose) PrintAndLogEx(FAILED, "ISO 14443-3 CRC fail");
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
if (verbose) PrintAndLogEx(FAILED, "ISO 14443-b card select failed");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
// get and print general info cryptoRF
|
||||||
|
int readHFCryptoRF(bool verbose) {
|
||||||
|
|
||||||
|
int res = PM3_ESOFT;
|
||||||
|
|
||||||
|
// 14b get and print UID only (general info)
|
||||||
|
clearCommandBuffer();
|
||||||
|
SendCommandMIX(CMD_HF_ISO14443B_COMMAND, ISO14B_CONNECT | ISO14B_SELECT_STD | ISO14B_DISCONNECT, 0, 0, NULL, 0);
|
||||||
|
PacketResponseNG resp;
|
||||||
|
|
||||||
|
if (!WaitForResponseTimeout(CMD_ACK, &resp, TIMEOUT)) {
|
||||||
|
if (verbose) PrintAndLogEx(WARNING, "command execution timeout");
|
||||||
|
return PM3_ETIMEOUT;
|
||||||
|
}
|
||||||
|
|
||||||
|
iso14b_card_select_t card;
|
||||||
|
memcpy(&card, (iso14b_card_select_t *)resp.data.asBytes, sizeof(iso14b_card_select_t));
|
||||||
|
|
||||||
|
uint64_t status = resp.oldarg[0];
|
||||||
|
|
||||||
|
switch (status) {
|
||||||
|
case 0:
|
||||||
|
PrintAndLogEx(NORMAL, "");
|
||||||
|
PrintAndLogEx(SUCCESS, " UID : %s", sprint_hex(card.uid, card.uidlen));
|
||||||
|
PrintAndLogEx(SUCCESS, " ATQB : %s", sprint_hex(card.atqb, sizeof(card.atqb)));
|
||||||
|
PrintAndLogEx(SUCCESS, " CHIPID : %02X", card.chipid);
|
||||||
|
res = PM3_SUCCESS;
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
if (verbose) PrintAndLogEx(FAILED, "ISO 14443-3 ATTRIB fail");
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
if (verbose) PrintAndLogEx(FAILED, "ISO 14443-3 CRC fail");
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
if (verbose) PrintAndLogEx(FAILED, "ISO 14443-b card select failed");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return res;
|
||||||
|
}
|
20
client/cmdhfcryptorf.h
Normal file
20
client/cmdhfcryptorf.h
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
// Copyright (C) 2020 iceman
|
||||||
|
//
|
||||||
|
// 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.
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
// High frequency CryptoRF commands (ISO14443B)
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
#ifndef CMDHFCRYPTORF_H__
|
||||||
|
#define CMDHFCRYPTORF_H__
|
||||||
|
|
||||||
|
#include "common.h"
|
||||||
|
|
||||||
|
int CmdHFCryptoRF(const char *Cmd);
|
||||||
|
|
||||||
|
int infoHFCryptoRF(bool verbose);
|
||||||
|
int readHFCryptoRF(bool verbose);
|
||||||
|
#endif
|
|
@ -1847,37 +1847,37 @@ int readFelicaUid(bool verbose) {
|
||||||
}
|
}
|
||||||
|
|
||||||
static command_t CommandTable[] = {
|
static command_t CommandTable[] = {
|
||||||
{"----------- General -----------", CmdHelp, IfPm3Iso14443a, ""},
|
{"----------- General -----------", CmdHelp, AlwaysAvailable, ""},
|
||||||
{"help", CmdHelp, AlwaysAvailable, "This help"},
|
{"help", CmdHelp, AlwaysAvailable, "This help"},
|
||||||
{"list", CmdHFFelicaList, AlwaysAvailable, "List ISO 18092/FeliCa history"},
|
{"list", CmdHFFelicaList, AlwaysAvailable, "List ISO 18092/FeliCa history"},
|
||||||
{"reader", CmdHFFelicaReader, IfPm3Felica, "Act like an ISO18092/FeliCa reader"},
|
{"reader", CmdHFFelicaReader, IfPm3Felica, "Act like an ISO18092/FeliCa reader"},
|
||||||
{"sniff", CmdHFFelicaSniff, IfPm3Felica, "Sniff ISO 18092/FeliCa traffic"},
|
{"sniff", CmdHFFelicaSniff, IfPm3Felica, "Sniff ISO 18092/FeliCa traffic"},
|
||||||
{"raw", CmdHFFelicaCmdRaw, IfPm3Felica, "Send raw hex data to tag"},
|
{"raw", CmdHFFelicaCmdRaw, IfPm3Felica, "Send raw hex data to tag"},
|
||||||
{"rdunencrypted", CmdHFFelicaReadWithoutEncryption, IfPm3Felica, "read Block Data from authentication-not-required Service."},
|
{"rdunencrypted", CmdHFFelicaReadWithoutEncryption, IfPm3Felica, "read Block Data from authentication-not-required Service."},
|
||||||
{"wrunencrypted", CmdHFFelicaWriteWithoutEncryption, IfPm3Felica, "write Block Data to an authentication-not-required Service."},
|
{"wrunencrypted", CmdHFFelicaWriteWithoutEncryption, IfPm3Felica, "write Block Data to an authentication-not-required Service."},
|
||||||
{"----------- FeliCa Standard -----------", CmdHelp, IfPm3Iso14443a, ""},
|
{"----------- FeliCa Standard -----------", CmdHelp, AlwaysAvailable, ""},
|
||||||
//{"dump", CmdHFFelicaDump, IfPm3Felica, "Wait for and try dumping FeliCa"},
|
//{"dump", CmdHFFelicaDump, IfPm3Felica, "Wait for and try dumping FeliCa"},
|
||||||
{"rqservice", CmdHFFelicaRequestService, IfPm3Felica, "verify the existence of Area and Service, and to acquire Key Version."},
|
{"rqservice", CmdHFFelicaRequestService, IfPm3Felica, "verify the existence of Area and Service, and to acquire Key Version."},
|
||||||
{"rqresponse", CmdHFFelicaRequestResponse, IfPm3Felica, "verify the existence of a card and its Mode."},
|
{"rqresponse", CmdHFFelicaRequestResponse, IfPm3Felica, "verify the existence of a card and its Mode."},
|
||||||
{"scsvcode", CmdHFFelicaNotImplementedYet, IfPm3Felica, "acquire Area Code and Service Code."},
|
{"scsvcode", CmdHFFelicaNotImplementedYet, IfPm3Felica, "acquire Area Code and Service Code."},
|
||||||
{"rqsyscode", CmdHFFelicaRequestSystemCode, IfPm3Felica, "acquire System Code registered to the card."},
|
{"rqsyscode", CmdHFFelicaRequestSystemCode, IfPm3Felica, "acquire System Code registered to the card."},
|
||||||
{"auth1", CmdHFFelicaAuthentication1, IfPm3Felica, "authenticate a card. Start mutual authentication with Auth1"},
|
{"auth1", CmdHFFelicaAuthentication1, IfPm3Felica, "authenticate a card. Start mutual authentication with Auth1"},
|
||||||
{"auth2", CmdHFFelicaAuthentication2, IfPm3Felica, "allow a card to authenticate a Reader/Writer. Complete mutual authentication"},
|
{"auth2", CmdHFFelicaAuthentication2, IfPm3Felica, "allow a card to authenticate a Reader/Writer. Complete mutual authentication"},
|
||||||
//{"read", CmdHFFelicaNotImplementedYet, IfPm3Felica, "read Block Data from authentication-required Service."},
|
//{"read", CmdHFFelicaNotImplementedYet, IfPm3Felica, "read Block Data from authentication-required Service."},
|
||||||
//{"write", CmdHFFelicaNotImplementedYet, IfPm3Felica, "write Block Data to an authentication-required Service."},
|
//{"write", CmdHFFelicaNotImplementedYet, IfPm3Felica, "write Block Data to an authentication-required Service."},
|
||||||
//{"scsvcodev2", CmdHFFelicaNotImplementedYet, IfPm3Felica, "verify the existence of Area or Service, and to acquire Key Version."},
|
//{"scsvcodev2", CmdHFFelicaNotImplementedYet, IfPm3Felica, "verify the existence of Area or Service, and to acquire Key Version."},
|
||||||
//{"getsysstatus", CmdHFFelicaNotImplementedYet, IfPm3Felica, "acquire the setup information in System."},
|
//{"getsysstatus", CmdHFFelicaNotImplementedYet, IfPm3Felica, "acquire the setup information in System."},
|
||||||
{"rqspecver", CmdHFFelicaRequestSpecificationVersion, IfPm3Felica, "acquire the version of card OS."},
|
{"rqspecver", CmdHFFelicaRequestSpecificationVersion, IfPm3Felica, "acquire the version of card OS."},
|
||||||
{"resetmode", CmdHFFelicaResetMode, IfPm3Felica, "reset Mode to Mode 0."},
|
{"resetmode", CmdHFFelicaResetMode, IfPm3Felica, "reset Mode to Mode 0."},
|
||||||
//{"auth1v2", CmdHFFelicaNotImplementedYet, IfPm3Felica, "authenticate a card."},
|
//{"auth1v2", CmdHFFelicaNotImplementedYet, IfPm3Felica, "authenticate a card."},
|
||||||
//{"auth2v2", CmdHFFelicaNotImplementedYet, IfPm3Felica, "allow a card to authenticate a Reader/Writer."},
|
//{"auth2v2", CmdHFFelicaNotImplementedYet, IfPm3Felica, "allow a card to authenticate a Reader/Writer."},
|
||||||
//{"readv2", CmdHFFelicaNotImplementedYet, IfPm3Felica, "read Block Data from authentication-required Service."},
|
//{"readv2", CmdHFFelicaNotImplementedYet, IfPm3Felica, "read Block Data from authentication-required Service."},
|
||||||
//{"writev2", CmdHFFelicaNotImplementedYet, IfPm3Felica, "write Block Data to authentication-required Service."},
|
//{"writev2", CmdHFFelicaNotImplementedYet, IfPm3Felica, "write Block Data to authentication-required Service."},
|
||||||
//{"uprandomid", CmdHFFelicaNotImplementedYet, IfPm3Felica, "update Random ID (IDr)."},
|
//{"uprandomid", CmdHFFelicaNotImplementedYet, IfPm3Felica, "update Random ID (IDr)."},
|
||||||
{"----------- FeliCa Light -----------", CmdHelp, IfPm3Iso14443a, ""},
|
{"----------- FeliCa Light -----------", CmdHelp, AlwaysAvailable, ""},
|
||||||
{"litesim", CmdHFFelicaSimLite, IfPm3Felica, "<NDEF2> - only reply to poll request"},
|
{"litesim", CmdHFFelicaSimLite, IfPm3Felica, "<NDEF2> - only reply to poll request"},
|
||||||
{"litedump", CmdHFFelicaDumpLite, IfPm3Felica, "Wait for and try dumping FelicaLite"},
|
{"litedump", CmdHFFelicaDumpLite, IfPm3Felica, "Wait for and try dumping FelicaLite"},
|
||||||
// {"sim", CmdHFFelicaSim, IfPm3Felica, "<UID> -- Simulate ISO 18092/FeliCa tag"}
|
// {"sim", CmdHFFelicaSim, IfPm3Felica, "<UID> -- Simulate ISO 18092/FeliCa tag"}
|
||||||
{NULL, NULL, NULL, NULL}
|
{NULL, NULL, NULL, NULL}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -2050,7 +2050,7 @@ static int CmdHFiClassReadTagFile(const char *Cmd) {
|
||||||
|
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
PrintAndLogEx(INFO, "File: " _YELLOW_("%s"), filename);
|
PrintAndLogEx(INFO, "File: " _YELLOW_("%s"), filename);
|
||||||
PrintAndLogEx(INFO, "File size %d bytes, file blocks %d (0x%02x)", bytes_read, bytes_read >> 3, bytes_read >> 3);
|
PrintAndLogEx(INFO, "File size %zu bytes, file blocks %d (0x%x)", bytes_read, (uint16_t)(bytes_read >> 3), (uint16_t)(bytes_read >> 3));
|
||||||
PrintAndLogEx(INFO, "Printing blocks from");
|
PrintAndLogEx(INFO, "Printing blocks from");
|
||||||
PrintAndLogEx(INFO, "start " _YELLOW_("0x%02x") "end " _YELLOW_("0x%02x"), (startblock == 0) ? 6 : startblock, endblock);
|
PrintAndLogEx(INFO, "start " _YELLOW_("0x%02x") "end " _YELLOW_("0x%02x"), (startblock == 0) ? 6 : startblock, endblock);
|
||||||
}
|
}
|
||||||
|
|
|
@ -1013,43 +1013,47 @@ static int CmdLegicDump(const char *Cmd) {
|
||||||
saveFile(filename, ".bin", data, readlen);
|
saveFile(filename, ".bin", data, readlen);
|
||||||
saveFileEML(filename, data, readlen, 8);
|
saveFileEML(filename, data, readlen, 8);
|
||||||
saveFileJSON(filename, jsfLegic, data, readlen);
|
saveFileJSON(filename, jsfLegic, data, readlen);
|
||||||
|
free(data);
|
||||||
return PM3_SUCCESS;
|
return PM3_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int CmdLegicRestore(const char *Cmd) {
|
static int CmdLegicRestore(const char *Cmd) {
|
||||||
|
|
||||||
char filename[FILE_PATH_SIZE] = {0x00};
|
char filename[FILE_PATH_SIZE] = {0x00};
|
||||||
size_t fileNlen = 0;
|
bool errors = false, shall_obsfuscate = false, have_filename = false;
|
||||||
bool errors = false, shall_obsfuscate = false;
|
|
||||||
size_t numofbytes;
|
size_t numofbytes;
|
||||||
uint8_t cmdp = 0;
|
uint8_t cmdp = 0;
|
||||||
|
|
||||||
memset(filename, 0, sizeof(filename));
|
|
||||||
|
|
||||||
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
|
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
|
||||||
switch (tolower(param_getchar(Cmd, cmdp))) {
|
switch (tolower(param_getchar(Cmd, cmdp))) {
|
||||||
case 'h':
|
case 'h': {
|
||||||
errors = true;
|
errors = true;
|
||||||
break;
|
break;
|
||||||
case 'f':
|
}
|
||||||
fileNlen = param_getstr(Cmd, cmdp + 1, filename, FILE_PATH_SIZE);
|
case 'f': {
|
||||||
if (!fileNlen)
|
if (param_getstr(Cmd, cmdp + 1, filename, FILE_PATH_SIZE) >= FILE_PATH_SIZE) {
|
||||||
errors = true;
|
PrintAndLogEx(FAILED, "Filename too long");
|
||||||
|
break;
|
||||||
if (fileNlen > FILE_PATH_SIZE - 5)
|
}
|
||||||
fileNlen = FILE_PATH_SIZE - 5;
|
have_filename = true;
|
||||||
cmdp += 2;
|
cmdp += 2;
|
||||||
break;
|
break;
|
||||||
case 'x':
|
}
|
||||||
|
case 'x': {
|
||||||
shall_obsfuscate = true;
|
shall_obsfuscate = true;
|
||||||
cmdp++;
|
cmdp++;
|
||||||
break;
|
break;
|
||||||
default:
|
}
|
||||||
|
default: {
|
||||||
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
|
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
|
||||||
errors = true;
|
errors = true;
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if (have_filename == false)
|
||||||
|
errors = true;
|
||||||
|
|
||||||
//Validations
|
//Validations
|
||||||
if (errors || cmdp == 0) return usage_legic_restore();
|
if (errors || cmdp == 0) return usage_legic_restore();
|
||||||
|
|
||||||
|
@ -1076,7 +1080,7 @@ static int CmdLegicRestore(const char *Cmd) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (card.cardsize != numofbytes) {
|
if (card.cardsize != numofbytes) {
|
||||||
PrintAndLogEx(WARNING, "Fail, filesize and cardsize is not equal. [%zu != %u]", card.cardsize, numofbytes);
|
PrintAndLogEx(WARNING, "Fail, filesize and cardsize is not equal. [%u != %zu]", card.cardsize, numofbytes);
|
||||||
free(data);
|
free(data);
|
||||||
return PM3_EFILE;
|
return PM3_EFILE;
|
||||||
}
|
}
|
||||||
|
@ -1132,45 +1136,54 @@ static int CmdLegicRestore(const char *Cmd) {
|
||||||
static int CmdLegicELoad(const char *Cmd) {
|
static int CmdLegicELoad(const char *Cmd) {
|
||||||
|
|
||||||
size_t numofbytes = 256;
|
size_t numofbytes = 256;
|
||||||
int fileNameLen = 0;
|
|
||||||
char filename[FILE_PATH_SIZE] = {0x00};
|
char filename[FILE_PATH_SIZE] = {0x00};
|
||||||
bool errors = false, shall_obsfuscate = false;
|
bool errors = false, shall_obsfuscate = false, have_filename = false;
|
||||||
uint8_t cmdp = 0;
|
uint8_t cmdp = 0;
|
||||||
|
|
||||||
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
|
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
|
||||||
switch (tolower(param_getchar(Cmd, cmdp))) {
|
switch (tolower(param_getchar(Cmd, cmdp))) {
|
||||||
case 'h' :
|
case 'h' : {
|
||||||
return usage_legic_eload();
|
return usage_legic_eload();
|
||||||
case 'f' :
|
}
|
||||||
fileNameLen = param_getstr(Cmd, cmdp + 1, filename, FILE_PATH_SIZE);
|
case 'f' : {
|
||||||
if (!fileNameLen)
|
if (param_getstr(Cmd, cmdp + 1, filename, FILE_PATH_SIZE) >= FILE_PATH_SIZE) {
|
||||||
errors = true;
|
PrintAndLogEx(FAILED, "Filename too long");
|
||||||
if (fileNameLen > FILE_PATH_SIZE - 5)
|
break;
|
||||||
fileNameLen = FILE_PATH_SIZE - 5;
|
}
|
||||||
|
have_filename = true;
|
||||||
cmdp += 2;
|
cmdp += 2;
|
||||||
break;
|
break;
|
||||||
case 'x':
|
}
|
||||||
|
case 'x': {
|
||||||
shall_obsfuscate = true;
|
shall_obsfuscate = true;
|
||||||
cmdp++;
|
cmdp++;
|
||||||
break;
|
break;
|
||||||
case '0' :
|
}
|
||||||
|
case '0' : {
|
||||||
numofbytes = 22;
|
numofbytes = 22;
|
||||||
cmdp++;
|
cmdp++;
|
||||||
break;
|
break;
|
||||||
case '1' :
|
}
|
||||||
|
case '1' : {
|
||||||
numofbytes = 256;
|
numofbytes = 256;
|
||||||
cmdp++;
|
cmdp++;
|
||||||
break;
|
break;
|
||||||
case '2' :
|
}
|
||||||
|
case '2' : {
|
||||||
numofbytes = 1024;
|
numofbytes = 1024;
|
||||||
cmdp++;
|
cmdp++;
|
||||||
break;
|
break;
|
||||||
default :
|
}
|
||||||
|
default : {
|
||||||
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
|
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
|
||||||
errors = true;
|
errors = true;
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if (have_filename == false)
|
||||||
|
errors = true;
|
||||||
|
|
||||||
//Validations
|
//Validations
|
||||||
if (errors || strlen(Cmd) == 0) return usage_legic_eload();
|
if (errors || strlen(Cmd) == 0) return usage_legic_eload();
|
||||||
|
|
||||||
|
@ -1358,8 +1371,8 @@ static command_t CommandTable[] = {
|
||||||
{"sim", CmdLegicSim, IfPm3Legicrf, "Start tag simulator"},
|
{"sim", CmdLegicSim, IfPm3Legicrf, "Start tag simulator"},
|
||||||
{"wrbl", CmdLegicWrbl, IfPm3Legicrf, "Write data to a LEGIC Prime tag"},
|
{"wrbl", CmdLegicWrbl, IfPm3Legicrf, "Write data to a LEGIC Prime tag"},
|
||||||
{"crc", CmdLegicCalcCrc, AlwaysAvailable, "Calculate Legic CRC over given bytes"},
|
{"crc", CmdLegicCalcCrc, AlwaysAvailable, "Calculate Legic CRC over given bytes"},
|
||||||
{"eload", CmdLegicELoad, IfPm3Legicrf, "Load binary dump to emulator memory"},
|
{"eload", CmdLegicELoad, AlwaysAvailable, "Load binary dump to emulator memory"},
|
||||||
{"esave", CmdLegicESave, IfPm3Legicrf, "Save emulator memory to binary file"},
|
{"esave", CmdLegicESave, AlwaysAvailable, "Save emulator memory to binary file"},
|
||||||
{"wipe", CmdLegicWipe, IfPm3Legicrf, "Wipe a LEGIC Prime tag"},
|
{"wipe", CmdLegicWipe, IfPm3Legicrf, "Wipe a LEGIC Prime tag"},
|
||||||
{NULL, NULL, NULL, NULL}
|
{NULL, NULL, NULL, NULL}
|
||||||
};
|
};
|
||||||
|
|
|
@ -3712,7 +3712,7 @@ int CmdHF14AMfELoad(const char *Cmd) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
PrintAndLogEx(INFO, "Copying to emulator memory");
|
PrintAndLogEx(INFO, "Uploading to emulator memory");
|
||||||
|
|
||||||
// fast push mode
|
// fast push mode
|
||||||
conn.block_after_ACK = true;
|
conn.block_after_ACK = true;
|
||||||
|
|
|
@ -2781,7 +2781,20 @@ static int CmdHF14MfuNDEF(const char *Cmd) {
|
||||||
// max datasize;
|
// max datasize;
|
||||||
maxsize = ndef_get_maxsize(data + 12);
|
maxsize = ndef_get_maxsize(data + 12);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// iceman: maybe always take MIN of tag identified size vs NDEF reported size?
|
||||||
|
// fix: UL_EV1 48bytes != NDEF reported size
|
||||||
|
for (uint8_t i = 0; i < ARRAYLEN(UL_TYPES_ARRAY); i++) {
|
||||||
|
if (tagtype & UL_TYPES_ARRAY[i]) {
|
||||||
|
|
||||||
|
if (maxsize != (UL_MEMORY_ARRAY[i] * 4) ) {
|
||||||
|
PrintAndLogEx(INFO, "Tag reported size vs NDEF reported size mismatch. Using smallest value");
|
||||||
|
}
|
||||||
|
maxsize = MIN(maxsize, (UL_MEMORY_ARRAY[i] * 4));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// allocate mem
|
// allocate mem
|
||||||
uint8_t *records = calloc(maxsize, sizeof(uint8_t));
|
uint8_t *records = calloc(maxsize, sizeof(uint8_t));
|
||||||
if (records == NULL) {
|
if (records == NULL) {
|
||||||
|
@ -2795,6 +2808,7 @@ static int CmdHF14MfuNDEF(const char *Cmd) {
|
||||||
if (status == -1) {
|
if (status == -1) {
|
||||||
DropField();
|
DropField();
|
||||||
PrintAndLogEx(ERR, "Error: tag didn't answer to READ");
|
PrintAndLogEx(ERR, "Error: tag didn't answer to READ");
|
||||||
|
free(records);
|
||||||
return PM3_ESOFT;
|
return PM3_ESOFT;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -94,6 +94,10 @@ int JsonSaveStr(json_t *root, const char *path, const char *value) {
|
||||||
return JsonSaveJsonObject(root, path, json_string(value));
|
return JsonSaveJsonObject(root, path, json_string(value));
|
||||||
};
|
};
|
||||||
|
|
||||||
|
int JsonSaveBoolean(json_t *root, const char *path, bool value) {
|
||||||
|
return JsonSaveJsonObject(root, path, json_boolean(value));
|
||||||
|
}
|
||||||
|
|
||||||
int JsonSaveBufAsHexCompact(json_t *elm, const char *path, uint8_t *data, size_t datalen) {
|
int JsonSaveBufAsHexCompact(json_t *elm, const char *path, uint8_t *data, size_t datalen) {
|
||||||
char *msg = sprint_hex_inrow(data, datalen);
|
char *msg = sprint_hex_inrow(data, datalen);
|
||||||
if (msg && strlen(msg) && msg[strlen(msg) - 1] == ' ')
|
if (msg && strlen(msg) && msg[strlen(msg) - 1] == ' ')
|
||||||
|
|
|
@ -24,6 +24,7 @@ const char *GetApplicationDataName(tlv_tag_t tag);
|
||||||
|
|
||||||
int JsonSaveJsonObject(json_t *root, const char *path, json_t *value);
|
int JsonSaveJsonObject(json_t *root, const char *path, json_t *value);
|
||||||
int JsonSaveStr(json_t *root, const char *path, const char *value);
|
int JsonSaveStr(json_t *root, const char *path, const char *value);
|
||||||
|
int JsonSaveBoolean(json_t *root, const char *path, bool value);
|
||||||
int JsonSaveInt(json_t *root, const char *path, int value);
|
int JsonSaveInt(json_t *root, const char *path, int value);
|
||||||
int JsonSaveBufAsHexCompact(json_t *elm, const char *path, uint8_t *data, size_t datalen);
|
int JsonSaveBufAsHexCompact(json_t *elm, const char *path, uint8_t *data, size_t datalen);
|
||||||
int JsonSaveBufAsHex(json_t *elm, const char *path, uint8_t *data, size_t datalen);
|
int JsonSaveBufAsHex(json_t *elm, const char *path, uint8_t *data, size_t datalen);
|
||||||
|
|
|
@ -38,6 +38,7 @@
|
||||||
// this define is needed for scandir/alphasort to work
|
// this define is needed for scandir/alphasort to work
|
||||||
#define _GNU_SOURCE
|
#define _GNU_SOURCE
|
||||||
#include "fileutils.h"
|
#include "fileutils.h"
|
||||||
|
#include "settings.h"
|
||||||
|
|
||||||
#include <dirent.h>
|
#include <dirent.h>
|
||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
|
@ -425,6 +426,9 @@ int saveFileJSON(const char *preferredName, JSONFileType ftype, uint8_t *data, s
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case jsfSettings:
|
||||||
|
settings_save_callback (root);
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -863,7 +867,9 @@ int loadFileJSON(const char *preferredName, void *data, size_t maxdatalen, size_
|
||||||
}
|
}
|
||||||
*datalen = sptr;
|
*datalen = sptr;
|
||||||
}
|
}
|
||||||
|
if (!strcmp(ctype,"settings")) {
|
||||||
|
settings_load_callback (root);
|
||||||
|
}
|
||||||
PrintAndLogEx(SUCCESS, "loaded from JSON file " _YELLOW_("%s"), fileName);
|
PrintAndLogEx(SUCCESS, "loaded from JSON file " _YELLOW_("%s"), fileName);
|
||||||
out:
|
out:
|
||||||
json_decref(root);
|
json_decref(root);
|
||||||
|
|
|
@ -62,6 +62,7 @@ typedef enum {
|
||||||
jsfT55x7,
|
jsfT55x7,
|
||||||
jsfT5555,
|
jsfT5555,
|
||||||
jsfMfPlusKeys,
|
jsfMfPlusKeys,
|
||||||
|
jsfSettings,
|
||||||
} JSONFileType;
|
} JSONFileType;
|
||||||
|
|
||||||
typedef enum {
|
typedef enum {
|
||||||
|
|
|
@ -1,13 +1,13 @@
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local bin = require('bin')
|
local bin = require('bin')
|
||||||
local dumplib = require('html_dumplib')
|
local dumplib = require('html_dumplib')
|
||||||
local ansicolors = require('ansicolors')
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Iceman'
|
author = 'Iceman'
|
||||||
version = 'v1.0.2'
|
version = 'v1.0.2'
|
||||||
desc =[[
|
desc =[[
|
||||||
This script takes an dumpfile on EML (ASCII) format and converts it to the PM3 dumpbin file to be used with `hf mf restore`
|
This script takes an dumpfile in EML (ASCII) format and converts it to the PM3 dumpbin file to be used with `hf mf restore`
|
||||||
]]
|
]]
|
||||||
example =[[
|
example =[[
|
||||||
1. script run emul2dump
|
1. script run emul2dump
|
||||||
|
@ -25,7 +25,7 @@ arguments = [[
|
||||||
]]
|
]]
|
||||||
---
|
---
|
||||||
-- This is only meant to be used when errors occur
|
-- This is only meant to be used when errors occur
|
||||||
local function dbg(err)
|
local function dbg(args)
|
||||||
if not DEBUG then return end
|
if not DEBUG then return end
|
||||||
if type(args) == 'table' then
|
if type(args) == 'table' then
|
||||||
local i = 1
|
local i = 1
|
||||||
|
|
|
@ -3,10 +3,11 @@ local getopt = require('getopt')
|
||||||
local bin = require('bin')
|
local bin = require('bin')
|
||||||
local lib14a = require('read14a')
|
local lib14a = require('read14a')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Iceman'
|
author = 'Iceman'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = [[
|
desc = [[
|
||||||
This script will generate 'hf mf wrbl' commands for each block to format a Mifare card.
|
This script will generate 'hf mf wrbl' commands for each block to format a Mifare card.
|
||||||
|
|
||||||
|
@ -29,8 +30,8 @@ example = [[
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run formatMifare -k <key> -n <key> -a <access> -x
|
script run formatMifare -k <key> -n <key> -a <access> -x
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h - this help
|
-h - this help
|
||||||
-k <key> - the current six byte key with write access
|
-k <key> - the current six byte key with write access
|
||||||
-n <key> - the new key that will be written to the card
|
-n <key> - the new key that will be written to the card
|
||||||
|
@ -71,9 +72,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
-- Exit message
|
-- Exit message
|
||||||
|
|
|
@ -2,38 +2,38 @@
|
||||||
-- Run me like this (connected via Blueshark addon): ./client/proxmark3 /dev/rfcomm0 -l ./hf_bruteforce.lua
|
-- Run me like this (connected via Blueshark addon): ./client/proxmark3 /dev/rfcomm0 -l ./hf_bruteforce.lua
|
||||||
|
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Daniel Underhay (updated), Keld Norman(original)'
|
author = 'Daniel Underhay (updated), Keld Norman(original)'
|
||||||
version = 'v2.0.0'
|
version = 'v2.0.1'
|
||||||
usage = [[
|
desc =[[
|
||||||
|
This script bruteforces 4 or 7 byte UID Mifare classic card numbers.
|
||||||
pm3 --> script run hf_bruteforce -s start_id -e end_id -t timeout -x mifare_card_type
|
]]
|
||||||
|
example =[[
|
||||||
Arguments:
|
|
||||||
-h this help
|
|
||||||
-s 0-0xFFFFFFFF start id
|
|
||||||
-e 0-0xFFFFFFFF end id
|
|
||||||
-t 0-99999, pause timeout (ms) between cards (use the word 'pause' to wait for user input)
|
|
||||||
-x mfc, mfu mifare type: mfc for Mifare Classic (default) or mfu for Mifare Ultralight EV1
|
|
||||||
|
|
||||||
|
|
||||||
Example:
|
|
||||||
|
|
||||||
pm3 --> script run hf_bruteforce -s 0x11223344 -e 0x11223346 -t 1000 -x mfc
|
|
||||||
|
|
||||||
Bruteforce a 4 byte UID Mifare classic card number, starting at 11223344, ending at 11223346.
|
Bruteforce a 4 byte UID Mifare classic card number, starting at 11223344, ending at 11223346.
|
||||||
|
|
||||||
|
script run hf_bruteforce -s 0x11223344 -e 0x11223346 -t 1000 -x mfc
|
||||||
pm3 --> script run hf_bruteforce -s 0x11223344556677 -e 0x11223344556679 -t 1000 -x mfu
|
|
||||||
|
|
||||||
Bruteforce a 7 byte UID Mifare Ultralight card number, starting at 11223344556677, ending at 11223344556679.
|
Bruteforce a 7 byte UID Mifare Ultralight card number, starting at 11223344556677, ending at 11223344556679.
|
||||||
|
|
||||||
|
script run hf_bruteforce -s 0x11223344556677 -e 0x11223344556679 -t 1000 -x mfu
|
||||||
|
]]
|
||||||
|
usage = [[
|
||||||
|
script run hf_bruteforce [-s <start_id>] [-e <end_id>] [-t <timeout>] [-x <mifare_card_type>]
|
||||||
|
]]
|
||||||
|
arguments = [[
|
||||||
|
-h this help
|
||||||
|
-s 0-0xFFFFFFFF start id
|
||||||
|
-e 0-0xFFFFFFFF end id
|
||||||
|
-t 0-99999, pause timeout (ms) between cards
|
||||||
|
(use the word 'pause' to wait for user input)
|
||||||
|
-x mfc, mfu mifare type:
|
||||||
|
mfc for Mifare Classic (default)
|
||||||
|
mfu for Mifare Ultralight EV1
|
||||||
]]
|
]]
|
||||||
|
|
||||||
|
|
||||||
local DEBUG = true
|
local DEBUG = true
|
||||||
|
|
||||||
---
|
---
|
||||||
-- Debug print function
|
-- Debug print function
|
||||||
local function dbg(args)
|
local function dbg(args)
|
||||||
|
@ -62,9 +62,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
---
|
---
|
||||||
--- Print user message
|
--- Print user message
|
||||||
|
|
|
@ -1,6 +1,65 @@
|
||||||
local reader = require('hf_reader')
|
local reader = require('hf_reader')
|
||||||
|
local getopt = require('getopt')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
|
copyright = ''
|
||||||
|
author = ''
|
||||||
|
version = 'v1.0.1'
|
||||||
|
desc = [[
|
||||||
|
This script tries to detect a HF card. Just like 'hf search' does but this is experimental
|
||||||
|
]]
|
||||||
|
example = [[
|
||||||
|
1. script run hf_read
|
||||||
|
]]
|
||||||
|
usage = [[
|
||||||
|
script run hf_read
|
||||||
|
]]
|
||||||
|
arguments = [[
|
||||||
|
-h - this help
|
||||||
|
]]
|
||||||
|
---
|
||||||
|
-- This is only meant to be used when errors occur
|
||||||
|
local function dbg(args)
|
||||||
|
if not DEBUG then return end
|
||||||
|
if type(args) == 'table' then
|
||||||
|
local i = 1
|
||||||
|
while args[i] do
|
||||||
|
dbg(args[i])
|
||||||
|
i = i+1
|
||||||
|
end
|
||||||
|
else
|
||||||
|
print('###', args)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
---
|
||||||
|
-- This is only meant to be used when errors occur
|
||||||
|
local function oops(err)
|
||||||
|
print('ERROR:', err)
|
||||||
|
core.clearCommandBuffer()
|
||||||
|
return nil, err
|
||||||
|
end
|
||||||
|
---
|
||||||
|
-- Usage help
|
||||||
|
local function help()
|
||||||
|
print(copyright)
|
||||||
|
print(author)
|
||||||
|
print(version)
|
||||||
|
print(desc)
|
||||||
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
|
end
|
||||||
|
---
|
||||||
|
--
|
||||||
local function main(args)
|
local function main(args)
|
||||||
|
-- Arguments for the script
|
||||||
|
for o, a in getopt.getopt(args, 'h') do
|
||||||
|
if o == 'h' then return help() end
|
||||||
|
end
|
||||||
|
|
||||||
print("WORK IN PROGRESS - not expected to be functional yet")
|
print("WORK IN PROGRESS - not expected to be functional yet")
|
||||||
info, err = reader.waitForTag()
|
info, err = reader.waitForTag()
|
||||||
|
|
||||||
|
@ -15,4 +74,5 @@ local function main(args)
|
||||||
end
|
end
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
|
|
||||||
main(args)
|
main(args)
|
||||||
|
|
|
@ -3,10 +3,11 @@
|
||||||
getopt = require('getopt')
|
getopt = require('getopt')
|
||||||
bin = require('bin')
|
bin = require('bin')
|
||||||
dumplib = require('html_dumplib')
|
dumplib = require('html_dumplib')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Martin Holst Swende'
|
author = 'Martin Holst Swende'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc =[[
|
desc =[[
|
||||||
This script takes a dumpfile and produces a html based dump, which is a
|
This script takes a dumpfile and produces a html based dump, which is a
|
||||||
bit more easily analyzed.
|
bit more easily analyzed.
|
||||||
|
@ -16,8 +17,8 @@ example = [[
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run htmldump [-i <file>] [-o <file>]
|
script run htmldump [-i <file>] [-o <file>]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h This help
|
-h This help
|
||||||
-i <file> Specifies the dump-file (input). If omitted, 'dumpdata.bin' is used
|
-i <file> Specifies the dump-file (input). If omitted, 'dumpdata.bin' is used
|
||||||
-o <filename> Speciies the output file. If omitted, <curtime>.html is used.
|
-o <filename> Speciies the output file. If omitted, <curtime>.html is used.
|
||||||
|
@ -55,9 +56,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
|
|
||||||
local function main(args)
|
local function main(args)
|
||||||
|
|
|
@ -1,21 +1,21 @@
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = 'Copyright (c) 2019 IceSQL AB. All rights reserved.'
|
copyright = 'Copyright (c) 2019 IceSQL AB. All rights reserved.'
|
||||||
author = 'Christian Herrmann'
|
author = 'Christian Herrmann'
|
||||||
version = 'v1.0.0'
|
version = 'v1.0.1'
|
||||||
desc = [[
|
desc = [[
|
||||||
This script initialize a Proxmark3 RDV4.0 with
|
This script initialize a Proxmark3 RDV4.0 with
|
||||||
- uploading dictionary files to flashmem
|
- uploading dictionary files to flashmem
|
||||||
- configuring the LF T55X7 device settings
|
- configuring the LF T55X7 device settings
|
||||||
]]
|
]]
|
||||||
example = [[
|
example = [[
|
||||||
|
|
||||||
script run init_rdv4
|
script run init_rdv4
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run init_rdv4 -h
|
script run init_rdv4 -h
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
]]
|
]]
|
||||||
|
|
||||||
|
@ -48,9 +48,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
---
|
---
|
||||||
-- The main entry point
|
-- The main entry point
|
||||||
|
|
|
@ -2,10 +2,11 @@ local cmds = require('commands')
|
||||||
local lib15 = require('read15')
|
local lib15 = require('read15')
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = 'Copyright (c) 2018 IceSQL AB. All rights reserved.'
|
copyright = 'Copyright (c) 2018 IceSQL AB. All rights reserved.'
|
||||||
author = 'Christian Herrmann'
|
author = 'Christian Herrmann'
|
||||||
version = 'v1.0.5'
|
version = 'v1.0.6'
|
||||||
desc = [[
|
desc = [[
|
||||||
This script tries to set UID on a IS15693 SLIX magic card
|
This script tries to set UID on a IS15693 SLIX magic card
|
||||||
Remember the UID ->MUST<- start with 0xE0
|
Remember the UID ->MUST<- start with 0xE0
|
||||||
|
@ -20,8 +21,8 @@ example = [[
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run iso15_magic -h -u <uid>
|
script run iso15_magic -h -u <uid>
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
-u <UID> : UID (16 hexsymbols)
|
-u <UID> : UID (16 hexsymbols)
|
||||||
-a : use offical pm3 repo ISO15 commands instead of iceman fork.
|
-a : use offical pm3 repo ISO15 commands instead of iceman fork.
|
||||||
|
@ -56,9 +57,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
--- Set UID on magic command enabled on a ICEMAN based REPO
|
--- Set UID on magic command enabled on a ICEMAN based REPO
|
||||||
|
|
|
@ -1,10 +1,11 @@
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
-- this script writes bytes 8 to 256 on the Legic MIM256
|
-- this script writes bytes 8 to 256 on the Legic MIM256
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Mosci'
|
author = 'Mosci'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc =
|
desc =
|
||||||
[[
|
[[
|
||||||
This is a script which writes value 0x01 to bytes from position 0x07 until 0xFF on a Legic Prime Tag (MIM256 or MIM1024) -- (created with 'hf legic save my_dump.hex') --
|
This is a script which writes value 0x01 to bytes from position 0x07 until 0xFF on a Legic Prime Tag (MIM256 or MIM1024) -- (created with 'hf legic save my_dump.hex') --
|
||||||
|
@ -14,8 +15,8 @@ example = [[
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run legic_buffer2card -h
|
script run legic_buffer2card -h
|
||||||
|
]]
|
||||||
Arguments
|
arguments = [[
|
||||||
-h - Help text
|
-h - Help text
|
||||||
]]
|
]]
|
||||||
|
|
||||||
|
@ -33,9 +34,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
-- simple loop-write from 0x07 to 0xff
|
-- simple loop-write from 0x07 to 0xff
|
||||||
|
|
|
@ -1,8 +1,12 @@
|
||||||
|
local utils = require('utils')
|
||||||
|
local cmds = require('commands')
|
||||||
|
local getopt = require('getopt')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
--[[
|
--[[
|
||||||
script to create a clone-dump with new crc
|
script to create a clone-dump with new crc
|
||||||
Author: mosci
|
Author: mosci
|
||||||
my Fork: https://github.com/icsom/proxmark3.git
|
my Fork: https://github.com/icsom/proxmark3.git
|
||||||
Upstream: https://github.com/Proxmark/proxmark3.git
|
|
||||||
|
|
||||||
1. read tag-dump, xor byte 22..end with byte 0x05 of the inputfile
|
1. read tag-dump, xor byte 22..end with byte 0x05 of the inputfile
|
||||||
2. write to outfile
|
2. write to outfile
|
||||||
|
@ -11,20 +15,19 @@
|
||||||
5. from 0x22..end xored with newcrc
|
5. from 0x22..end xored with newcrc
|
||||||
6. calculate new crc on each segment (needs to know the new MCD & MSN0..2)
|
6. calculate new crc on each segment (needs to know the new MCD & MSN0..2)
|
||||||
|
|
||||||
simplest usage:
|
simplest usage:
|
||||||
read a valid legic tag with 'hf legic reader'
|
Dump a legic tag with 'hf legic dump'
|
||||||
save the dump with 'hf legic save orig.hex'
|
place your 'empty' tag on the reader and run
|
||||||
place your 'empty' tag on the reader and run 'script run Legic_clone -i orig.hex -w'
|
'script run legic_clone -i orig.bin -w'
|
||||||
you will see some output like:
|
|
||||||
read 1024 bytes from legic_dumps/j_0000.hex
|
you will see some output like:
|
||||||
|
|
||||||
|
read 1024 bytes from orig.bin
|
||||||
|
|
||||||
place your empty tag onto the PM3 to read and display the MCD & MSN0..2
|
place your empty tag onto the PM3 to read and display the MCD & MSN0..2
|
||||||
the values will be shown below
|
the values will be shown below
|
||||||
confirm when ready [y/n] ?y
|
confirm when ready [y/n] ?y
|
||||||
#db# setting up legic card
|
|
||||||
#db# MIM 256 card found, reading card ...
|
|
||||||
#db# Card read, use 'hf legic decode' or
|
|
||||||
#db# 'data hexsamples 8' to view results
|
|
||||||
0b ad c0 de <- !! here you'll see the MCD & MSN of your empty tag, which has to be typed in manually as seen below !!
|
0b ad c0 de <- !! here you'll see the MCD & MSN of your empty tag, which has to be typed in manually as seen below !!
|
||||||
type in MCD as 2-digit value - e.g.: 00 (default: 79 )
|
type in MCD as 2-digit value - e.g.: 00 (default: 79 )
|
||||||
> 0b
|
> 0b
|
||||||
|
@ -86,49 +89,63 @@
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Mosci'
|
author = 'Mosci'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = [[
|
desc = [[
|
||||||
This is a script which creates a clone-dump of a dump from a Legic Prime Tag (MIM256 or MIM1024)
|
This is a script which creates a clone-dump of a dump from a LEGIC Prime Tag (MIM256 or MIM1024)
|
||||||
(created with 'hf legic save my_dump.hex')
|
Create a dump by running `hf legic dump`.
|
||||||
]]
|
]]
|
||||||
example = [[
|
example = [[
|
||||||
script run legic_clone -i my_dump.hex -o my_clone.hex -c f8
|
script run legic_clone -i my_dump.bin -o my_clone.bin -c f8
|
||||||
script run legic_clone -i my_dump.hex -d -s
|
script run legic_clone -i my_dump.bin -d -s
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run legic_clone -h -i <file> -o <file> -c <crc> -d -s -w
|
script run legic_clone [-h] [-i <file>] [-o <file>] [-c <crc>] [-d] [-s] [-w]
|
||||||
|
]]
|
||||||
|
arguments = [[
|
||||||
|
required :
|
||||||
|
-i <input file> - file to read data from, must be in binary format (*.bin)
|
||||||
|
|
||||||
required arguments:
|
optional :
|
||||||
-i <input file> (file to read data from)
|
|
||||||
|
|
||||||
optional arguments :
|
|
||||||
-h - Help text
|
-h - Help text
|
||||||
-o <output file> - requires option -c to be given
|
-o <output file> - requires option -c to be given
|
||||||
-c <new-tag crc> - requires option -o to be given
|
-c <new-tag crc> - requires option -o to be given
|
||||||
-d - Display content of found Segments
|
-d - Display content of found Segments
|
||||||
-s - Display summary at the end
|
-s - Display summary at the end
|
||||||
-w - write directly to Tag - a file myLegicClone.hex wille be generated also
|
-w - write directly to tag - a file hf-legic-UID-dump.bin will also be generated
|
||||||
|
|
||||||
e.g.:
|
e.g.:
|
||||||
hint: using the CRC '00' will result in a plain dump ( -c 00 )
|
hint: using the CRC '00' will result in a plain dump ( -c 00 )
|
||||||
]]
|
]]
|
||||||
local utils = require('utils')
|
local DEBUG = true
|
||||||
local getopt = require('getopt')
|
|
||||||
local bxor = bit32.bxor
|
local bxor = bit32.bxor
|
||||||
|
---
|
||||||
|
-- This is only meant to be used when errors occur
|
||||||
|
local function dbg(args)
|
||||||
|
if not DEBUG then return end
|
||||||
|
if type(args) == 'table' then
|
||||||
|
local i = 1
|
||||||
|
while args[i] do
|
||||||
|
dbg(args[i])
|
||||||
|
i = i+1
|
||||||
|
end
|
||||||
|
else
|
||||||
|
print('###', args)
|
||||||
|
end
|
||||||
|
end
|
||||||
-- we need always 2 digits
|
-- we need always 2 digits
|
||||||
local function prepend_zero(s)
|
local function prepend_zero(s)
|
||||||
if (string.len(s) == 1) then
|
if s == nil then return '..' end
|
||||||
|
|
||||||
|
if (#s == 1) then
|
||||||
return '0' .. s
|
return '0' .. s
|
||||||
else
|
else
|
||||||
if (string.len(s) == 0) then
|
if (#s == 0) then
|
||||||
return '00'
|
return '00'
|
||||||
else
|
else
|
||||||
return s
|
return s
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
---
|
---
|
||||||
-- This is only meant to be used when errors occur
|
-- This is only meant to be used when errors occur
|
||||||
local function oops(err)
|
local function oops(err)
|
||||||
|
@ -136,7 +153,6 @@ local function oops(err)
|
||||||
core.clearCommandBuffer()
|
core.clearCommandBuffer()
|
||||||
return nil, err
|
return nil, err
|
||||||
end
|
end
|
||||||
|
|
||||||
---
|
---
|
||||||
-- Usage help
|
-- Usage help
|
||||||
local function help()
|
local function help()
|
||||||
|
@ -144,27 +160,45 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
|
end
|
||||||
|
-- read LEGIC data
|
||||||
|
local function readlegicdata(offset, length, iv)
|
||||||
|
-- Read data
|
||||||
|
local command = Command:newMIX{
|
||||||
|
cmd = cmds.CMD_HF_LEGIC_READER
|
||||||
|
, arg1 = offset
|
||||||
|
, arg2 = length
|
||||||
|
, arg3 = iv
|
||||||
|
, data = nil
|
||||||
|
}
|
||||||
|
local result, err = command:sendMIX()
|
||||||
|
if not result then return oops(err) end
|
||||||
|
-- result is a packed data structure, data starts at offset 33
|
||||||
|
return result
|
||||||
end
|
end
|
||||||
|
|
||||||
-- Check availability of file
|
-- Check availability of file
|
||||||
local function file_check(file_name)
|
local function file_check(file_name)
|
||||||
local file_found = io.open(file_name, "r")
|
local exists = io.open(file_name, "r")
|
||||||
if not file_found then
|
if not exists then
|
||||||
file_found = false
|
exists = false
|
||||||
else
|
else
|
||||||
file_found = true
|
exists = true
|
||||||
end
|
end
|
||||||
return file_found
|
return exists
|
||||||
end
|
end
|
||||||
|
|
||||||
--- xor-wrapper
|
--- xor-wrapper
|
||||||
-- xor all from addr 0x22 (start counting from 1 => 23)
|
-- xor all from addr 0x22 (start counting from 1 => 23)
|
||||||
local function xorme(hex, xor, index)
|
local function xorme(hex, xor, index)
|
||||||
if ( index >= 23 ) then
|
if ( index >= 23 ) then
|
||||||
return ('%02x'):format(bxor( tonumber(hex,16) , tonumber(xor,16) ))
|
return ('%02x'):format(bxor( tonumber(hex, 16) , tonumber(xor, 16) ))
|
||||||
else
|
else
|
||||||
return hex
|
return hex
|
||||||
end
|
end
|
||||||
|
@ -172,48 +206,28 @@ end
|
||||||
|
|
||||||
-- read input-file into array
|
-- read input-file into array
|
||||||
local function getInputBytes(infile)
|
local function getInputBytes(infile)
|
||||||
local line
|
|
||||||
local bytes = {}
|
local bytes = {}
|
||||||
|
local f = io.open(infile, "rb")
|
||||||
|
if f == nil then print("OOps ... failed to read from file ".. infile); return false; end
|
||||||
|
|
||||||
local fhi,err = io.open(infile)
|
local str = f:read("*all")
|
||||||
if err then print("OOps ... faild to read from file ".. infile); return false; end
|
f:close()
|
||||||
|
|
||||||
while true do
|
for c in (str or ''):gmatch'.' do
|
||||||
line = fhi:read()
|
bytes[#bytes + 1] = ('%02x'):format(c:byte())
|
||||||
if line == nil then break end
|
|
||||||
|
|
||||||
for byte in line:gmatch("%w+") do
|
|
||||||
table.insert(bytes, byte)
|
|
||||||
end
|
|
||||||
end
|
end
|
||||||
|
|
||||||
fhi:close()
|
print("\nread ".. #bytes .." bytes from "..ansicolors.yellow..infile..ansicolors.reset)
|
||||||
|
|
||||||
print("\nread ".. #bytes .." bytes from ".. infile)
|
|
||||||
return bytes
|
return bytes
|
||||||
end
|
end
|
||||||
|
|
||||||
-- write to file
|
-- write to file
|
||||||
local function writeOutputBytes(bytes, outfile)
|
local function writeOutputBytes(bytes, outfile)
|
||||||
local line
|
local fho,err = io.open(outfile, "wb")
|
||||||
local bcnt = 0
|
|
||||||
local fho,err = io.open(outfile,"w")
|
|
||||||
if err then print("OOps ... faild to open output-file ".. outfile); return false; end
|
if err then print("OOps ... faild to open output-file ".. outfile); return false; end
|
||||||
|
|
||||||
for i = 1, #bytes do
|
for i = 1, #bytes do
|
||||||
if (bcnt == 0) then
|
fho:write(string.char(tonumber(bytes[i], 16)))
|
||||||
line = bytes[i]
|
|
||||||
elseif (bcnt <= 7) then
|
|
||||||
line = line.." "..bytes[i]
|
|
||||||
end
|
|
||||||
if (bcnt == 7) then
|
|
||||||
-- write line to new file
|
|
||||||
fho:write(line.."\n")
|
|
||||||
-- reset counter & line
|
|
||||||
bcnt = -1
|
|
||||||
line = ""
|
|
||||||
end
|
|
||||||
bcnt = bcnt + 1
|
|
||||||
end
|
end
|
||||||
fho:close()
|
fho:close()
|
||||||
print("\nwrote ".. #bytes .." bytes to " .. outfile)
|
print("\nwrote ".. #bytes .." bytes to " .. outfile)
|
||||||
|
@ -228,7 +242,7 @@ local function xorBytes(inBytes, crc)
|
||||||
end
|
end
|
||||||
if (#inBytes == #bytes) then
|
if (#inBytes == #bytes) then
|
||||||
-- replace crc
|
-- replace crc
|
||||||
bytes[5] = string.sub(crc,-2)
|
bytes[5] = string.sub(crc, -2)
|
||||||
return bytes
|
return bytes
|
||||||
else
|
else
|
||||||
print("error: byte-count missmatch")
|
print("error: byte-count missmatch")
|
||||||
|
@ -237,63 +251,63 @@ local function xorBytes(inBytes, crc)
|
||||||
end
|
end
|
||||||
|
|
||||||
-- get raw segment-data
|
-- get raw segment-data
|
||||||
function getSegmentData(bytes, start, index)
|
local function getSegmentData(bytes, start, index)
|
||||||
local raw, len, valid, last, wrp, wrc, rd, crc
|
local raw, len, valid, last, wrp, wrc, rd, crc
|
||||||
local segment = {}
|
local segment = {}
|
||||||
segment[0] = bytes[start]..' '..bytes[start+1]..' '..bytes[start+2]..' '..bytes[start+3]
|
segment[0] = bytes[start]..' '..bytes[start + 1]..' '..bytes[start + 2]..' '..bytes[start + 3]
|
||||||
-- flag = high nibble of byte 1
|
-- flag = high nibble of byte 1
|
||||||
segment[1] = string.sub(bytes[start+1],0,1)
|
segment[1] = string.sub(bytes[start + 1], 0, 1)
|
||||||
|
|
||||||
-- valid = bit 6 of byte 1
|
-- valid = bit 6 of byte 1
|
||||||
segment[2] = tonumber(bit32.extract('0x'..bytes[start+1],6,1),16)
|
segment[2] = tonumber(bit32.extract('0x'..bytes[start + 1], 6, 1), 16)
|
||||||
|
|
||||||
-- last = bit 7 of byte 1
|
-- last = bit 7 of byte 1
|
||||||
segment[3] = tonumber(bit32.extract('0x'..bytes[start+1],7,1),16)
|
segment[3] = tonumber(bit32.extract('0x'..bytes[start + 1], 7, 1), 16)
|
||||||
|
|
||||||
-- len = (byte 0)+(bit0-3 of byte 1)
|
-- len = (byte 0)+(bit0-3 of byte 1)
|
||||||
segment[4] = tonumber(('%03x'):format(tonumber(bit32.extract('0x'..bytes[start+1],0,3),16)..tonumber(bytes[start],16)),16)
|
segment[4] = tonumber(('%03x'):format(tonumber(bit32.extract('0x'..bytes[start + 1], 0, 3), 16)..tonumber(bytes[start], 16)), 16)
|
||||||
|
|
||||||
-- wrp (write proteted) = byte 2
|
-- wrp (write proteted) = byte 2
|
||||||
segment[5] = tonumber(bytes[start+2])
|
segment[5] = tonumber(bytes[start + 2])
|
||||||
|
|
||||||
-- wrc (write control) - bit 4-6 of byte 3
|
-- wrc (write control) - bit 4-6 of byte 3
|
||||||
segment[6] = tonumber(bit32.extract('0x'..bytes[start+3],4,3),16)
|
segment[6] = tonumber(bit32.extract('0x'..bytes[start + 3], 4, 3), 16)
|
||||||
|
|
||||||
-- rd (read disabled) - bit 7 of byte 3
|
-- rd (read disabled) - bit 7 of byte 3
|
||||||
segment[7] = tonumber(bit32.extract('0x'..bytes[start+3],7,1),16)
|
segment[7] = tonumber(bit32.extract('0x'..bytes[start + 3], 7, 1), 16)
|
||||||
|
|
||||||
-- crc byte 4
|
-- crc byte 4
|
||||||
segment[8] = bytes[start+4]
|
segment[8] = bytes[start + 4]
|
||||||
|
|
||||||
-- segment index
|
-- segment index
|
||||||
segment[9] = index
|
segment[9] = index
|
||||||
|
|
||||||
-- # crc-byte
|
-- # crc-byte
|
||||||
segment[10] = start+4
|
segment[10] = start + 4
|
||||||
return segment
|
return segment
|
||||||
end
|
end
|
||||||
|
|
||||||
--- Kaba Group Header
|
--- Kaba Group Header
|
||||||
-- checks if a segment does have a kghCRC
|
-- checks if a segment does have a kghCRC
|
||||||
-- returns boolean false if no kgh has being detected or the kghCRC if a kgh was detected
|
-- returns boolean false if no kgh has being detected or the kghCRC if a kgh was detected
|
||||||
function CheckKgh(bytes, segStart, segEnd)
|
local function CheckKgh(bytes, segStart, segEnd)
|
||||||
if (bytes[8]=='9f' and bytes[9]=='ff' and bytes[13]=='11') then
|
if (bytes[8] == '9f' and bytes[9] == 'ff' and bytes[13] == '11') then
|
||||||
local i
|
local i
|
||||||
local data = {}
|
local data = {}
|
||||||
segStart = tonumber(segStart, 10)
|
segStart = tonumber(segStart, 10)
|
||||||
segEnd = tonumber(segEnd, 10)
|
segEnd = tonumber(segEnd, 10)
|
||||||
local dataLen = segEnd-segStart-5
|
local dataLen = segEnd - segStart - 5
|
||||||
--- gather creadentials for verify
|
--- gather creadentials for verify
|
||||||
local WRP = bytes[(segStart+2)]
|
local WRP = bytes[(segStart + 2)]
|
||||||
local WRC = ("%02x"):format(tonumber(bit32.extract("0x"..bytes[segStart+3],4,3),16))
|
local WRC = ("%02x"):format(tonumber(bit32.extract("0x"..bytes[segStart+3], 4, 3), 16))
|
||||||
local RD = ("%02x"):format(tonumber(bit32.extract("0x"..bytes[segStart+3],7,1),16))
|
local RD = ("%02x"):format(tonumber(bit32.extract("0x"..bytes[segStart+3], 7, 1), 16))
|
||||||
local XX = "00"
|
local XX = "00"
|
||||||
cmd = bytes[1]..bytes[2]..bytes[3]..bytes[4]..WRP..WRC..RD..XX
|
cmd = bytes[1]..bytes[2]..bytes[3]..bytes[4]..WRP..WRC..RD..XX
|
||||||
for i = (segStart+5), (segStart+5+dataLen-2) do
|
for i = (segStart + 5), (segStart + 5 + dataLen - 2) do
|
||||||
cmd = cmd..bytes[i]
|
cmd = cmd..bytes[i]
|
||||||
end
|
end
|
||||||
local KGH = ("%02x"):format(utils.Crc8Legic(cmd))
|
local KGH = ("%02x"):format(utils.Crc8Legic(cmd))
|
||||||
if (KGH == bytes[segEnd-1]) then
|
if (KGH == bytes[segEnd - 1]) then
|
||||||
return KGH
|
return KGH
|
||||||
else
|
else
|
||||||
return false
|
return false
|
||||||
|
@ -304,12 +318,12 @@ function CheckKgh(bytes, segStart, segEnd)
|
||||||
end
|
end
|
||||||
|
|
||||||
-- get only the addresses of segemnt-crc's and the length of bytes
|
-- get only the addresses of segemnt-crc's and the length of bytes
|
||||||
function getSegmentCrcBytes(bytes)
|
local function getSegmentCrcBytes(bytes)
|
||||||
local start = 23
|
local start = 23
|
||||||
local index = 0
|
local index = 0
|
||||||
local crcbytes = {}
|
local crcbytes = {}
|
||||||
repeat
|
repeat
|
||||||
seg = getSegmentData(bytes,start,index)
|
seg = getSegmentData(bytes, start, index)
|
||||||
crcbytes[index] = seg[10]
|
crcbytes[index] = seg[10]
|
||||||
start = start + seg[4]
|
start = start + seg[4]
|
||||||
index = index + 1
|
index = index + 1
|
||||||
|
@ -318,59 +332,8 @@ function getSegmentCrcBytes(bytes)
|
||||||
return crcbytes
|
return crcbytes
|
||||||
end
|
end
|
||||||
|
|
||||||
-- print segment-data (hf legic decode like)
|
|
||||||
function displaySegments(bytes)
|
|
||||||
--display segment header(s)
|
|
||||||
start = 23
|
|
||||||
index = '00'
|
|
||||||
|
|
||||||
--repeat until last-flag ist set to 1 or segment-index has reached 126
|
|
||||||
repeat
|
|
||||||
wrc = ''
|
|
||||||
wrp = ''
|
|
||||||
pld = ''
|
|
||||||
Seg = getSegmentData(bytes, start, index)
|
|
||||||
KGH = CheckKgh(bytes, start, (start+tonumber(Seg[4],10)))
|
|
||||||
printSegment(Seg)
|
|
||||||
|
|
||||||
-- wrc
|
|
||||||
if (Seg[6] > 0) then
|
|
||||||
print("WRC protected area:")
|
|
||||||
-- length of wrc = wrc
|
|
||||||
for i=1, Seg[6] do
|
|
||||||
-- starts at (segment-start + segment-header + segment-crc)-1
|
|
||||||
wrc = wrc..bytes[(start+4+1+i)-1]..' '
|
|
||||||
end
|
|
||||||
print(wrc)
|
|
||||||
elseif (Seg[5] > 0) then
|
|
||||||
print("Remaining write protected area:")
|
|
||||||
-- length of wrp = (wrp-wrc)
|
|
||||||
for i=1, (Seg[5]-Seg[6]) do
|
|
||||||
-- starts at (segment-start + segment-header + segment-crc + wrc)-1
|
|
||||||
wrp = wrp..bytes[(start+4+1+Seg[6]+i)-1]..' '
|
|
||||||
end
|
|
||||||
print(wrp)
|
|
||||||
end
|
|
||||||
|
|
||||||
-- payload
|
|
||||||
print("Remaining segment payload:")
|
|
||||||
--length of payload = segment-len - segment-header - segment-crc - wrp -wrc
|
|
||||||
for i=1, (Seg[4]-4-1-Seg[5]-Seg[6]) do
|
|
||||||
-- starts at (segment-start + segment-header + segment-crc + segment-wrp + segemnt-wrc)-1
|
|
||||||
pld = pld..bytes[(start+4+1+Seg[5]+Seg[6]+i)-1]..' '
|
|
||||||
end
|
|
||||||
print(pld)
|
|
||||||
if (KGH) then
|
|
||||||
print("'Kaba Group Header' detected")
|
|
||||||
end
|
|
||||||
start = start+Seg[4]
|
|
||||||
index = prepend_zero(tonumber(Seg[9])+1)
|
|
||||||
|
|
||||||
until (Seg[3] == 1 or tonumber(Seg[9]) == 126 )
|
|
||||||
end
|
|
||||||
|
|
||||||
-- print Segment values
|
-- print Segment values
|
||||||
function printSegment(SegmentData)
|
local function printSegment(SegmentData)
|
||||||
res = "\nSegment "..SegmentData[9]..": "
|
res = "\nSegment "..SegmentData[9]..": "
|
||||||
res = res.. "raw header="..SegmentData[0]..", "
|
res = res.. "raw header="..SegmentData[0]..", "
|
||||||
res = res.. "flag="..SegmentData[1].." (valid="..SegmentData[2].." last="..SegmentData[3].."), "
|
res = res.. "flag="..SegmentData[1].." (valid="..SegmentData[2].." last="..SegmentData[3].."), "
|
||||||
|
@ -382,42 +345,100 @@ function printSegment(SegmentData)
|
||||||
print(res)
|
print(res)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
-- print segment-data (hf legic info like)
|
||||||
|
local function displaySegments(bytes)
|
||||||
|
|
||||||
|
--display segment header(s)
|
||||||
|
start = 23
|
||||||
|
index = '00'
|
||||||
|
|
||||||
|
--repeat until last-flag ist set to 1 or segment-index has reached 126
|
||||||
|
repeat
|
||||||
|
wrc = ''
|
||||||
|
wrp = ''
|
||||||
|
pld = ''
|
||||||
|
Seg = getSegmentData(bytes, start, index)
|
||||||
|
if Seg == nil then return OOps("segment is nil") end
|
||||||
|
|
||||||
|
KGH = CheckKgh(bytes, start, (start + tonumber(Seg[4], 10)))
|
||||||
|
|
||||||
|
printSegment(Seg)
|
||||||
|
|
||||||
|
-- wrc
|
||||||
|
if (Seg[6] > 0) then
|
||||||
|
print("WRC protected area:")
|
||||||
|
-- length of wrc = wrc
|
||||||
|
for i = 1, Seg[6] do
|
||||||
|
-- starts at (segment-start + segment-header + segment-crc)-1
|
||||||
|
wrc = wrc..bytes[(start + 4 + 1 + i) - 1]..' '
|
||||||
|
end
|
||||||
|
print(wrc)
|
||||||
|
elseif (Seg[5] > 0) then
|
||||||
|
print("Remaining write protected area:")
|
||||||
|
-- length of wrp = (wrp-wrc)
|
||||||
|
for i = 1, (Seg[5] - Seg[6]) do
|
||||||
|
-- starts at (segment-start + segment-header + segment-crc + wrc)-1
|
||||||
|
wrp = wrp..bytes[(start + 4 + 1 + Seg[6] + i) - 1]..' '
|
||||||
|
end
|
||||||
|
print(wrp)
|
||||||
|
end
|
||||||
|
|
||||||
|
-- payload
|
||||||
|
print("Remaining segment payload:")
|
||||||
|
--length of payload = segment-len - segment-header - segment-crc - wrp -wrc
|
||||||
|
for i = 1, (Seg[4] - 4 - 1 - Seg[5] - Seg[6]) do
|
||||||
|
-- starts at (segment-start + segment-header + segment-crc + segment-wrp + segemnt-wrc)-1
|
||||||
|
pld = pld..bytes[(start + 4 + 1 + Seg[5] + Seg[6] + i) - 1]..' '
|
||||||
|
end
|
||||||
|
print(pld)
|
||||||
|
if (KGH) then
|
||||||
|
print(ansicolors.yellow.."'Kaba Group Header' detected"..ansicolors.reset)
|
||||||
|
end
|
||||||
|
start = start + Seg[4]
|
||||||
|
index = prepend_zero(tonumber(Seg[9]) + 1)
|
||||||
|
|
||||||
|
until (Seg[3] == 1 or tonumber(Seg[9]) == 126 )
|
||||||
|
end
|
||||||
|
|
||||||
-- write clone-data to tag
|
-- write clone-data to tag
|
||||||
function writeToTag(plainBytes)
|
local function writeToTag(plainBytes)
|
||||||
local SegCrcs = {}
|
local SegCrcs = {}
|
||||||
if(utils.confirm("\nplace your empty tag onto the PM3 to read and display the MCD & MSN0..2\nthe values will be shown below\n confirm when ready") == false) then
|
local output
|
||||||
return
|
local readbytes
|
||||||
end
|
if (utils.confirm("\nplace your empty tag onto the PM3 to restore the data of the input file\nthe CRCs will be calculated as needed\n confirm when ready") == false) then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
|
readbytes = readlegicdata(0, 4, 0x55)
|
||||||
-- gather MCD & MSN from new Tag - this must be enterd manually
|
-- gather MCD & MSN from new Tag - this must be enterd manually
|
||||||
cmd = 'hf legic read 0x00 0x04'
|
|
||||||
core.console(cmd)
|
|
||||||
print("\nthese are the MCD MSN0 MSN1 MSN2 from the Tag that has being read:")
|
print("\nthese are the MCD MSN0 MSN1 MSN2 from the Tag that has being read:")
|
||||||
cmd = 'data hexsamples 4'
|
|
||||||
core.console(cmd)
|
|
||||||
print("^^ use this values as input for the following answers (one 2-digit-value per question/answer):")
|
|
||||||
-- enter MCD & MSN (in hex)
|
|
||||||
MCD = utils.input("type in MCD as 2-digit value - e.g.: 00", plainBytes[1])
|
|
||||||
MSN0 = utils.input("type in MSN0 as 2-digit value - e.g.: 01", plainBytes[2])
|
|
||||||
MSN1 = utils.input("type in MSN1 as 2-digit value - e.g.: 02", plainBytes[3])
|
|
||||||
MSN2 = utils.input("type in MSN2 as 2-digit value - e.g.: 03", plainBytes[4])
|
|
||||||
|
|
||||||
|
-- readbytes is a usbcommandOLD package, hence 32 bytes offset until data.
|
||||||
|
plainBytes[1] = ('%02x'):format(readbytes:byte(33))
|
||||||
|
plainBytes[2] = ('%02x'):format(readbytes:byte(34))
|
||||||
|
plainBytes[3] = ('%02x'):format(readbytes:byte(35))
|
||||||
|
plainBytes[4] = ('%02x'):format(readbytes:byte(36))
|
||||||
|
|
||||||
|
MCD = plainBytes[1]
|
||||||
|
MSN0 = plainBytes[2]
|
||||||
|
MSN1 = plainBytes[3]
|
||||||
|
MSN2 = plainBytes[4]
|
||||||
-- calculate crc8 over MCD & MSN
|
-- calculate crc8 over MCD & MSN
|
||||||
cmd = MCD..MSN0..MSN1..MSN2
|
cmd = MCD..MSN0..MSN1..MSN2
|
||||||
MCC = ("%02x"):format(utils.Crc8Legic(cmd))
|
MCC = ("%02x"):format(utils.Crc8Legic(cmd))
|
||||||
print("MCD:"..MCD..", MSN:"..MSN0.." "..MSN1.." "..MSN2..", MCC:"..MCC)
|
print("MCD:"..ansicolors.green..MCD..ansicolors.reset..", MSN:"..ansicolors.green..MSN0.." "..MSN1.." "..MSN2..ansicolors.reset..", MCC:"..MCC)
|
||||||
|
|
||||||
-- calculate new Segment-CRC for each valid segment
|
-- calculate new Segment-CRC for each valid segment
|
||||||
SegCrcs = getSegmentCrcBytes(plainBytes)
|
SegCrcs = getSegmentCrcBytes(plainBytes)
|
||||||
for i=0, (#SegCrcs-1) do
|
for i = 0, (#SegCrcs - 1) do
|
||||||
-- SegCrcs[i]-4 = address of first byte of segmentHeader (low byte segment-length)
|
-- SegCrcs[i]-4 = address of first byte of segmentHeader (low byte segment-length)
|
||||||
segLen = tonumber(("%1x"):format(tonumber(bit32.extract("0x"..plainBytes[(SegCrcs[i]-3)],0,3),16))..("%02x"):format(tonumber(plainBytes[SegCrcs[i]-4],16)),16)
|
segLen = tonumber(("%1x"):format(tonumber(bit32.extract("0x"..plainBytes[(SegCrcs[i] - 3)], 0, 3), 16))..("%02x"):format(tonumber(plainBytes[SegCrcs[i] - 4], 16)), 16)
|
||||||
segStart = (SegCrcs[i]-4)
|
segStart = (SegCrcs[i] - 4)
|
||||||
segEnd = (SegCrcs[i]-4+segLen)
|
segEnd = (SegCrcs[i] - 4 + segLen)
|
||||||
KGH = CheckKgh(plainBytes,segStart,segEnd)
|
KGH = CheckKgh(plainBytes, segStart, segEnd)
|
||||||
if (KGH) then
|
if (KGH) then
|
||||||
print("'Kaba Group Header' detected - re-calculate...")
|
print("'Kaba Group Header' detected - re-calculate...")
|
||||||
end
|
end
|
||||||
cmd = MCD..MSN0..MSN1..MSN2..plainBytes[SegCrcs[i]-4]..plainBytes[SegCrcs[i]-3]..plainBytes[SegCrcs[i]-2]..plainBytes[SegCrcs[i]-1]
|
cmd = MCD..MSN0..MSN1..MSN2..plainBytes[SegCrcs[i]-4]..plainBytes[SegCrcs[i]-3]..plainBytes[SegCrcs[i]-2]..plainBytes[SegCrcs[i]-1]
|
||||||
plainBytes[SegCrcs[i]] = ("%02x"):format(utils.Crc8Legic(cmd))
|
plainBytes[SegCrcs[i]] = ("%02x"):format(utils.Crc8Legic(cmd))
|
||||||
end
|
end
|
||||||
|
@ -433,32 +454,15 @@ function writeToTag(plainBytes)
|
||||||
bytes = xorBytes(plainBytes, MCC)
|
bytes = xorBytes(plainBytes, MCC)
|
||||||
|
|
||||||
-- write data to file
|
-- write data to file
|
||||||
if (writeOutputBytes(bytes, "myLegicClone.hex")) then
|
if (writeOutputBytes(bytes, "hf-legic-UID-dump.bin")) then
|
||||||
WriteBytes = utils.input("enter number of bytes to write?", SegCrcs[#SegCrcs])
|
|
||||||
|
|
||||||
-- load file into pm3-buffer
|
|
||||||
cmd = 'hf legic eload myLegicClone.hex'
|
|
||||||
core.console(cmd)
|
|
||||||
|
|
||||||
-- write pm3-buffer to Tag
|
-- write pm3-buffer to Tag
|
||||||
for i=0, WriteBytes do
|
cmd = ('hf legic restore f hf-legic-UID-dump')
|
||||||
if ( i<5 or i>6) then
|
core.console(cmd)
|
||||||
cmd = ('hf legic write o %02x d 01'):format(i)
|
|
||||||
core.console(cmd)
|
|
||||||
elseif (i == 6) then
|
|
||||||
-- write DCF in reverse order (requires 'mosci-patch')
|
|
||||||
cmd = 'hf legic write o 05 d 02'
|
|
||||||
core.console(cmd)
|
|
||||||
else
|
|
||||||
print("skipping byte 0x05 - will be written next step")
|
|
||||||
end
|
|
||||||
utils.Sleep(0.2)
|
|
||||||
end
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
-- main function
|
-- main function
|
||||||
function main(args)
|
local function main(args)
|
||||||
-- some variables
|
-- some variables
|
||||||
local i = 0
|
local i = 0
|
||||||
local oldcrc, newcrc, infile, outfile
|
local oldcrc, newcrc, infile, outfile
|
||||||
|
@ -473,25 +477,24 @@ function main(args)
|
||||||
ofs = true
|
ofs = true
|
||||||
if (file_check(a)) then
|
if (file_check(a)) then
|
||||||
local answer = utils.confirm('\nthe output-file '..a..' already exists!\nthis will delete the previous content!\ncontinue?')
|
local answer = utils.confirm('\nthe output-file '..a..' already exists!\nthis will delete the previous content!\ncontinue?')
|
||||||
if (answer==false) then return oops('quiting') end
|
if (answer == false) then return oops('quiting') end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
-- input file
|
-- input file
|
||||||
if o == 'i' then
|
if o == 'i' then
|
||||||
infile = a
|
infile = a
|
||||||
if (file_check(infile)==false) then
|
if (file_check(infile) == false) then return oops('input file: '..infile..' not found') end
|
||||||
return oops('input file: '..infile..' not found')
|
|
||||||
else
|
bytes = getInputBytes(infile)
|
||||||
bytes = getInputBytes(infile)
|
oldcrc = bytes[5]
|
||||||
oldcrc = bytes[5]
|
ifs = true
|
||||||
ifs = true
|
if (bytes == false) then return oops('couldnt read file') end
|
||||||
if (bytes == false) then return oops('couldnt get input bytes') end
|
|
||||||
end
|
i = i + 1
|
||||||
i = i+1
|
|
||||||
end
|
end
|
||||||
-- new crc
|
-- new crc
|
||||||
if o == 'c' then
|
if o == 'c' then
|
||||||
newcrc = a
|
newcrc = a:lower()
|
||||||
ncs = true
|
ncs = true
|
||||||
end
|
end
|
||||||
-- display segments switch
|
-- display segments switch
|
||||||
|
@ -504,7 +507,7 @@ function main(args)
|
||||||
if o == 'h' then return help() end
|
if o == 'h' then return help() end
|
||||||
end
|
end
|
||||||
|
|
||||||
if (not ifs) then return oops('option -i <input file> is required but missing') end
|
if (not ifs) then return oops('option -i <input file> is required') end
|
||||||
|
|
||||||
-- bytes to plain
|
-- bytes to plain
|
||||||
bytes = xorBytes(bytes, oldcrc)
|
bytes = xorBytes(bytes, oldcrc)
|
||||||
|
@ -525,13 +528,15 @@ function main(args)
|
||||||
-- information
|
-- information
|
||||||
res = "\n+-------------------------------------------- Summary -------------------------------------------+"
|
res = "\n+-------------------------------------------- Summary -------------------------------------------+"
|
||||||
res = res .."\ncreated clone_dump from\n\t"..infile.." crc: "..oldcrc.."\ndump_file:"
|
res = res .."\ncreated clone_dump from\n\t"..infile.." crc: "..oldcrc.."\ndump_file:"
|
||||||
res = res .."\n\t"..outfile.." crc: "..string.sub(newcrc,-2)
|
res = res .."\n\t"..outfile.." crc: "..string.sub(newcrc, -2)
|
||||||
res = res .."\nyou may load the new file with: hf legic load "..outfile
|
res = res .."\nyou may load the new file with:"
|
||||||
|
res = res ..ansicolors.yellow.."hf legic eload f "..outfile..ansicolors.reset
|
||||||
res = res .."\n\nif you don't write to tag immediately ('-w' switch) you will need to recalculate each segmentCRC"
|
res = res .."\n\nif you don't write to tag immediately ('-w' switch) you will need to recalculate each segmentCRC"
|
||||||
res = res .."\nafter writing this dump to a tag!"
|
res = res .."\nafter writing this dump to a tag!"
|
||||||
res = res .."\n\na segmentCRC gets calculated over MCD,MSN0..3,Segment-Header0..3"
|
res = res .."\n\na segmentCRC gets calculated over MCD,MSN0..3, Segment-Header0..3"
|
||||||
res = res .."\ne.g. (based on Segment00 of the data from "..infile.."):"
|
res = res .."\ne.g. (based on Segment00 of the data from "..infile.."):"
|
||||||
res = res .."\nhf legic crc8 "..bytes[1]..bytes[2]..bytes[3]..bytes[4]..bytes[23]..bytes[24]..bytes[25]..bytes[26]
|
res = res .."\n"
|
||||||
|
res = res ..ansicolors.yellow.."hf legic crc d "..bytes[1]..bytes[2]..bytes[3]..bytes[4]..bytes[23]..bytes[24]..bytes[25]..bytes[26].." u "..newcrc.." c 8"..ansicolors.reset
|
||||||
-- this can not be calculated without knowing the new MCD, MSN0..2
|
-- this can not be calculated without knowing the new MCD, MSN0..2
|
||||||
print(res)
|
print(res)
|
||||||
end
|
end
|
||||||
|
@ -545,8 +550,8 @@ function main(args)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
-- write to tag
|
-- write to tag
|
||||||
if (ws and #bytes == 1024) then
|
if (ws and ( #bytes == 1024 or #bytes == 256)) then
|
||||||
writeToTag(bytes)
|
writeToTag(bytes)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,10 +3,11 @@
|
||||||
-- Updated 2017-04-18
|
-- Updated 2017-04-18
|
||||||
-- Updated 2018-02-20 iceman
|
-- Updated 2018-02-20 iceman
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = "Brian Redbeard"
|
author = "Brian Redbeard"
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = [[
|
desc = [[
|
||||||
Perform bulk enrollment of 26 bit H10301 style RFID Tags
|
Perform bulk enrollment of 26 bit H10301 style RFID Tags
|
||||||
For more info, check the comments in the code
|
For more info, check the comments in the code
|
||||||
|
@ -17,8 +18,8 @@ example = [[
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run lf_bulk.lua -f facility -b base_id_num -c count
|
script run lf_bulk.lua -f facility -b base_id_num -c count
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
-f : facility id
|
-f : facility id
|
||||||
-b : starting card id
|
-b : starting card id
|
||||||
|
@ -56,9 +57,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
---
|
---
|
||||||
-- Exit message
|
-- Exit message
|
||||||
|
|
|
@ -2,10 +2,11 @@ local cmds = require('commands')
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local lib14a = require('read14a')
|
local lib14a = require('read14a')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Kevin'
|
author = 'Kevin'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = [[
|
desc = [[
|
||||||
This is a script that reads LTO-CM ISO14443a tags.
|
This is a script that reads LTO-CM ISO14443a tags.
|
||||||
It starts from block 0 and ends at default block 254.
|
It starts from block 0 and ends at default block 254.
|
||||||
|
@ -19,8 +20,8 @@ example = [[
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run lto_dump -h -s -e
|
script run lto_dump -h -s -e
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
h this helptext
|
h this helptext
|
||||||
s start block in decimal
|
s start block in decimal
|
||||||
e end block in decimal
|
e end block in decimal
|
||||||
|
@ -58,9 +59,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
|
|
||||||
local function sendRaw(rawdata, options)
|
local function sendRaw(rawdata, options)
|
||||||
|
|
|
@ -12,9 +12,9 @@ local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = '0xdrrb'
|
author = '0xdrrb'
|
||||||
version = 'v0.1.0'
|
version = 'v0.1.1'
|
||||||
desc = [[
|
desc = [[
|
||||||
This is a script to dump and decrypt the data of a specific type of Mifare laundromat token.
|
This is a script that tries to dump and decrypt the data of a specific type of Mifare laundromat token. OBS! Tag must be on the antenna.
|
||||||
]]
|
]]
|
||||||
example = [[
|
example = [[
|
||||||
script run luxeodump
|
script run luxeodump
|
||||||
|
@ -22,7 +22,9 @@ example = [[
|
||||||
usage = [[
|
usage = [[
|
||||||
script run luxeodump
|
script run luxeodump
|
||||||
]]
|
]]
|
||||||
|
arguments = [[
|
||||||
|
-h This help
|
||||||
|
]]
|
||||||
local PM3_SUCCESS = 0
|
local PM3_SUCCESS = 0
|
||||||
|
|
||||||
-- Some shortcuts
|
-- Some shortcuts
|
||||||
|
@ -48,7 +50,22 @@ local function oops(err)
|
||||||
core.clearCommandBuffer()
|
core.clearCommandBuffer()
|
||||||
return nil, err
|
return nil, err
|
||||||
end
|
end
|
||||||
|
---
|
||||||
|
-- Usage help
|
||||||
|
local function help()
|
||||||
|
print(copyright)
|
||||||
|
print(author)
|
||||||
|
print(version)
|
||||||
|
print(desc)
|
||||||
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
|
end
|
||||||
|
---
|
||||||
|
--
|
||||||
local function setdevicedebug( status )
|
local function setdevicedebug( status )
|
||||||
local c = 'hw dbg '
|
local c = 'hw dbg '
|
||||||
if status then
|
if status then
|
||||||
|
@ -72,8 +89,8 @@ local function xteaCrypt(num_rounds, v, key)
|
||||||
-- v1 += (((v0 << 4) ^ (v0 >> 5)) + v0) ^ (sum + key[(sum>>11) & 3]);
|
-- v1 += (((v0 << 4) ^ (v0 >> 5)) + v0) ^ (sum + key[(sum>>11) & 3]);
|
||||||
v1 = band(bxor(bxor(lsh(v0,4), rsh(v0,5)) + v0, sum + key[band(rsh(sum,11),3)]) + v1, 0xFFFFFFFF)
|
v1 = band(bxor(bxor(lsh(v0,4), rsh(v0,5)) + v0, sum + key[band(rsh(sum,11),3)]) + v1, 0xFFFFFFFF)
|
||||||
end
|
end
|
||||||
v[0]=v0
|
v[0] = v0
|
||||||
v[1]=v1
|
v[1] = v1
|
||||||
end
|
end
|
||||||
|
|
||||||
local function xteaDecrypt(num_rounds, v, key)
|
local function xteaDecrypt(num_rounds, v, key)
|
||||||
|
@ -89,8 +106,8 @@ local function xteaDecrypt(num_rounds, v, key)
|
||||||
-- v0 -= (((v1 << 4) ^ (v1 >> 5)) + v1) ^ (sum + key[sum & 3]);
|
-- v0 -= (((v1 << 4) ^ (v1 >> 5)) + v1) ^ (sum + key[sum & 3]);
|
||||||
v0 = band(v0 - bxor(bxor(lsh(v1,4), rsh(v1,5)) + v1, sum + key[band(sum,3)]), 0xFFFFFFFF)
|
v0 = band(v0 - bxor(bxor(lsh(v1,4), rsh(v1,5)) + v1, sum + key[band(sum,3)]), 0xFFFFFFFF)
|
||||||
end
|
end
|
||||||
v[0]=v0
|
v[0] = v0
|
||||||
v[1]=v1
|
v[1] = v1
|
||||||
end
|
end
|
||||||
|
|
||||||
local function createxteakey(mfuid)
|
local function createxteakey(mfuid)
|
||||||
|
@ -150,7 +167,7 @@ local function readtag(mfkey,xteakey)
|
||||||
|
|
||||||
-- Read 4 sectors and build table
|
-- Read 4 sectors and build table
|
||||||
for sect = 8, 11 do
|
for sect = 8, 11 do
|
||||||
for blockn = sect*4, (sect*4)+2 do
|
for blockn = sect * 4, (sect * 4) + 2 do
|
||||||
local blockdata = readblock(blockn, mfkey)
|
local blockdata = readblock(blockn, mfkey)
|
||||||
if not blockdata then return oops('[!] failed reading block') end
|
if not blockdata then return oops('[!] failed reading block') end
|
||||||
table.insert(tagdata, blockdata)
|
table.insert(tagdata, blockdata)
|
||||||
|
@ -160,17 +177,17 @@ local function readtag(mfkey,xteakey)
|
||||||
-- Decrypt data and build clear table
|
-- Decrypt data and build clear table
|
||||||
for key,value in ipairs(tagdata) do
|
for key,value in ipairs(tagdata) do
|
||||||
local clearblockdata
|
local clearblockdata
|
||||||
v[0]=utils.SwapEndianness(value:sub(1,8),32)
|
v[0] = utils.SwapEndianness(value:sub(1, 8), 32)
|
||||||
v[1]=utils.SwapEndianness(value:sub(9,16),32)
|
v[1] = utils.SwapEndianness(value:sub(9, 16), 32)
|
||||||
xteaDecrypt(16, v, xteakey)
|
xteaDecrypt(16, v, xteakey)
|
||||||
vv[0]=utils.SwapEndianness(value:sub(17,24),32)
|
vv[0] = utils.SwapEndianness(value:sub(17, 24), 32)
|
||||||
vv[1]=utils.SwapEndianness(value:sub(25,32),32)
|
vv[1] = utils.SwapEndianness(value:sub(25, 32), 32)
|
||||||
xteaDecrypt(16, vv, xteakey)
|
xteaDecrypt(16, vv, xteakey)
|
||||||
clearblockdata=string.format("%08X%08X%08X%08X",
|
clearblockdata=string.format("%08X%08X%08X%08X",
|
||||||
utils.SwapEndianness(string.format("%08X", v[0]),32),
|
utils.SwapEndianness(string.format("%08X", v[0]), 32),
|
||||||
utils.SwapEndianness(string.format("%08X", v[1]),32),
|
utils.SwapEndianness(string.format("%08X", v[1]), 32),
|
||||||
utils.SwapEndianness(string.format("%08X", vv[0]),32),
|
utils.SwapEndianness(string.format("%08X", vv[0]), 32),
|
||||||
utils.SwapEndianness(string.format("%08X", vv[1]),32))
|
utils.SwapEndianness(string.format("%08X", vv[1]), 32))
|
||||||
table.insert(cleardata, clearblockdata)
|
table.insert(cleardata, clearblockdata)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -180,6 +197,12 @@ end
|
||||||
|
|
||||||
|
|
||||||
local function main(args)
|
local function main(args)
|
||||||
|
|
||||||
|
-- Arguments for the script
|
||||||
|
for o, a in getopt.getopt(args, 'h') do
|
||||||
|
if o == 'h' then return help() end
|
||||||
|
end
|
||||||
|
|
||||||
local xteakey = {}
|
local xteakey = {}
|
||||||
-- local v = {}
|
-- local v = {}
|
||||||
local edata = {}
|
local edata = {}
|
||||||
|
@ -207,7 +230,7 @@ local function main(args)
|
||||||
print(acblue.."UID: "..tag.uid..acoff)
|
print(acblue.."UID: "..tag.uid..acoff)
|
||||||
print(acblue..string.format("XTEA key: %08X %08X %08X %08X", xteakey[0], xteakey[1], xteakey[2], xteakey[3])..acoff)
|
print(acblue..string.format("XTEA key: %08X %08X %08X %08X", xteakey[0], xteakey[1], xteakey[2], xteakey[3])..acoff)
|
||||||
|
|
||||||
edata, cdata = readtag("415A54454B4D",xteakey)
|
edata, cdata = readtag("415A54454B4D", xteakey)
|
||||||
|
|
||||||
if edata == nil or cdata == nil then
|
if edata == nil or cdata == nil then
|
||||||
print("ERROR Reading tag!")
|
print("ERROR Reading tag!")
|
||||||
|
|
|
@ -13,10 +13,11 @@ local keylist = require('mfc_default_keys')
|
||||||
local lib14a = require('read14a')
|
local lib14a = require('read14a')
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = "Holiman"
|
author = "Holiman"
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = ("This script implements Mifare check keys.\
|
desc = ("This script implements Mifare check keys.\
|
||||||
It utilises a large list of default keys (currently %d keys).\
|
It utilises a large list of default keys (currently %d keys).\
|
||||||
If you want to add more, just put them inside /lualibs/mfc_default_keys.lua\n"):format(#keylist)
|
If you want to add more, just put them inside /lualibs/mfc_default_keys.lua\n"):format(#keylist)
|
||||||
|
@ -24,7 +25,9 @@ example = [[
|
||||||
1. script run mfckeys
|
1. script run mfckeys
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
Arguments:
|
script run mfckeys [-p]
|
||||||
|
]]
|
||||||
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
-p : print keys
|
-p : print keys
|
||||||
]]
|
]]
|
||||||
|
@ -46,9 +49,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
-- waits for answer from pm3 device
|
-- waits for answer from pm3 device
|
||||||
|
@ -269,8 +275,6 @@ end
|
||||||
-- The main entry point
|
-- The main entry point
|
||||||
local function main(args)
|
local function main(args)
|
||||||
|
|
||||||
local numSectors = 16
|
|
||||||
|
|
||||||
-- Arguments for the script
|
-- Arguments for the script
|
||||||
for o, a in getopt.getopt(args, 'hp') do
|
for o, a in getopt.getopt(args, 'hp') do
|
||||||
if o == 'h' then return help() end
|
if o == 'h' then return help() end
|
||||||
|
@ -280,6 +284,8 @@ local function main(args)
|
||||||
tag, err = lib14a.read(false, true)
|
tag, err = lib14a.read(false, true)
|
||||||
if not tag then return oops(err) end
|
if not tag then return oops(err) end
|
||||||
|
|
||||||
|
local numSectors = 16
|
||||||
|
|
||||||
-- detect sectors and print taginfo
|
-- detect sectors and print taginfo
|
||||||
numsectors = taginfo(tag)
|
numsectors = taginfo(tag)
|
||||||
|
|
||||||
|
|
|
@ -2,6 +2,7 @@ local cmds = require('commands')
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local lib14a = require('read14a')
|
local lib14a = require('read14a')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
-- global
|
-- global
|
||||||
local DEBUG = false -- the debug flag
|
local DEBUG = false -- the debug flag
|
||||||
|
@ -11,10 +12,9 @@ local err_lock = 'use -k or change cfg0 block'
|
||||||
|
|
||||||
copyright = 'Copyright (c) 2017 IceSQL AB. All rights reserved.'
|
copyright = 'Copyright (c) 2017 IceSQL AB. All rights reserved.'
|
||||||
author = 'Christian Herrmann'
|
author = 'Christian Herrmann'
|
||||||
version = 'v1.1.2'
|
version = 'v1.1.3'
|
||||||
desc = 'This script enables easy programming of a MAGIC NTAG 21* card'
|
desc = 'This script enables easy programming of a MAGIC NTAG 21* card'
|
||||||
example =
|
example = [[
|
||||||
[[
|
|
||||||
-- wipe tag
|
-- wipe tag
|
||||||
script run mfu_magic -w
|
script run mfu_magic -w
|
||||||
|
|
||||||
|
@ -36,12 +36,10 @@ example =
|
||||||
-- set signature
|
-- set signature
|
||||||
script run mfu_magic -s 1122334455667788990011223344556677889900112233445566778899001122
|
script run mfu_magic -s 1122334455667788990011223344556677889900112233445566778899001122
|
||||||
]]
|
]]
|
||||||
usage =
|
usage = [[
|
||||||
[[
|
|
||||||
Usage:
|
|
||||||
script run mfu_magic -h -k <passwd> -c -w -u <uid> -t <type> -p <passwd> -a <pack> -s <signature> -o <otp> -v <version>
|
script run mfu_magic -h -k <passwd> -c -w -u <uid> -t <type> -p <passwd> -a <pack> -s <signature> -o <otp> -v <version>
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h this help
|
-h this help
|
||||||
-c read magic configuration
|
-c read magic configuration
|
||||||
-u UID (14 hexsymbols), set UID on tag
|
-u UID (14 hexsymbols), set UID on tag
|
||||||
|
@ -94,9 +92,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
---
|
---
|
||||||
-- set the global password variable
|
-- set the global password variable
|
||||||
|
|
|
@ -1,8 +1,9 @@
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = "Neuromancer"
|
author = "Neuromancer"
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = [[
|
desc = [[
|
||||||
This script tries to decode Mifare Classic Access bytes
|
This script tries to decode Mifare Classic Access bytes
|
||||||
]]
|
]]
|
||||||
|
@ -10,9 +11,9 @@ example = [[
|
||||||
1. script run mifare_access -a 7F0F0869
|
1. script run mifare_access -a 7F0F0869
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run mifare_access -h -a <access bytes>
|
script run mifare_access [-h] [-a <access bytes>]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
-a <access bytes> : 4 bytes ACCESS CONDITIONS
|
-a <access bytes> : 4 bytes ACCESS CONDITIONS
|
||||||
]]
|
]]
|
||||||
|
@ -50,9 +51,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
|
|
||||||
local access_condition_sector_trailer = {}
|
local access_condition_sector_trailer = {}
|
||||||
|
|
|
@ -2,20 +2,23 @@ local getopt = require('getopt')
|
||||||
local lib14a = require('read14a')
|
local lib14a = require('read14a')
|
||||||
local cmds = require('commands')
|
local cmds = require('commands')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = "Martin Holst Swende"
|
author = "Martin Holst Swende"
|
||||||
version = 'v1.0.2'
|
version = 'v1.0.3'
|
||||||
desc = [[
|
desc = [[
|
||||||
This is a script which automates cracking and dumping mifare classic cards. It sets itself into
|
This is a script which automates cracking and dumping mifare classic cards. It sets itself into
|
||||||
'listening'-mode, after which it cracks and dumps any mifare classic card that you
|
'listening'-mode, after which it cracks and dumps any mifare classic card that you
|
||||||
place by the device.
|
place by the device.
|
||||||
]]
|
]]
|
||||||
example = [[
|
example = [[
|
||||||
script run mifare_autopwn
|
1. script run mifare_autopwn
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
Arguments:
|
script run mifare_autopwn [-h] [-d] [-k <key>]
|
||||||
|
]]
|
||||||
|
arguments = [[
|
||||||
-h this help
|
-h this help
|
||||||
-d debug logging on
|
-d debug logging on
|
||||||
-k known key for Sector 0 , keytype A
|
-k known key for Sector 0 , keytype A
|
||||||
|
@ -61,9 +64,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
---
|
---
|
||||||
-- Waits for a mifare card to be placed within the vicinity of the reader.
|
-- Waits for a mifare card to be placed within the vicinity of the reader.
|
||||||
|
|
|
@ -1,12 +1,12 @@
|
||||||
local cmds = require('commands')
|
local cmds = require('commands')
|
||||||
local lib14a = require('read14a')
|
local lib14a = require('read14a')
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Dominic Celiano'
|
author = 'Dominic Celiano'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc =
|
desc = [[
|
||||||
[[
|
|
||||||
Purpose: Lua script to communicate with the Mifare Plus EV1, including personalization (setting the keys) and proximity check. Manually edit the file to add to the commands you can send the card.
|
Purpose: Lua script to communicate with the Mifare Plus EV1, including personalization (setting the keys) and proximity check. Manually edit the file to add to the commands you can send the card.
|
||||||
Please read the NXP manual before running this script to prevent making irreversible changes. Also note:
|
Please read the NXP manual before running this script to prevent making irreversible changes. Also note:
|
||||||
- The Mifare Plus must start in SL0 for personalization. Card can then be moved to SL1 or SL3.
|
- The Mifare Plus must start in SL0 for personalization. Card can then be moved to SL1 or SL3.
|
||||||
|
@ -15,13 +15,12 @@ Please read the NXP manual before running this script to prevent making irrevers
|
||||||
Small changes can be to made this script to communicate with the Mifare Plus S, X, or SE.
|
Small changes can be to made this script to communicate with the Mifare Plus S, X, or SE.
|
||||||
]]
|
]]
|
||||||
example = [[
|
example = [[
|
||||||
-- default
|
1. script run mifareplus
|
||||||
script run mifareplus
|
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run mifareplus -h
|
script run mifareplus [-h]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
]]
|
]]
|
||||||
|
|
||||||
|
@ -57,9 +56,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
---
|
---
|
||||||
-- Used to send raw data to the firmware to subsequently forward the data to the card.
|
-- Used to send raw data to the firmware to subsequently forward the data to the card.
|
||||||
|
|
|
@ -2,11 +2,12 @@ local getopt = require('getopt')
|
||||||
local cmds = require('commands')
|
local cmds = require('commands')
|
||||||
local lib14a = require('read14a')
|
local lib14a = require('read14a')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
--
|
--
|
||||||
-- Refactored iceman, 2019
|
-- Refactored iceman, 2019
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Martin Holst Swende & Asper'
|
author = 'Martin Holst Swende & Asper'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = [[
|
desc = [[
|
||||||
This script will automatically recognize and dump full content of a NFC NDEF Initialized tag; non-initialized tags will be ignored.
|
This script will automatically recognize and dump full content of a NFC NDEF Initialized tag; non-initialized tags will be ignored.
|
||||||
|
|
||||||
|
@ -23,9 +24,9 @@ example = [[
|
||||||
1. script run ndef_dump
|
1. script run ndef_dump
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run ndef_dump
|
script run ndef_dump [-h] [-d] [-v]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h this help
|
-h this help
|
||||||
-d debug logging on
|
-d debug logging on
|
||||||
-v verbose output (from ndef parsing)
|
-v verbose output (from ndef parsing)
|
||||||
|
@ -63,9 +64,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
-- Sends an instruction to do nothing, only disconnect
|
-- Sends an instruction to do nothing, only disconnect
|
||||||
|
|
|
@ -1,10 +1,11 @@
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local lib14a = require('read14a')
|
local lib14a = require('read14a')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = 'Copyright (c) 2017 IceSQL AB. All rights reserved.'
|
copyright = 'Copyright (c) 2017 IceSQL AB. All rights reserved.'
|
||||||
author = "Christian Herrmann"
|
author = "Christian Herrmann"
|
||||||
version = 'v1.0.4'
|
version = 'v1.0.5'
|
||||||
desc = [[
|
desc = [[
|
||||||
This script writes a empty template for 3D printing system onto a empty NTAG213 or MAGIC NTAG21*
|
This script writes a empty template for 3D printing system onto a empty NTAG213 or MAGIC NTAG21*
|
||||||
|
|
||||||
|
@ -21,9 +22,9 @@ example =[[
|
||||||
script run ntag_3d -u 11223344556677 -c 46 -m 50 -p 5448 -s 4555 -l 200 -1
|
script run ntag_3d -u 11223344556677 -c 46 -m 50 -p 5448 -s 4555 -l 200 -1
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run ntag_3d -h -t -u <uid> -c <color> -m <material> -p <region> -s <region> -l <length>
|
script run ntag_3d [-h] [-t] [-u <uid>] [-c <color>] [-m <material>] [-p <region>] [-s <region>] [-l <length>]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
-t : selftest
|
-t : selftest
|
||||||
-u <UID> : UID
|
-u <UID> : UID
|
||||||
|
@ -168,9 +169,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
-- Exit message
|
-- Exit message
|
||||||
|
|
|
@ -1,19 +1,31 @@
|
||||||
-- The getopt-functionality is loaded from pm3/getopt.lua
|
-- The getopt-functionality is loaded from pm3/getopt.lua
|
||||||
-- Have a look there for further details
|
-- Have a look there for further details
|
||||||
getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
usage = 'script run parameters.lua -a 1 -blala -c -de'
|
usage = 'script run parameters.lua -a 1 -blala -c -de'
|
||||||
author = 'Martin Holst Swende'
|
author = 'Martin Holst Swende'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = [[
|
desc = [[
|
||||||
This is an example script to demonstrate handle parameters in scripts.
|
This is an example script to demonstrate handle parameters in scripts.
|
||||||
For more info, check the comments in the code
|
For more info, check the comments in the code
|
||||||
]]
|
]]
|
||||||
example = [[
|
example = [[
|
||||||
|
1. script run parameters -a mytestparam_input -c
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
|
script run parameters [-h] [-a <txt>] [-b <txt>] [-c] [-d] [-e]
|
||||||
]]
|
]]
|
||||||
|
arguments = [[
|
||||||
|
-h This help
|
||||||
|
-a <txt> text
|
||||||
|
-b <txt> text
|
||||||
|
-c test param w/o input
|
||||||
|
-d test param w/o input
|
||||||
|
-e test param w/o input
|
||||||
|
]]
|
||||||
|
|
||||||
---
|
---
|
||||||
-- Usage help
|
-- Usage help
|
||||||
local function help()
|
local function help()
|
||||||
|
@ -21,9 +33,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
|
|
||||||
local function main(args)
|
local function main(args)
|
||||||
|
|
|
@ -1,11 +1,11 @@
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local bin = require('bin')
|
local bin = require('bin')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = 'Copyright (c) 2018 Bogito. All rights reserved.'
|
copyright = 'Copyright (c) 2018 Bogito. All rights reserved.'
|
||||||
author = 'Bogito'
|
author = 'Bogito'
|
||||||
version = 'v1.0.3'
|
version = 'v1.0.4'
|
||||||
desc =
|
desc = [[
|
||||||
[[
|
|
||||||
This script will read the flash memory of RDV4 and print the stored passwords/keys.
|
This script will read the flash memory of RDV4 and print the stored passwords/keys.
|
||||||
|
|
||||||
It was meant to be used as a help tool after using the BogRun standalone mode before SPIFFS.
|
It was meant to be used as a help tool after using the BogRun standalone mode before SPIFFS.
|
||||||
|
@ -13,8 +13,7 @@ You should now use read_pwd_mem_spiffs instead after the updated BogRun standalo
|
||||||
|
|
||||||
(Iceman) script adapted to read and print keys in the default dictionary flashmemory sections.
|
(Iceman) script adapted to read and print keys in the default dictionary flashmemory sections.
|
||||||
]]
|
]]
|
||||||
example =
|
example = [[
|
||||||
[[
|
|
||||||
-- This will scan the first 256 bytes of flash memory for stored passwords
|
-- This will scan the first 256 bytes of flash memory for stored passwords
|
||||||
script run read_pwd_mem
|
script run read_pwd_mem
|
||||||
|
|
||||||
|
@ -33,12 +32,10 @@ example =
|
||||||
-- This will print the stored iClass dictionary keys
|
-- This will print the stored iClass dictionary keys
|
||||||
script run read_pwd_mem -i
|
script run read_pwd_mem -i
|
||||||
]]
|
]]
|
||||||
usage =
|
usage = [[
|
||||||
[[
|
script run read_pwd_mem [-h] [-o <offset>] [-l <length>] [-k <keylength>] [-m] [-t] [-i]
|
||||||
Usage:
|
]]
|
||||||
script run read_pwd_mem -h -o <offset> -l <length> -k <keylength>
|
arguments = [[
|
||||||
|
|
||||||
Arguments:
|
|
||||||
-h : this help
|
-h : this help
|
||||||
-o <offset> : memory offset, default is 0
|
-o <offset> : memory offset, default is 0
|
||||||
-l <length> : length in bytes, default is 256
|
-l <length> : length in bytes, default is 256
|
||||||
|
@ -61,9 +58,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
---
|
---
|
||||||
-- The main entry point
|
-- The main entry point
|
||||||
|
|
|
@ -1,16 +1,15 @@
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local bin = require('bin')
|
local bin = require('bin')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = 'Copyright (c) 2019 Bogito. All rights reserved.'
|
copyright = 'Copyright (c) 2019 Bogito. All rights reserved.'
|
||||||
author = 'Bogito'
|
author = 'Bogito'
|
||||||
version = 'v1.1.1'
|
version = 'v1.1.2'
|
||||||
desc =
|
desc = [[
|
||||||
[[
|
|
||||||
This script will read the flash memory of RDV4 using SPIFFS and print the stored passwords.
|
This script will read the flash memory of RDV4 using SPIFFS and print the stored passwords.
|
||||||
It was meant to be used as a help tool after using the BogRun standalone mode.
|
It was meant to be used as a help tool after using the BogRun standalone mode.
|
||||||
]]
|
]]
|
||||||
example =
|
example = [[
|
||||||
[[
|
|
||||||
-- This will read the hf_bog.log file in SPIFFS and print the stored passwords
|
-- This will read the hf_bog.log file in SPIFFS and print the stored passwords
|
||||||
script run read_pwd_mem_spiffs
|
script run read_pwd_mem_spiffs
|
||||||
|
|
||||||
|
@ -20,12 +19,10 @@ example =
|
||||||
-- This will delete the hf_bog.log file from SPIFFS
|
-- This will delete the hf_bog.log file from SPIFFS
|
||||||
script run read_pwd_mem_spiffs -r
|
script run read_pwd_mem_spiffs -r
|
||||||
]]
|
]]
|
||||||
usage =
|
usage = [[
|
||||||
[[
|
script run read_pwd_mem_spiffs [-h] [-f <filename>] [-r]
|
||||||
Usage:
|
]]
|
||||||
script run read_pwd_mem_spiffs -h -f <filename> -r
|
arguments = [[
|
||||||
|
|
||||||
Arguments:
|
|
||||||
-h : this help
|
-h : this help
|
||||||
-f <filename> : filename in SPIFFS
|
-f <filename> : filename in SPIFFS
|
||||||
-r : delete filename from SPIFFS
|
-r : delete filename from SPIFFS
|
||||||
|
@ -44,9 +41,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
---
|
---
|
||||||
-- The main entry point
|
-- The main entry point
|
||||||
|
|
|
@ -1,10 +1,10 @@
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Iceman'
|
author = 'Iceman'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc =
|
desc = [[
|
||||||
[[
|
|
||||||
This is a script that tries to bring back a chinese magic card (1k generation1)
|
This is a script that tries to bring back a chinese magic card (1k generation1)
|
||||||
from the dead when it's block 0 has been written with bad values.
|
from the dead when it's block 0 has been written with bad values.
|
||||||
or mifare Ultralight magic card which answers to chinese backdoor commands
|
or mifare Ultralight magic card which answers to chinese backdoor commands
|
||||||
|
@ -15,9 +15,9 @@ example = [[
|
||||||
|
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run remagic
|
script run remagic [-h] [-u]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h this help
|
-h this help
|
||||||
-u remagic a Ultralight tag w 7 bytes UID.
|
-u remagic a Ultralight tag w 7 bytes UID.
|
||||||
]]
|
]]
|
||||||
|
@ -49,9 +49,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
|
|
||||||
local function cmdUltralight()
|
local function cmdUltralight()
|
||||||
|
|
|
@ -2,13 +2,14 @@ local cmds = require('commands')
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local bin = require('bin')
|
local bin = require('bin')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
local format = string.format
|
local format = string.format
|
||||||
local floor = math.floor
|
local floor = math.floor
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = "Iceman"
|
author = "Iceman"
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc =[[
|
desc =[[
|
||||||
This script will program a T55x7 TAG with a configuration and four blocks of data.
|
This script will program a T55x7 TAG with a configuration and four blocks of data.
|
||||||
It will then try to detect and read back those block data and compare if read data matches the expected data.
|
It will then try to detect and read back those block data and compare if read data matches the expected data.
|
||||||
|
@ -32,10 +33,9 @@ example = [[
|
||||||
1. script run test_t55x7
|
1. script run test_t55x7
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
|
script run test_t55x7 [-h]
|
||||||
script run test_t55x7
|
]]
|
||||||
|
arguments = [[
|
||||||
Arguments:
|
|
||||||
-h this help
|
-h this help
|
||||||
]]
|
]]
|
||||||
|
|
||||||
|
@ -79,9 +79,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print("Example usage")
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
---
|
---
|
||||||
-- Exit message
|
-- Exit message
|
||||||
|
|
|
@ -2,14 +2,15 @@ local cmds = require('commands')
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local bin = require('bin')
|
local bin = require('bin')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
local format=string.format
|
local format=string.format
|
||||||
local floor=math.floor
|
local floor=math.floor
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Iceman'
|
author = 'Iceman'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc =[[
|
desc = [[
|
||||||
This script will program a T55x7 TAG with the configuration: block 0x00 data 0x000100
|
This script will program a T55x7 TAG with the configuration: block 0x00 data 0x000100
|
||||||
The outlined procedure is as following:
|
The outlined procedure is as following:
|
||||||
|
|
||||||
|
@ -41,9 +42,9 @@ example =[[
|
||||||
1. script run test_t55x7_ask
|
1. script run test_t55x7_ask
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run test_t55x7_ask
|
script run test_t55x7_ask [-h]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
]]
|
]]
|
||||||
|
|
||||||
|
@ -87,9 +88,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
-- Exit message
|
-- Exit message
|
||||||
|
|
|
@ -2,10 +2,11 @@ local cmds = require('commands')
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local bin = require('bin')
|
local bin = require('bin')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Iceman'
|
author = 'Iceman'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = [[
|
desc = [[
|
||||||
This script will program a T55x7 TAG with the configuration: block 0x00 data 0x00010040
|
This script will program a T55x7 TAG with the configuration: block 0x00 data 0x00010040
|
||||||
The outlined procedure is as following:
|
The outlined procedure is as following:
|
||||||
|
@ -35,9 +36,9 @@ example = [[
|
||||||
1. script run test_t55x7_bi
|
1. script run test_t55x7_bi
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run test_t55x7_bi
|
script run test_t55x7_bi [-h]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
]]
|
]]
|
||||||
|
|
||||||
|
@ -81,9 +82,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
-- Exit message
|
-- Exit message
|
||||||
|
|
|
@ -2,10 +2,11 @@ local cmds = require('commands')
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local bin = require('bin')
|
local bin = require('bin')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Iceman'
|
author = 'Iceman'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = [[
|
desc = [[
|
||||||
This script will program a T55x7 TAG with the configuration: block 0x00 data 0x000100
|
This script will program a T55x7 TAG with the configuration: block 0x00 data 0x000100
|
||||||
The outlined procedure is as following:
|
The outlined procedure is as following:
|
||||||
|
@ -37,9 +38,9 @@ example = [[
|
||||||
1. script run test_t55x7_fsk
|
1. script run test_t55x7_fsk
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run test_t55x7_fsk
|
script run test_t55x7_fsk [-h]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
]]
|
]]
|
||||||
|
|
||||||
|
@ -83,9 +84,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
-- Exit message
|
-- Exit message
|
||||||
|
|
|
@ -2,10 +2,11 @@ local cmds = require('commands')
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local bin = require('bin')
|
local bin = require('bin')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Iceman'
|
author = 'Iceman'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = [[
|
desc = [[
|
||||||
This script will program a T55x7 TAG with the configuration: block 0x00 data 0x00088040
|
This script will program a T55x7 TAG with the configuration: block 0x00 data 0x00088040
|
||||||
The outlined procedure is as following:
|
The outlined procedure is as following:
|
||||||
|
@ -33,9 +34,9 @@ example = [[
|
||||||
2. script run test_t55x7_psk -o
|
2. script run test_t55x7_psk -o
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run test_t55x7_psk
|
script run test_t55x7_psk [-h]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
]]
|
]]
|
||||||
|
|
||||||
|
@ -82,9 +83,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
-- Exit message
|
-- Exit message
|
||||||
|
|
|
@ -4,6 +4,7 @@ local lib14a = require('read14a')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
local pre = require('precalc')
|
local pre = require('precalc')
|
||||||
local toys = require('default_toys')
|
local toys = require('default_toys')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
local lsh = bit32.lshift
|
local lsh = bit32.lshift
|
||||||
local rsh = bit32.rshift
|
local rsh = bit32.rshift
|
||||||
|
@ -12,11 +13,11 @@ local band = bit32.band
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = "Iceman"
|
author = "Iceman"
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc =[[
|
desc = [[
|
||||||
This script will try making a barebone clone of a tnp3 tag on to a magic generation1 card.
|
This script will try making a barebone clone of a tnp3 tag on to a magic generation1 card.
|
||||||
]]
|
]]
|
||||||
example =[[
|
example = [[
|
||||||
script run tnp3clone
|
script run tnp3clone
|
||||||
script run tnp3clone -h
|
script run tnp3clone -h
|
||||||
script run tnp3clone -l
|
script run tnp3clone -l
|
||||||
|
@ -24,9 +25,9 @@ example =[[
|
||||||
|
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run tnp3clone -t <toytype> -s <subtype>
|
script run tnp3clone [-h] [-t <toytype>] [-s <subtype>]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
-l : list all known toy tokens
|
-l : list all known toy tokens
|
||||||
-t <data> : toytype id, 4hex symbols
|
-t <data> : toytype id, 4hex symbols
|
||||||
|
@ -56,9 +57,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
---
|
---
|
||||||
-- decode response and get the blockdata from a normal mifare read command
|
-- decode response and get the blockdata from a normal mifare read command
|
||||||
|
|
|
@ -6,11 +6,12 @@ local utils = require('utils')
|
||||||
local md5 = require('md5')
|
local md5 = require('md5')
|
||||||
local dumplib = require('html_dumplib')
|
local dumplib = require('html_dumplib')
|
||||||
local toys = require('default_toys')
|
local toys = require('default_toys')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Iceman'
|
author = 'Iceman'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc =[[
|
desc = [[
|
||||||
This script will try to dump the contents of a Mifare TNP3xxx card.
|
This script will try to dump the contents of a Mifare TNP3xxx card.
|
||||||
It will need a valid KeyA in order to find the other keys and decode the card.
|
It will need a valid KeyA in order to find the other keys and decode the card.
|
||||||
]]
|
]]
|
||||||
|
@ -26,9 +27,9 @@ example = [[
|
||||||
script run tnp3dump -k aabbccddeeff -n -o myfile
|
script run tnp3dump -k aabbccddeeff -n -o myfile
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run tnp3dump -k <key> -n -p -o <filename>
|
script run tnp3dump [-h] [-k <key>] [-n] [-p] [-o <filename>]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
-k <key> : Sector 0 Key A.
|
-k <key> : Sector 0 Key A.
|
||||||
-n : Use the nested cmd to find all keys
|
-n : Use the nested cmd to find all keys
|
||||||
|
@ -69,9 +70,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
-- Exit message
|
-- Exit message
|
||||||
|
|
|
@ -6,25 +6,26 @@ local utils = require('utils')
|
||||||
local md5 = require('md5')
|
local md5 = require('md5')
|
||||||
local toys = require('default_toys')
|
local toys = require('default_toys')
|
||||||
local pre = require('precalc')
|
local pre = require('precalc')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Iceman'
|
author = 'Iceman'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc =[[
|
desc = [[
|
||||||
This script will try to load a binary datadump of a Mifare TNP3xxx card.
|
This script will try to load a binary datadump of a Mifare TNP3xxx card.
|
||||||
It vill try to validate all checksums and view some information stored in the dump
|
It vill try to validate all checksums and view some information stored in the dump
|
||||||
For an experimental mode, it tries to manipulate some data.
|
For an experimental mode, it tries to manipulate some data.
|
||||||
At last it sends all data to the PM3 device memory where it can be used in the command "hf mf sim"
|
At last it sends all data to the PM3 device memory where it can be used in the command "hf mf sim"
|
||||||
]]
|
]]
|
||||||
example =[[
|
example = [[
|
||||||
1. script run tnp3sim
|
1. script run tnp3sim
|
||||||
2. script run tnp3sim -m
|
2. script run tnp3sim -m
|
||||||
3. script run tnp3sim -m -i myfile
|
3. script run tnp3sim -m -i myfile
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run tnp3sim -h -m -i <filename>
|
script run tnp3sim [-h] [-m] [-i <filename>]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
-m : Maxed out items (experimental)
|
-m : Maxed out items (experimental)
|
||||||
-i : filename for the datadump to read (bin)
|
-i : filename for the datadump to read (bin)
|
||||||
|
@ -70,9 +71,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
-- Exit message
|
-- Exit message
|
||||||
|
|
|
@ -3,11 +3,12 @@ local getopt = require('getopt')
|
||||||
local bin = require('bin')
|
local bin = require('bin')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
local dumplib = require('html_dumplib')
|
local dumplib = require('html_dumplib')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Iceman'
|
author = 'Iceman'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc =[[
|
desc = [[
|
||||||
This script will load several traces files in ../traces/ folder and do
|
This script will load several traces files in ../traces/ folder and do
|
||||||
"data load"
|
"data load"
|
||||||
"lf search 1 u"
|
"lf search 1 u"
|
||||||
|
@ -16,13 +17,13 @@ The following tracefiles will be loaded:
|
||||||
em*.pm3
|
em*.pm3
|
||||||
m*.pm3
|
m*.pm3
|
||||||
]]
|
]]
|
||||||
example =[[
|
example = [[
|
||||||
script run tracetest
|
1. script run tracetest
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run tracetest -h
|
script run tracetest [-h]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
]]
|
]]
|
||||||
local DEBUG = true -- the debug flag
|
local DEBUG = true -- the debug flag
|
||||||
|
@ -54,9 +55,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
-- Exit message
|
-- Exit message
|
||||||
|
|
|
@ -2,10 +2,11 @@ local cmds = require('commands')
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local lib14a = require('read14a')
|
local lib14a = require('read14a')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = 'Iceman'
|
author = 'Iceman'
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = [[
|
desc = [[
|
||||||
This is a script that reads AZTEK ISO14443a tags.
|
This is a script that reads AZTEK ISO14443a tags.
|
||||||
It starts from block 0 and ends at default block 20. Use 'b' to say different endblock.
|
It starts from block 0 and ends at default block 20. Use 'b' to say different endblock.
|
||||||
|
@ -19,11 +20,11 @@ example = [[
|
||||||
script run ufodump -b 10
|
script run ufodump -b 10
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run ufudump -h -b
|
script run ufudump [-h] [-b]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
h this helptext
|
-h This help
|
||||||
b endblock in decimal (1-255, default 20)
|
-b endblock in decimal (1-255, default 20)
|
||||||
]]
|
]]
|
||||||
|
|
||||||
-- Some globals
|
-- Some globals
|
||||||
|
@ -56,9 +57,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
--- Picks out and displays the data read from a tag
|
--- Picks out and displays the data read from a tag
|
||||||
|
|
|
@ -1,9 +1,10 @@
|
||||||
local getopt = require('getopt')
|
local getopt = require('getopt')
|
||||||
local utils = require('utils')
|
local utils = require('utils')
|
||||||
|
local ansicolors = require('ansicolors')
|
||||||
|
|
||||||
copyright = ''
|
copyright = ''
|
||||||
author = "Iceman"
|
author = "Iceman"
|
||||||
version = 'v1.0.1'
|
version = 'v1.0.2'
|
||||||
desc = [[
|
desc = [[
|
||||||
This script tries to set UID on a mifare Ultralight magic card which either
|
This script tries to set UID on a mifare Ultralight magic card which either
|
||||||
- answers to chinese backdoor commands
|
- answers to chinese backdoor commands
|
||||||
|
@ -17,9 +18,9 @@ example = [[
|
||||||
script run ul_uid -b -u 11223344556677
|
script run ul_uid -b -u 11223344556677
|
||||||
]]
|
]]
|
||||||
usage = [[
|
usage = [[
|
||||||
script run ul_uid -h -b -u <uid>
|
script run ul_uid [-h] [-b] [-u <uid>]
|
||||||
|
]]
|
||||||
Arguments:
|
arguments = [[
|
||||||
-h : this help
|
-h : this help
|
||||||
-u <UID> : UID (14 hexsymbols)
|
-u <UID> : UID (14 hexsymbols)
|
||||||
-b : write to brickable magic tag
|
-b : write to brickable magic tag
|
||||||
|
@ -55,9 +56,12 @@ local function help()
|
||||||
print(author)
|
print(author)
|
||||||
print(version)
|
print(version)
|
||||||
print(desc)
|
print(desc)
|
||||||
print('Example usage')
|
print(ansicolors.cyan..'Usage'..ansicolors.reset)
|
||||||
print(example)
|
|
||||||
print(usage)
|
print(usage)
|
||||||
|
print(ansicolors.cyan..'Arguments'..ansicolors.reset)
|
||||||
|
print(arguments)
|
||||||
|
print(ansicolors.cyan..'Example usage'..ansicolors.reset)
|
||||||
|
print(example)
|
||||||
end
|
end
|
||||||
--
|
--
|
||||||
--- Set UID on magic command enabled
|
--- Set UID on magic command enabled
|
||||||
|
|
|
@ -27,6 +27,7 @@
|
||||||
#include "comms.h"
|
#include "comms.h"
|
||||||
#include "fileutils.h"
|
#include "fileutils.h"
|
||||||
#include "flash.h"
|
#include "flash.h"
|
||||||
|
#include "settings.h"
|
||||||
|
|
||||||
static void showBanner(void) {
|
static void showBanner(void) {
|
||||||
g_printAndLog = PRINTANDLOG_PRINT;
|
g_printAndLog = PRINTANDLOG_PRINT;
|
||||||
|
@ -581,6 +582,12 @@ int main(int argc, char *argv[]) {
|
||||||
set_my_executable_path();
|
set_my_executable_path();
|
||||||
set_my_user_directory();
|
set_my_user_directory();
|
||||||
|
|
||||||
|
// Settings Load and Test
|
||||||
|
// settings_load ();
|
||||||
|
// settings_save ();
|
||||||
|
// printf ("Ver : %s\n",mySettings.version);
|
||||||
|
// End Settings
|
||||||
|
|
||||||
for (int i = 1; i < argc; i++) {
|
for (int i = 1; i < argc; i++) {
|
||||||
|
|
||||||
if (argv[i][0] != '-') {
|
if (argv[i][0] != '-') {
|
||||||
|
|
184
client/settings.c
Normal file
184
client/settings.c
Normal file
|
@ -0,0 +1,184 @@
|
||||||
|
/*****************************************************************************
|
||||||
|
* WARNING
|
||||||
|
*
|
||||||
|
* THIS CODE IS CREATED FOR EXPERIMENTATION AND EDUCATIONAL USE ONLY.
|
||||||
|
*
|
||||||
|
* USAGE OF THIS CODE IN OTHER WAYS MAY INFRINGE UPON THE INTELLECTUAL
|
||||||
|
* PROPERTY OF OTHER PARTIES, SUCH AS INSIDE SECURE AND HID GLOBAL,
|
||||||
|
* AND MAY EXPOSE YOU TO AN INFRINGEMENT ACTION FROM THOSE PARTIES.
|
||||||
|
*
|
||||||
|
* THIS CODE SHOULD NEVER BE USED TO INFRINGE PATENTS OR INTELLECTUAL PROPERTY RIGHTS.
|
||||||
|
*
|
||||||
|
*****************************************************************************
|
||||||
|
*
|
||||||
|
* This file is part of loclass. It is a reconstructon of the cipher engine
|
||||||
|
* used in iClass, and RFID techology.
|
||||||
|
*
|
||||||
|
* The implementation is based on the work performed by
|
||||||
|
* Flavio D. Garcia, Gerhard de Koning Gans, Roel Verdult and
|
||||||
|
* Milosch Meriac in the paper "Dismantling IClass".
|
||||||
|
*
|
||||||
|
* Copyright (C) 2014 Martin Holst Swende
|
||||||
|
*
|
||||||
|
* This is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License version 2 as published
|
||||||
|
* by the Free Software Foundation, or, at your option, any later version.
|
||||||
|
*
|
||||||
|
* This file is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with loclass. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*
|
||||||
|
*
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
// Settings Functions
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
#include "settings.h"
|
||||||
|
#include "comms.h"
|
||||||
|
#include "emv/emvjson.h"
|
||||||
|
|
||||||
|
// Load all settings into memory (struct)
|
||||||
|
int settings_load (void)
|
||||||
|
{
|
||||||
|
// loadFileJson wants these, so pass in place holder values, though not used
|
||||||
|
// in settings load;
|
||||||
|
uint8_t dummyData = 0x00;
|
||||||
|
size_t dummyDL = 0x00;
|
||||||
|
|
||||||
|
// clear all settings
|
||||||
|
memset (&mySettings,0x00,sizeof(mySettings));
|
||||||
|
|
||||||
|
if (loadFileJSON(settingsFilename, &dummyData, sizeof(dummyData), &dummyDL) == PM3_SUCCESS) {
|
||||||
|
printf ("==> Settings Loaded\n");
|
||||||
|
mySettings.loaded = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Test results
|
||||||
|
/*
|
||||||
|
bool os_windows_usecolor;
|
||||||
|
bool os_windows_useansicolor;
|
||||||
|
int window_xpos;
|
||||||
|
int window_ypos;
|
||||||
|
int window_hsize;
|
||||||
|
int window_wsize;
|
||||||
|
*/
|
||||||
|
printf (" Settings Version : [%s]\n",mySettings.version);
|
||||||
|
printf (" os_windows_usecolor (bool) : [%d]\n",mySettings.os_windows_usecolor);
|
||||||
|
printf (" os_windows_useAnsicolor (bool) : [%d]\n",mySettings.os_windows_useansicolor);
|
||||||
|
printf (" window_xpos (int) : [%d]\n",mySettings.window_xpos);
|
||||||
|
printf (" window_ypos (int) : [%d]\n",mySettings.window_ypos);
|
||||||
|
printf (" window_hsize (int) : [%d]\n",mySettings.window_hsize);
|
||||||
|
printf (" window_wsize (int) : [%d]\n",mySettings.window_wsize);
|
||||||
|
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Save all settings from memory (struct) to file
|
||||||
|
int settings_save (void)
|
||||||
|
{
|
||||||
|
// Note sure if backup has value ?
|
||||||
|
char backupFilename[500];
|
||||||
|
|
||||||
|
snprintf (backupFilename,sizeof(backupFilename),"%s.bak",settingsFilename);
|
||||||
|
|
||||||
|
if (fileExists (backupFilename)) {
|
||||||
|
if (remove (backupFilename) != 0) {
|
||||||
|
PrintAndLogEx (FAILED, "Error - could not delete old settings backup file \"%s\"",backupFilename);
|
||||||
|
return PM3_ESOFT;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (fileExists (settingsFilename)) {
|
||||||
|
if (rename (settingsFilename,backupFilename) != 0) {
|
||||||
|
PrintAndLogEx (FAILED, "Error - could not backup settings file \"%s\" to \"%s\"",settingsFilename,backupFilename);
|
||||||
|
return PM3_ESOFT;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
uint8_t dummyData = 0x00;
|
||||||
|
size_t dummyDL = 0x00;
|
||||||
|
|
||||||
|
// int saveFileJSON(const char *preferredName, JSONFileType ftype, uint8_t *data, size_t datalen);
|
||||||
|
|
||||||
|
if (saveFileJSON(settingsFilename, jsfSettings, &dummyData, dummyDL) == PM3_SUCCESS)
|
||||||
|
PrintAndLogEx (NORMAL, "settings have been saved to \"%s\"",settingsFilename);
|
||||||
|
|
||||||
|
return PM3_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
void settings_save_callback (json_t *root)
|
||||||
|
{
|
||||||
|
// extern settings_t mySettings;
|
||||||
|
|
||||||
|
printf ("==> Save Settings\n");
|
||||||
|
//JsonSaveStr(root, "FileType", "settings");
|
||||||
|
//JsonSaveStr (root,"Test1.Test2","test settings");
|
||||||
|
/*
|
||||||
|
"version": "1.0 Nov 2019",
|
||||||
|
"os.windows.usecolor": true,
|
||||||
|
"os.windows.useAnsiColor": true,
|
||||||
|
"window.xpos": 10,
|
||||||
|
"window.ypos": 10,
|
||||||
|
"window.hsize": 300,
|
||||||
|
"window.wsize": 600
|
||||||
|
*/
|
||||||
|
JsonSaveStr (root,"FileType","settings");
|
||||||
|
JsonSaveStr (root,"version","1.0 Nov 2019");//mySettings.version);
|
||||||
|
JsonSaveBoolean (root,"os.windows.useColor",mySettings.os_windows_usecolor);
|
||||||
|
JsonSaveBoolean (root,"os.windows.useAnsiColor",mySettings.os_windows_useansicolor);
|
||||||
|
JsonSaveInt (root,"window.xpos",mySettings.window_xpos);
|
||||||
|
JsonSaveInt (root,"window.ypos",mySettings.window_ypos);
|
||||||
|
JsonSaveInt (root,"window.hsize",mySettings.window_hsize);
|
||||||
|
JsonSaveInt (root,"window.wsize",mySettings.window_wsize);
|
||||||
|
}
|
||||||
|
|
||||||
|
void settings_load_callback (json_t *root)
|
||||||
|
{
|
||||||
|
// extern settings_t mySettings;
|
||||||
|
json_error_t up_error = {0};
|
||||||
|
int b1;
|
||||||
|
int i1;
|
||||||
|
const char *s1;
|
||||||
|
|
||||||
|
if (json_unpack_ex(root, &up_error , 0, "{s:s}","version",&s1) == 0)
|
||||||
|
strncpy (mySettings.version,s1,sizeof (mySettings.version) - 1);
|
||||||
|
else
|
||||||
|
strncpy (mySettings.version,"unknown",sizeof (mySettings.version) - 1);
|
||||||
|
|
||||||
|
// os.windows...
|
||||||
|
if (json_unpack_ex(root,&up_error, 0, "{s:b}","os.windows.useColor",&b1) == 0)
|
||||||
|
mySettings.os_windows_usecolor = b1;
|
||||||
|
else // default
|
||||||
|
mySettings.os_windows_useansicolor = false;
|
||||||
|
|
||||||
|
if (json_unpack_ex(root,&up_error, 0, "{s:b}","os.windows.useAnsiColor",&b1) == 0)
|
||||||
|
mySettings.os_windows_useansicolor = b1;
|
||||||
|
else // default
|
||||||
|
mySettings.os_windows_useansicolor = false;
|
||||||
|
|
||||||
|
// window...
|
||||||
|
if (json_unpack_ex(root,&up_error, 0, "{s:i}","window.xpos",&i1) == 0)
|
||||||
|
mySettings.window_xpos = i1;
|
||||||
|
else // default
|
||||||
|
mySettings.window_xpos = 0;
|
||||||
|
if (json_unpack_ex(root,&up_error, 0, "{s:i}","window.ypos",&i1) == 0)
|
||||||
|
mySettings.window_ypos = i1;
|
||||||
|
else // default
|
||||||
|
mySettings.window_ypos = 0;
|
||||||
|
if (json_unpack_ex(root,&up_error, 0, "{s:i}","window.hsize",&i1) == 0)
|
||||||
|
mySettings.window_hsize = i1;
|
||||||
|
else // default
|
||||||
|
mySettings.window_hsize = 0;
|
||||||
|
if (json_unpack_ex(root,&up_error, 0, "{s:i}","window.wsize",&i1) == 0)
|
||||||
|
mySettings.window_wsize = i1;
|
||||||
|
else // default
|
||||||
|
mySettings.window_wsize = 0;
|
||||||
|
|
||||||
|
}
|
38
client/settings.h
Normal file
38
client/settings.h
Normal file
|
@ -0,0 +1,38 @@
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
// Copyright (C) 2009 Michael Gernoth <michael at gernoth.net>
|
||||||
|
// Copyright (C) 2010 iZsh <izsh at fail0verflow.com>
|
||||||
|
//
|
||||||
|
// 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.
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
// Settings Functions
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
#ifndef settings_h
|
||||||
|
#define settings_h
|
||||||
|
|
||||||
|
#include "fileutils.h"
|
||||||
|
|
||||||
|
#define settingsFilename "settings.json"
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
bool loaded;
|
||||||
|
char version[20];
|
||||||
|
bool os_windows_usecolor;
|
||||||
|
bool os_windows_useansicolor;
|
||||||
|
int window_xpos;
|
||||||
|
int window_ypos;
|
||||||
|
int window_hsize;
|
||||||
|
int window_wsize;
|
||||||
|
} settings_t;
|
||||||
|
|
||||||
|
// Settings struct so as to be available to other modules by including settings.h
|
||||||
|
settings_t mySettings;
|
||||||
|
|
||||||
|
int settings_load (void);
|
||||||
|
int settings_save (void);
|
||||||
|
|
||||||
|
void settings_save_callback (json_t *root);
|
||||||
|
void settings_load_callback (json_t *root);
|
||||||
|
|
||||||
|
#endif
|
Loading…
Add table
Add a link
Reference in a new issue