chg: 'lf t55xx info p' - got some more love, now can read with password :)

chg: 'lf t55xx dump p' - less outputs and now can read with password :)
chg: 'lf t55xx trace 1' - can now decode trace from a saved trace. However you must have correct configuration set in order to work.
chg: 'lf t55xx wipe p' - now can use a password to write to configblock first.
This commit is contained in:
iceman1001 2019-09-12 17:34:55 +02:00
commit c3a0d7d88a

View file

@ -91,6 +91,17 @@ static int usage_t55xx_read() {
PrintAndLogEx(NORMAL, "");
return PM3_SUCCESS;
}
static int usage_t55xx_resetread() {
PrintAndLogEx(NORMAL, "Send Reset Cmd then lf read the stream to attempt to identify the start of it (needs a demod and/or plot after)");
PrintAndLogEx(NORMAL, "Usage: lf t55xx resetread [r <mode>]");
PrintAndLogEx(NORMAL, "Options:");
print_usage_t55xx_downloadlink();
PrintAndLogEx(NORMAL, "");
PrintAndLogEx(NORMAL, "Examples:");
PrintAndLogEx(NORMAL, " lf t55xx resetread");
PrintAndLogEx(NORMAL, "");
return PM3_SUCCESS;
}
static int usage_t55xx_write() {
PrintAndLogEx(NORMAL, "Usage: lf t55xx write [r <mode>] b <block> d <data> [p <password>] [1] [t]");
PrintAndLogEx(NORMAL, "Options:");
@ -108,15 +119,14 @@ static int usage_t55xx_write() {
return PM3_SUCCESS;
}
static int usage_t55xx_trace() {
PrintAndLogEx(NORMAL, "Usage: lf t55xx trace [r mode]");
PrintAndLogEx(NORMAL, "Usage: lf t55xx trace [1] [r mode]");
PrintAndLogEx(NORMAL, "Options:");
print_usage_t55xx_downloadlink();
// Command did not seem to support the 1 option (yet) so have removed the help lines
// PrintAndLogEx(NORMAL, " 1 - if set, use Graphbuffer otherwise read data from tag.");
PrintAndLogEx(NORMAL, " 1 - if set, use Graphbuffer otherwise read data from tag.");
PrintAndLogEx(NORMAL, "");
PrintAndLogEx(NORMAL, "Examples:");
PrintAndLogEx(NORMAL, " lf t55xx trace");
// PrintAndLogEx(NORMAL, " lf t55xx trace 1");
PrintAndLogEx(NORMAL, " lf t55xx trace 1");
PrintAndLogEx(NORMAL, "");
return PM3_SUCCESS;
}
@ -124,6 +134,7 @@ static int usage_t55xx_info() {
PrintAndLogEx(NORMAL, "Usage: lf t55xx info [1] [r <mode>] [d <data> [q]]");
PrintAndLogEx(NORMAL, "Options:");
PrintAndLogEx(NORMAL, " (default) - read data from tag.");
PrintAndLogEx(NORMAL, " p <password> - OPTIONAL password 4bytes (8 hex symbols)");
PrintAndLogEx(NORMAL, " 1 - if set, use Graphbuffer instead of reading tag.");
PrintAndLogEx(NORMAL, " d <data> - 4 bytes of data (8 hex characters)");
PrintAndLogEx(NORMAL, " if set, use these data instead of reading tag.");
@ -135,19 +146,20 @@ static int usage_t55xx_info() {
PrintAndLogEx(NORMAL, " lf t55xx info 1");
PrintAndLogEx(NORMAL, " lf t55xx info d 00083040");
PrintAndLogEx(NORMAL, " lf t55xx info d 6001805A q");
PrintAndLogEx(NORMAL, " lf t55xx info p 11223344");
PrintAndLogEx(NORMAL, "");
return PM3_SUCCESS;
}
static int usage_t55xx_dump() {
PrintAndLogEx(NORMAL, "Usage: lf t55xx dump [r <mode>] [<password> [o]]");
PrintAndLogEx(NORMAL, "Usage: lf t55xx dump [r <mode>] [p <password> [o]]");
PrintAndLogEx(NORMAL, "Options:");
PrintAndLogEx(NORMAL, " <password> - OPTIONAL password 4bytes (8 hex symbols)");
PrintAndLogEx(NORMAL, " p <password> - OPTIONAL password 4bytes (8 hex symbols)");
PrintAndLogEx(NORMAL, " o - OPTIONAL override, force pwd read despite danger to card");
print_usage_t55xx_downloadlink();
PrintAndLogEx(NORMAL, "");
PrintAndLogEx(NORMAL, "Examples:");
PrintAndLogEx(NORMAL, " lf t55xx dump");
PrintAndLogEx(NORMAL, " lf t55xx dump feedbeef o");
PrintAndLogEx(NORMAL, " lf t55xx dump p feedbeef o");
PrintAndLogEx(NORMAL, "");
return PM3_SUCCESS;
}
@ -215,16 +227,16 @@ static int usage_t55xx_bruteforce() {
PrintAndLogEx(NORMAL, "press " _YELLOW_("'enter'") " to cancel the command");
PrintAndLogEx(NORMAL, "WARNING: this may brick non-password protected chips!");
PrintAndLogEx(NORMAL, "Try reading block 7 before\n");
PrintAndLogEx(NORMAL, "Usage: lf t55xx bruteforce [h] [r <mode>] <start password> <end password>");
PrintAndLogEx(NORMAL, "Usage: lf t55xx bruteforce [h] [r <mode>] [s <start password>] [e <end password>]");
PrintAndLogEx(NORMAL, " password must be 4 bytes (8 hex symbols)");
PrintAndLogEx(NORMAL, "Options:");
PrintAndLogEx(NORMAL, " h - this help");
print_usage_t55xx_downloadlink();
PrintAndLogEx(NORMAL, " <start_pwd> - 4 byte hex value to start pwd search at");
PrintAndLogEx(NORMAL, " <end_pwd> - 4 byte hex value to end pwd search at");
PrintAndLogEx(NORMAL, " s <start_pwd> - 4 byte hex value to start pwd search at");
PrintAndLogEx(NORMAL, " e <end_pwd> - 4 byte hex value to end pwd search at");
PrintAndLogEx(NORMAL, "");
PrintAndLogEx(NORMAL, "Examples:");
PrintAndLogEx(NORMAL, " lf t55xx bruteforce r 2 aaaaaa77 aaaaaa99");
PrintAndLogEx(NORMAL, " lf t55xx bruteforce r 2 s aaaaaa77 e aaaaaa99");
PrintAndLogEx(NORMAL, "");
return PM3_SUCCESS;
}
@ -248,15 +260,15 @@ static int usage_t55xx_recoverpw() {
return PM3_SUCCESS;
}
static int usage_t55xx_wipe() {
PrintAndLogEx(NORMAL, "Usage: lf t55xx wipe [h] [Q5]");
PrintAndLogEx(NORMAL, "Usage: lf t55xx wipe [h] [Q5] [p <password>]");
PrintAndLogEx(NORMAL, "This commands wipes a tag, fills blocks 1-7 with zeros and a default configuration block");
PrintAndLogEx(NORMAL, "Options:");
PrintAndLogEx(NORMAL, " h - this help");
PrintAndLogEx(NORMAL, " Q5 - indicates to use the T5555 (Q5) default configuration block");
PrintAndLogEx(NORMAL, " q - indicates to use the T5555 (Q5) default configuration block");
PrintAndLogEx(NORMAL, "");
PrintAndLogEx(NORMAL, "Examples:");
PrintAndLogEx(NORMAL, " lf t55xx wipe - wipes a t55x7 tag, config block 0x000880E0");
PrintAndLogEx(NORMAL, " lf t55xx wipe Q5 - wipes a t5555 Q5 tag, config block 0x6001F004");
PrintAndLogEx(NORMAL, " lf t55xx wipe q - wipes a t5555 Q5 tag, config block 0x6001F004");
return PM3_SUCCESS;
}
static int usage_lf_deviceconfig() {
@ -292,6 +304,9 @@ void printT5xxHeader(uint8_t page) {
static int CmdT55xxSetConfig(const char *Cmd) {
// No args
if (strlen(Cmd) == 0) return printConfiguration(config);
uint8_t offset = 0, bitRate = 0;
char modulation[6] = {0x00};
uint8_t rates[9] = {8, 16, 32, 40, 50, 64, 100, 128, 0};
@ -395,9 +410,6 @@ static int CmdT55xxSetConfig(const char *Cmd) {
}
}
// No args
if (cmdp == 0) return printConfiguration(config);
//Validations
if (errors) return usage_t55xx_config();
@ -418,16 +430,14 @@ int T55xxReadBlock(uint8_t block, bool page1, bool usepwd, uint8_t override, uin
} else {
PrintAndLogEx(NORMAL, "Safety Check: PWD bit is NOT set in config block. Reading without password...");
usepwd = false;
page1 = false;
page1 = false; // ??
}
} else {
} else if (override == 1) {
// Show only if first for command i.e. override = 1 (override and display) override = 2 (override and dont display)
if (override == 1)
PrintAndLogEx(NORMAL, "Safety Check Overriden - proceeding despite risk");
}
}
if (!AquireData(page1, block, usepwd, password, downlink_mode))
return PM3_ESOFT;
@ -470,8 +480,10 @@ static int CmdT55xxReadBlock(const char *Cmd) {
cmdp++;
break;
case 'r':
downlink_mode = param_getchar(Cmd, cmdp + 1) - '0';
if (downlink_mode > 3) downlink_mode = 0;
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode > 3)
downlink_mode = 0;
cmdp += 2;
break;
@ -620,9 +632,13 @@ static int CmdT55xxDetect(const char *Cmd) {
cmdp++;
break;
case 'r':
downlink_mode = param_getchar(Cmd, cmdp + 1) - '0';
if (downlink_mode == 4) try_all_dl_modes = true;
if (downlink_mode > 3) downlink_mode = 0;
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode == 4)
try_all_dl_modes = true;
if (downlink_mode > 3)
downlink_mode = 0;
cmdp += 2;
break;
default:
@ -1135,11 +1151,12 @@ static int CmdT55xxWakeUp(const char *Cmd) {
case 'p':
password = param_get32ex(Cmd, cmdp + 1, 0, 16);
cmdp += 2;
errors = false;
break;
case 'r':
downlink_mode = param_getchar(Cmd, cmdp + 1) - '0';
if (downlink_mode > 3) downlink_mode = 0;
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode > 3)
downlink_mode = 0;
cmdp += 2;
break;
default:
@ -1203,8 +1220,10 @@ static int CmdT55xxWriteBlock(const char *Cmd) {
cmdp++;
break;
case 'r':
downlink_mode = param_getchar(Cmd, cmdp + 1) - '0';
if (downlink_mode > 3) downlink_mode = 0;
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode > 3)
downlink_mode = 0;
cmdp += 2;
break;
default:
@ -1254,25 +1273,43 @@ static int CmdT55xxWriteBlock(const char *Cmd) {
}
static int CmdT55xxReadTrace(const char *Cmd) {
uint8_t cmd_len = 0;
bool frombuff = false;
uint8_t downlink_mode = 0;
uint8_t cmdp = 0;
bool errors = false;
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
switch (tolower(param_getchar(Cmd, cmdp))) {
case 'h':
return usage_t55xx_trace();
case 'r':
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode > 3)
downlink_mode = 0;
char cmdp = tolower(param_getchar(Cmd, 0));
if (cmdp == 'r') {
downlink_mode = param_getchar(Cmd, 1) - '0';
if (downlink_mode > 3) downlink_mode = 0;
cmd_len = 3;
cmdp += 2;
break;
case '1':
frombuff = true;
cmdp += 2;
break;
default:
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
errors = true;
break;
}
}
if ((strlen(Cmd) != cmd_len) || (cmdp == 'h')) return usage_t55xx_trace();
if (strlen(Cmd) == cmd_len) {
if (errors) return usage_t55xx_trace();
if (!frombuff) {
// sanity check.
if (SanityOfflineCheck(false) != PM3_SUCCESS) return PM3_ENODATA;
bool pwdmode = false;
uint32_t password = 0;
// REGULAR_READ_MODE_BLOCK - yeilds correct Page 1 Block 2 data i.e. + 32 bit offset.
// if (!AquireData(T55x7_PAGE1, T55x7_TRACE_BLOCK1, pwdmode, password,downlink_mode))
if (!AquireData(T55x7_PAGE1, REGULAR_READ_MODE_BLOCK, pwdmode, password, downlink_mode))
return PM3_ENODATA;
}
@ -1515,10 +1552,10 @@ static int CmdT55xxInfo(const char *Cmd) {
Normal mode
Extended mode
*/
bool frombuff = false, gotdata = false, dataasq5 = false;
bool frombuff = false, gotdata = false, dataasq5 = false, usepwd = false;
uint8_t cmdp = 0;
uint8_t downlink_mode = 0;
uint32_t block0 = 0;
uint32_t block0 = 0, password = 0;
while (param_getchar(Cmd, cmdp) != 0x00) {
switch (tolower(param_getchar(Cmd, cmdp))) {
@ -1529,6 +1566,11 @@ static int CmdT55xxInfo(const char *Cmd) {
gotdata = true;
cmdp += 2;
break;
case 'p':
password = param_get32ex(Cmd, cmdp + 1, 0, 16);
usepwd = true;
cmdp += 2;
break;
case '1':
frombuff = true;
cmdp += 2;
@ -1538,8 +1580,10 @@ static int CmdT55xxInfo(const char *Cmd) {
cmdp += 2;
break;
case 'r':
downlink_mode = param_getchar(Cmd, cmdp + 1) - '0';
if (downlink_mode > 3) downlink_mode = 0;
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode > 3)
downlink_mode = 0;
cmdp += 2;
break;
default:
@ -1558,11 +1602,10 @@ static int CmdT55xxInfo(const char *Cmd) {
// sanity check.
if (SanityOfflineCheck(false) != PM3_SUCCESS) return PM3_ENODATA;
bool pwdmode = false;
uint32_t password = 0;
if (!AquireData(T55x7_PAGE0, T55x7_CONFIGURATION_BLOCK, pwdmode, password, downlink_mode))
if (!AquireData(T55x7_PAGE0, T55x7_CONFIGURATION_BLOCK, usepwd, password, downlink_mode))
return PM3_ENODATA;
}
if (!gotdata) {
if (!DecodeT55xxBlock()) return PM3_ESOFT;
@ -1657,26 +1700,38 @@ static int CmdT55xxDump(const char *Cmd) {
uint32_t password = 0;
uint8_t override = 0;
uint8_t cmd_opt_idx = 0;
uint8_t downlink_mode = 0;
uint8_t pwd_offset = 0;
char cmdp = tolower(param_getchar(Cmd, 0));
bool usepwd = false;
bool errors = false;
uint8_t cmdp = 0;
if (cmdp == 'h') return usage_t55xx_dump();
if (cmdp == 'r') {
cmd_opt_idx++;
downlink_mode = param_getchar(Cmd, cmd_opt_idx++) - '0';
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
switch (tolower(param_getchar(Cmd, cmdp))) {
case 'h':
return usage_t55xx_dump();
case 'r':
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode > 3)
downlink_mode = 0;
pwd_offset = 3;
}
bool usepwd = (strlen(Cmd) > pwd_offset);
if (usepwd) {
password = param_get32ex(Cmd, cmd_opt_idx++, 0, 16);
if (param_getchar(Cmd, cmd_opt_idx++) == 'o')
cmdp += 2;
break;
case 'p':
password = param_get32ex(Cmd, cmdp + 1, 0, 16);
usepwd = true;
cmdp += 2;
break;
case 'o':
override = 1;
cmdp++;
break;
default:
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
errors = true;
break;
}
}
if (errors) return usage_t55xx_dump();
printT5xxHeader(0);
for (uint8_t i = 0; i < 8; ++i) {
@ -1974,15 +2029,33 @@ static int CmdResetRead(const char *Cmd) {
uint8_t downlink_mode = 0;
uint8_t flags = 0;
uint8_t cmdp = 0;
bool errors = false;
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
switch (tolower(param_getchar(Cmd, cmdp))) {
case 'h':
return usage_t55xx_resetread();
case 'r':
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode > 3)
downlink_mode = 0;
if (strlen(Cmd) == 3)
downlink_mode = param_getchar(Cmd, 1) - '0';
cmdp += 2;
break;
default:
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
errors = true;
break;
}
}
if (downlink_mode > 3) downlink_mode = 0;
if (errors) return usage_t55xx_resetread();
PrintAndLogEx(INFO, "DL : %d\n", downlink_mode);
printf("DL : %d\n", downlink_mode);
flags = downlink_mode << 3;
clearCommandBuffer();
SendCommandNG(CMD_LF_T55XX_RESET_READ, &flags, sizeof(flags));
if (!WaitForResponseTimeout(CMD_ACK, NULL, 2500)) {
@ -2002,27 +2075,63 @@ static int CmdResetRead(const char *Cmd) {
static int CmdT55xxWipe(const char *Cmd) {
char writeData[20] = {0};
char *ptrData = writeData;
char cmdp = tolower(param_getchar(Cmd, 0));
if (cmdp == 'h') return usage_t55xx_wipe();
uint32_t password = 0;
bool usepwd = false;
bool Q5 = false;
uint8_t cmdp = 0;
bool errors = false;
bool Q5 = (cmdp == 'q');
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
switch (tolower(param_getchar(Cmd, cmdp))) {
case 'h':
return usage_t55xx_wipe();
case 'p':
// password used by handheld cloners
password = param_get32ex(Cmd, cmdp + 1, 0x51243648, 16);
usepwd = true;
cmdp += 2;
break;
case 'q':
Q5 = true;
cmdp++;
break;
default:
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
errors = true;
break;
}
}
if (errors) return usage_t55xx_wipe();
// Try with the default password to reset block 0
// With a pwd should work even if pwd bit not set
PrintAndLogEx(INFO, "\nBeginning Wipe of a T55xx tag (assuming the tag is not password protected)\n");
if (Q5)
snprintf(ptrData, sizeof(writeData), "b 0 d 6001F004 p 0");
else
snprintf(ptrData, sizeof(writeData), "b 0 d 000880E0 p 0");
if (CmdT55xxWriteBlock(ptrData) != PM3_SUCCESS) PrintAndLogEx(WARNING, "Warning: error writing blk 0");
if (usepwd) {
snprintf(ptrData, sizeof(writeData), "b 0 p %08x ", password);
} else {
snprintf(ptrData, sizeof(writeData), "b 0 ");
}
if (Q5)
snprintf(ptrData + strlen(ptrData), sizeof(writeData) - strlen(ptrData), "d 6001F004");
else
snprintf(ptrData + strlen(ptrData), sizeof(writeData) - strlen(ptrData), "d 000880E0");
PrintAndLogEx(INFO, "%s", ptrData);
return 0;
if (CmdT55xxWriteBlock(ptrData) != PM3_SUCCESS)
PrintAndLogEx(WARNING, "Warning: error writing blk 0");
for (uint8_t blk = 1; blk < 8; blk++) {
snprintf(ptrData, sizeof(writeData), "b %d d 0", blk);
if (CmdT55xxWriteBlock(ptrData) != PM3_SUCCESS) PrintAndLogEx(WARNING, "Warning: error writing blk %d", blk);
if (CmdT55xxWriteBlock(ptrData) != PM3_SUCCESS)
PrintAndLogEx(WARNING, "Warning: error writing blk %d", blk);
memset(writeData, 0x00, sizeof(writeData));
}
@ -2047,37 +2156,45 @@ static int CmdT55xxChkPwds(const char *Cmd) {
bool from_flash = false;
bool try_all_dl_modes = false;
uint8_t downlink_mode = 0;
int len;
char cmdp;
bool use_pwd_file = false;
int dl_mode; // to try each downlink mode for each password
uint8_t cmdp = 0;
bool errors = false;
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
switch (tolower(param_getchar(Cmd, cmdp))) {
case 'h':
return usage_t55xx_chk();
case 'r':
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode == 4)
try_all_dl_modes = true;
cmdp = tolower(param_getchar(Cmd, 0));
if (downlink_mode > 3)
downlink_mode = 0;
if (cmdp == 'h') return usage_t55xx_chk();
if (cmdp == 'm') {
cmdp += 2;
break;
case 'm':
from_flash = true;
Cmd += 2;
cmdp = tolower(param_getchar(Cmd, 0));
cmdp++;
break;
case 'i':
if ( param_getstr(Cmd, cmdp + 1, filename, sizeof(filename)) == 0 ) {
PrintAndLogEx(ERR, "Error, no filename after 'f' was found");
errors = true;
}
if (cmdp == 'r') {
Cmd += 2;
downlink_mode = param_getchar(Cmd, 0) - '0'; // get 2nd option, as this is fixed order.
if (downlink_mode == 4) try_all_dl_modes = true;
if (downlink_mode > 3) downlink_mode = 0;
Cmd += 2;
cmdp = param_getchar(Cmd, 0);
}
if (cmdp == 'i') {
Cmd += 2;
len = strlen(Cmd);
if (len > FILE_PATH_SIZE) len = FILE_PATH_SIZE;
memcpy(filename, Cmd, len);
use_pwd_file = true;
cmdp += 2;
break;
default:
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
errors = true;
break;
}
}
if (errors) return usage_t55xx_chk();
/*
// block 7, page1 = false, usepwd = false, override = false, pwd = 00000000
@ -2194,30 +2311,45 @@ static int CmdT55xxBruteForce(const char *Cmd) {
uint32_t end_password = 0xFFFFFFFF; //end password
uint32_t curr = 0;
uint8_t downlink_mode = 0;
uint8_t cmd_opt_idx = 0;
uint8_t found = 0; // > 0 if found xx1 xx downlink needed, 1 found
uint8_t cmdp = 0;
bool errors = false;
char cmdp = tolower(param_getchar(Cmd, cmd_opt_idx));
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
switch (tolower(param_getchar(Cmd, cmdp))) {
case 'h':
return usage_t55xx_bruteforce();
case 'r':
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode > 4)
downlink_mode = 0;
if (cmdp == 'h') return usage_t55xx_bruteforce();
if (cmdp == 'r') { // downlink mode supplied
cmd_opt_idx++; // skip over 'r'
downlink_mode = param_getchar(Cmd, cmd_opt_idx++) - '0';
if (downlink_mode > 4) downlink_mode = 0;
cmdp += 2;
break;
case 's':
start_password = param_get32ex(Cmd, cmdp + 1, 0, 16);
cmdp += 2;
break;
case 'e':
end_password = param_get32ex(Cmd, cmdp + 1, 0, 16);
cmdp += 2;
break;
default:
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
errors = true;
break;
}
}
uint64_t t1 = msclock();
start_password = param_get32ex(Cmd, cmd_opt_idx++, 0, 16);
end_password = param_get32ex(Cmd, cmd_opt_idx++, 0, 16);
curr = start_password;
if (start_password >= end_password) {
return usage_t55xx_bruteforce();
}
if (errors) return usage_t55xx_bruteforce();
uint64_t t1 = msclock();
curr = start_password;
PrintAndLogEx(INFO, "Search password range [%08X -> %08X]", start_password, end_password);
while (found == 0) {
@ -2285,18 +2417,34 @@ static int CmdT55xxRecoverPW(const char *Cmd) {
uint32_t mask = 0x0;
uint8_t downlink_mode = 0;
uint8_t found = 0;
uint8_t cmd_opt_idx = 0;
uint8_t cmdp = 0;
bool errors = false;
char cmdp = tolower(param_getchar(Cmd, cmd_opt_idx));
while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
switch (tolower(param_getchar(Cmd, cmdp))) {
case 'h':
return usage_t55xx_recoverpw();
case 'p':
// password used by handheld cloners
orig_password = param_get32ex(Cmd, cmdp + 1, 0x51243648, 16);
cmdp += 2;
break;
case 'r':
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode > 4)
downlink_mode = 0;
if (cmdp == 'h') return usage_t55xx_recoverpw();
if (cmdp == 'r') { // downlink mode supplied
cmd_opt_idx++; // skip over 'r'
downlink_mode = param_getchar(Cmd, cmd_opt_idx++) - '0';
if (downlink_mode > 4) downlink_mode = 0;
cmdp += 2;
break;
default:
PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
errors = true;
break;
}
}
orig_password = param_get32ex(Cmd, cmd_opt_idx++, 0x51243648, 16); //password used by handheld cloners
if (errors) return usage_t55xx_recoverpw();
// first try fliping each bit in the expected password
while (bit < 32) {
@ -2511,9 +2659,13 @@ static int CmdT55xxDetectPage1(const char *Cmd) {
cmdp++;
break;
case 'r':
downlink_mode = param_getchar(Cmd, cmdp + 1) - '0';
if (downlink_mode == 4) try_all_dl_modes = true;
if (downlink_mode > 3) downlink_mode = 0;
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode == 4)
try_all_dl_modes = true;
if (downlink_mode > 3)
downlink_mode = 0;
cmdp += 2;
break;
default:
@ -2589,8 +2741,10 @@ static int CmdT55xxSetDeviceConfig(const char *Cmd) {
cmdp += 2;
break;
case 'r':
downlink_mode = param_getchar(Cmd, cmdp + 1) - '0';
if (downlink_mode > 3) downlink_mode = 0;
downlink_mode = param_get8ex(Cmd, cmdp + 1, 0, 10);
if (downlink_mode > 3)
downlink_mode = 0;
cmdp += 2;
break;
case 'p':