mirror of
https://github.com/RfidResearchGroup/proxmark3.git
synced 2025-08-20 21:33:47 -07:00
Merge pull request #2505 from douniwan5788/8268
Added support for 8268/8310
This commit is contained in:
commit
3e4f1576c4
5 changed files with 132 additions and 45 deletions
|
@ -3,6 +3,7 @@ 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...
|
||||
|
||||
## [unreleased][unreleased]
|
||||
- Added support for 8268/8310 (@douniwan5788)
|
||||
- Changed scripting string params to accept 1024 chars, Thanks @evildaemond! (@iceman1001)
|
||||
- Added detection for FM11NT021 (@iceman1001)
|
||||
- Added detection of a magic NTAG 215 (@iceman1001)
|
||||
|
|
|
@ -37,7 +37,19 @@
|
|||
#define CRC_PRESET 0xFF
|
||||
#define CRC_POLYNOM 0x1D
|
||||
|
||||
static struct hitagS_tag tag;
|
||||
static struct hitagS_tag tag = {
|
||||
.pages =
|
||||
{
|
||||
// Plain mode: | Authentication mode:
|
||||
[0] = {0x88, 0xcd, 0x6d, 0xf3}, // UID | UID
|
||||
[1] = {0xca, 0x24, 0x00, 0x00}, // CON0 CON1 CON2 Reserved | CON0 CON1 CON2 PWDH0
|
||||
[2] = {0xaa, 0xaa, 0xaa, 0xaa}, // Data | PWDL0 PWDL1 KEYH0 KEYH1
|
||||
[3] = {0x55, 0x55, 0x55, 0x55}, // Data | KEYL0 KEYL1 KEYL2 KEYL3
|
||||
[4] = {0xff, 0x80, 0x00, 0x00}, // Data
|
||||
[5] = {0x00, 0x00, 0x00, 0x00}, // Data
|
||||
// up to index 63 for HITAG S2048 public data
|
||||
},
|
||||
};
|
||||
static uint8_t page_to_be_written = 0;
|
||||
static int block_data_left = 0;
|
||||
|
||||
|
@ -1360,6 +1372,40 @@ static int selectHitagS(const lf_hitag_data_t *packet, uint8_t *tx, size_t sizeo
|
|||
tx[i] = ((NrAr >> (56 - (i * 8))) & 0xFF);
|
||||
}
|
||||
|
||||
} else if (packet->cmd == RHTSF_82xx || packet->cmd == WHTSF_82xx) {
|
||||
// 8268/8310 Authentication by writing password to block 64
|
||||
|
||||
//send write page request
|
||||
txlen = 0;
|
||||
cmd = HITAGS_WRITE_PAGE;
|
||||
txlen = concatbits(tx, txlen, &cmd, 0, 4);
|
||||
|
||||
uint8_t addr = 64;
|
||||
txlen = concatbits(tx, txlen, &addr, 0, 8);
|
||||
|
||||
crc = CRC8Hitag1Bits(tx, txlen);
|
||||
txlen = concatbits(tx, txlen, &crc, 0, 8);
|
||||
|
||||
sendReceiveHitagS(tx, txlen, rx, sizeofrx, &rxlen, HITAG_T_WAIT_SC, ledcontrol, false);
|
||||
|
||||
if ((rxlen != 2) || (rx[0] >> (8 - 2) != 0x01)) {
|
||||
Dbprintf("no write access on page " _YELLOW_("64") ". not 82xx?");
|
||||
return -1;
|
||||
}
|
||||
|
||||
txlen = 0;
|
||||
txlen = concatbits(tx, txlen, packet->pwd, 0, 32);
|
||||
crc = CRC8Hitag1Bits(tx, txlen);
|
||||
txlen = concatbits(tx, txlen, &crc, 0, 8);
|
||||
|
||||
sendReceiveHitagS(tx, txlen, rx, sizeofrx, &rxlen, HITAG_T_WAIT_SC, ledcontrol, false);
|
||||
|
||||
if ((rxlen != 2) || (rx[0] >> (8 - 2) != 0x01)) {
|
||||
Dbprintf("write to page " _YELLOW_("64") " failed! wrong password?");
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
} else if (packet->cmd == RHTSF_PLAIN || packet->cmd == WHTSF_PLAIN) {
|
||||
Dbprintf("Error, " _YELLOW_("AUT=1") " This tag is configured in Authentication Mode");
|
||||
return -1;
|
||||
|
@ -1413,19 +1459,15 @@ static int selectHitagS(const lf_hitag_data_t *packet, uint8_t *tx, size_t sizeo
|
|||
* Reads every page of a hitag S transpoder.
|
||||
*/
|
||||
void ReadHitagS(const lf_hitag_data_t *payload, bool ledcontrol) {
|
||||
|
||||
int status = PM3_SUCCESS;
|
||||
uint8_t rx[HITAG_FRAME_LEN];
|
||||
size_t rxlen = 0;
|
||||
|
||||
uint8_t tx[HITAG_FRAME_LEN];
|
||||
|
||||
if (selectHitagS(payload, tx, ARRAYLEN(tx), rx, ARRAYLEN(rx), HITAG_T_WAIT_FIRST, ledcontrol) == -1) {
|
||||
|
||||
hitagS_stop_clock();
|
||||
set_tracing(false);
|
||||
lf_finalize(ledcontrol);
|
||||
reply_ng(CMD_LF_HITAGS_READ, PM3_ERFTRANS, NULL, 0);
|
||||
return;
|
||||
status = PM3_ERFTRANS;
|
||||
goto read_end;
|
||||
}
|
||||
|
||||
int pageNum = 0;
|
||||
|
@ -1445,9 +1487,10 @@ void ReadHitagS(const lf_hitag_data_t *payload, bool ledcontrol) {
|
|||
|
||||
sendReceiveHitagS(tx, txlen, rx, ARRAYLEN(rx), &rxlen, HITAG_T_WAIT_SC, ledcontrol, false);
|
||||
|
||||
if (rxlen == 0) {
|
||||
if (rxlen != 40) {
|
||||
Dbprintf("Read page failed!");
|
||||
break;
|
||||
status = PM3_ERFTRANS;
|
||||
goto read_end;
|
||||
}
|
||||
|
||||
//save received data - 40 bits
|
||||
|
@ -1499,10 +1542,11 @@ void ReadHitagS(const lf_hitag_data_t *payload, bool ledcontrol) {
|
|||
}
|
||||
}
|
||||
|
||||
read_end:
|
||||
hitagS_stop_clock();
|
||||
set_tracing(false);
|
||||
lf_finalize(ledcontrol);
|
||||
reply_ng(CMD_LF_HITAGS_READ, PM3_SUCCESS, (uint8_t *)tag.pages, sizeof(tag.pages));
|
||||
reply_ng(CMD_LF_HITAGS_READ, status, (uint8_t *)tag.pages, sizeof(tag.pages));
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
|
@ -676,11 +676,11 @@ static size_t concatbits(uint8_t *dst, size_t dstskip, const uint8_t *src, size_
|
|||
static int CmdEM410xClone(const char *Cmd) {
|
||||
CLIParserContext *ctx;
|
||||
CLIParserInit(&ctx, "lf em 410x clone",
|
||||
"clone a EM410x ID to a T55x7, Q5/T5555, EM4305/4469 or Hitag S/8211 tag.",
|
||||
"clone a EM410x ID to a T55x7, Q5/T5555, EM4305/4469 or Hitag S/8211/8268/8310 tag.",
|
||||
"lf em 410x clone --id 0F0368568B -> encode for T55x7 tag\n"
|
||||
"lf em 410x clone --id 0F0368568B --q5 -> encode for Q5/T5555 tag\n"
|
||||
"lf em 410x clone --id 0F0368568B --em -> encode for EM4305/4469\n"
|
||||
"lf em 410x clone --id 0F0368568B --hs -> encode for Hitag S/8211"
|
||||
"lf em 410x clone --id 0F0368568B --hts -> encode for Hitag S/8211/8268/8310"
|
||||
);
|
||||
|
||||
void *argtable[] = {
|
||||
|
@ -689,7 +689,7 @@ static int CmdEM410xClone(const char *Cmd) {
|
|||
arg_str1(NULL, "id", "<hex>", "EM Tag ID number (5 hex bytes)"),
|
||||
arg_lit0(NULL, "q5", "optional - specify writing to Q5/T5555 tag"),
|
||||
arg_lit0(NULL, "em", "optional - specify writing to EM4305/4469 tag"),
|
||||
arg_lit0(NULL, "hs", "optional - specify writing to Hitag S/8211 tag"),
|
||||
arg_lit0(NULL, "hts", "optional - specify writing to Hitag S/8211/8268/8310 tag"),
|
||||
arg_lit0(NULL, "electra", "optional - add Electra blocks to tag"),
|
||||
arg_param_end
|
||||
};
|
||||
|
@ -702,16 +702,16 @@ static int CmdEM410xClone(const char *Cmd) {
|
|||
CLIGetHexWithReturn(ctx, 2, uid, &uid_len);
|
||||
bool q5 = arg_get_lit(ctx, 3);
|
||||
bool em = arg_get_lit(ctx, 4);
|
||||
bool hs = arg_get_lit(ctx, 5);
|
||||
bool hts = arg_get_lit(ctx, 5);
|
||||
bool add_electra = arg_get_lit(ctx, 6);
|
||||
CLIParserFree(ctx);
|
||||
|
||||
if (q5 + em + hs > 1) {
|
||||
if (q5 + em + hts > 1) {
|
||||
PrintAndLogEx(FAILED, "Only specify one tag Type");
|
||||
return PM3_EINVARG;
|
||||
}
|
||||
|
||||
if (hs) {
|
||||
if (hts) {
|
||||
if (IfPm3Hitag() == false) {
|
||||
PrintAndLogEx(FAILED, "Device not compiled to support Hitag");
|
||||
return PM3_EINVARG;
|
||||
|
@ -730,7 +730,7 @@ static int CmdEM410xClone(const char *Cmd) {
|
|||
|
||||
uint64_t id = bytes_to_num(uid, uid_len);
|
||||
PrintAndLogEx(SUCCESS, "Preparing to clone EM4102 to " _YELLOW_("%s") " tag with EM Tag ID " _GREEN_("%010" PRIX64) " (RF/%d)",
|
||||
q5 ? "Q5/T5555" : (em ? "EM4305/4469" : (hs ? "Hitag S/8211" : "T55x7")), id, clk);
|
||||
q5 ? "Q5/T5555" : (em ? "EM4305/4469" : (hts ? "Hitag S/82xx" : "T55x7")), id, clk);
|
||||
|
||||
uint8_t data[HITAG_BLOCK_SIZE * 2] = {0xFF, 0x80}; // EM410X_HEADER 9 bits of one
|
||||
uint32_t databits = 9;
|
||||
|
@ -754,7 +754,7 @@ static int CmdEM410xClone(const char *Cmd) {
|
|||
clearCommandBuffer();
|
||||
PacketResponseNG resp;
|
||||
|
||||
if (hs) {
|
||||
if (hts) {
|
||||
lf_hitag_data_t packet;
|
||||
memset(&packet, 0, sizeof(packet));
|
||||
|
||||
|
@ -791,7 +791,8 @@ static int CmdEM410xClone(const char *Cmd) {
|
|||
break;
|
||||
}
|
||||
|
||||
packet.cmd = WHTSF_PLAIN;
|
||||
packet.cmd = WHTSF_82xx;
|
||||
memcpy(packet.pwd, (uint8_t[]){0xBB, 0xDD, 0x33, 0x99}, 4);
|
||||
SendCommandNG(CMD_LF_HITAGS_WRITE, (uint8_t *)&packet, sizeof(packet));
|
||||
if (WaitForResponseTimeout(CMD_LF_HITAGS_WRITE, &resp, 4000) == false) {
|
||||
PrintAndLogEx(WARNING, "timeout while waiting for reply.");
|
||||
|
|
|
@ -43,8 +43,11 @@ static int CmdLFHitagSRead(const char *Cmd) {
|
|||
"Read Hitag S memory.\n\n"
|
||||
" Crypto mode: \n"
|
||||
" - key format ISK high + ISK low\n"
|
||||
" - default key 4F4E4D494B52 (ONMIKR)\n",
|
||||
" lf hitag hts read -> Hitag S, plain mode\n"
|
||||
" - default key 4F4E4D494B52 (ONMIKR)\n\n"
|
||||
" 8268/8310 password mode: \n"
|
||||
" - default password BBDD3399\n",
|
||||
" lf hitag hts read -> Hitag S/8211, plain mode\n"
|
||||
" lf hitag hts read --8 -k BBDD3399 -> 8268/8310, password mode\n"
|
||||
" lf hitag hts read --nrar 0102030411223344 -> Hitag S, challenge mode\n"
|
||||
" lf hitag hts read --crypto -> Hitag S, crypto mode, def key\n"
|
||||
" lf hitag hts read -k 4F4E4D494B52 -> Hitag S, crypto mode\n\n"
|
||||
|
@ -53,8 +56,9 @@ static int CmdLFHitagSRead(const char *Cmd) {
|
|||
void *argtable[] = {
|
||||
arg_param_begin,
|
||||
arg_str0(NULL, "nrar", "<hex>", "nonce / answer writer, 8 hex bytes"),
|
||||
arg_lit0(NULL, "8", "8268/8310 mode"),
|
||||
arg_lit0(NULL, "crypto", "crypto mode"),
|
||||
arg_str0("k", "key", "<hex>", "key, 4 or 6 hex bytes"),
|
||||
arg_str0("k", "key", "<hex>", "pwd or key, 4 or 6 hex bytes"),
|
||||
arg_param_end
|
||||
};
|
||||
CLIExecWithReturn(ctx, Cmd, argtable, true);
|
||||
|
@ -71,12 +75,13 @@ static int CmdLFHitagSRead(const char *Cmd) {
|
|||
}
|
||||
|
||||
bool use_nrar = nrar_len > 0;
|
||||
bool use_crypto = arg_get_lit(ctx, 2);
|
||||
bool use_82xx = arg_get_lit(ctx, 2);
|
||||
bool use_crypto = arg_get_lit(ctx, 3);
|
||||
|
||||
uint8_t key[6];
|
||||
int key_len = 0;
|
||||
|
||||
res = CLIParamHexToBuf(arg_get_str(ctx, 3), key, sizeof(key), &key_len);
|
||||
res = CLIParamHexToBuf(arg_get_str(ctx, 4), key, sizeof(key), &key_len);
|
||||
if (res != 0) {
|
||||
CLIParserFree(ctx);
|
||||
return PM3_EINVARG;
|
||||
|
@ -84,8 +89,8 @@ static int CmdLFHitagSRead(const char *Cmd) {
|
|||
|
||||
CLIParserFree(ctx);
|
||||
|
||||
if (key_len && key_len != HITAGS_CRYPTOKEY_SIZE) {
|
||||
PrintAndLogEx(WARNING, "Wrong KEY len expected %d, got %d", HITAGS_CRYPTOKEY_SIZE, key_len);
|
||||
if (key_len != 0 && key_len != 4 && key_len != 6) {
|
||||
PrintAndLogEx(WARNING, "Wrong KEY len expected 0, 4 or 6, got %d", key_len);
|
||||
return PM3_EINVARG;
|
||||
}
|
||||
|
||||
|
@ -94,13 +99,24 @@ static int CmdLFHitagSRead(const char *Cmd) {
|
|||
return PM3_EINVARG;
|
||||
}
|
||||
|
||||
if (!key_len && use_crypto) {
|
||||
// complete options
|
||||
if (key_len == 4) {
|
||||
use_82xx = true;
|
||||
}
|
||||
if (key_len == 6) {
|
||||
use_crypto = true;
|
||||
}
|
||||
if ((key_len == 0) && use_82xx) {
|
||||
memcpy(key, (uint8_t[]){0xBB, 0xDD, 0x33, 0x99}, 4);
|
||||
key_len = 4;
|
||||
}
|
||||
if ((key_len == 0) && use_crypto) {
|
||||
memcpy(key, "ONMIKR", 6);
|
||||
key_len = 6;
|
||||
}
|
||||
|
||||
// check coherence
|
||||
uint8_t auth_methods = (use_plain + use_nrar + use_crypto);
|
||||
uint8_t auth_methods = (use_plain + use_nrar + use_82xx + use_crypto);
|
||||
if (auth_methods > 1) {
|
||||
PrintAndLogEx(WARNING, "Specify only one authentication mode");
|
||||
return PM3_EINVARG;
|
||||
|
@ -118,6 +134,11 @@ static int CmdLFHitagSRead(const char *Cmd) {
|
|||
memcpy(packet.NrAr, nrar, sizeof(packet.NrAr));
|
||||
}
|
||||
|
||||
if (use_82xx) {
|
||||
packet.cmd = RHTSF_82xx;
|
||||
memcpy(packet.pwd, key, sizeof(packet.pwd));
|
||||
}
|
||||
|
||||
if (use_crypto) {
|
||||
packet.cmd = RHTSF_KEY;
|
||||
memcpy(packet.key, key, sizeof(packet.key));
|
||||
|
@ -168,8 +189,11 @@ static int CmdLFHitagSWrite(const char *Cmd) {
|
|||
"Write a page in Hitag S memory.\n"
|
||||
" Crypto mode: \n"
|
||||
" - key format ISK high + ISK low\n"
|
||||
" - default key 4F4E4D494B52 (ONMIKR)\n",
|
||||
" lf hitag hts write -p 6 -d 01020304 -> Hitag S, plain mode\n"
|
||||
" - default key 4F4E4D494B52 (ONMIKR)\n\n"
|
||||
" 8268/8310 password mode: \n"
|
||||
" - default password BBDD3399\n",
|
||||
" lf hitag hts write -p 6 -d 01020304 -> Hitag S/8211, plain mode\n"
|
||||
" lf hitag hts write -p 6 -d 01020304 --8 -k BBDD3399 -> 8268/8310, password mode\n"
|
||||
" lf hitag hts write -p 6 -d 01020304 --nrar 0102030411223344 -> Hitag S, challenge mode\n"
|
||||
" lf hitag hts write -p 6 -d 01020304 --crypto -> Hitag S, crypto mode, default key\n"
|
||||
" lf hitag hts write -p 6 -d 01020304 -k 4F4E4D494B52 -> Hitag S, crypto mode\n\n"
|
||||
|
@ -178,8 +202,9 @@ static int CmdLFHitagSWrite(const char *Cmd) {
|
|||
void *argtable[] = {
|
||||
arg_param_begin,
|
||||
arg_str0(NULL, "nrar", "<hex>", "nonce / answer writer, 8 hex bytes"),
|
||||
arg_lit0(NULL, "8", "8268/8310 mode"),
|
||||
arg_lit0(NULL, "crypto", "crypto mode"),
|
||||
arg_str0("k", "key", "<hex>", "key, 6 hex bytes"),
|
||||
arg_str0("k", "key", "<hex>", "pwd or key, 4 or 6 hex bytes"),
|
||||
arg_int1("p", "page", "<dec>", "page address to write to"),
|
||||
arg_str1("d", "data", "<hex>", "data, 4 hex bytes"),
|
||||
arg_param_end
|
||||
|
@ -198,23 +223,24 @@ static int CmdLFHitagSWrite(const char *Cmd) {
|
|||
}
|
||||
|
||||
bool use_nrar = nrar_len > 0;
|
||||
bool use_crypto = arg_get_lit(ctx, 2);
|
||||
bool use_82xx = arg_get_lit(ctx, 2);
|
||||
bool use_crypto = arg_get_lit(ctx, 3);
|
||||
|
||||
uint8_t key[6];
|
||||
int key_len = 0;
|
||||
|
||||
res = CLIParamHexToBuf(arg_get_str(ctx, 3), key, sizeof(key), &key_len);
|
||||
res = CLIParamHexToBuf(arg_get_str(ctx, 4), key, sizeof(key), &key_len);
|
||||
if (res != 0) {
|
||||
CLIParserFree(ctx);
|
||||
return PM3_EINVARG;
|
||||
}
|
||||
|
||||
int page = arg_get_int_def(ctx, 4, 0);
|
||||
int page = arg_get_int_def(ctx, 5, 0);
|
||||
|
||||
uint8_t data[4];
|
||||
int data_len = 0;
|
||||
|
||||
res = CLIParamHexToBuf(arg_get_str(ctx, 5), data, sizeof(data), &data_len);
|
||||
res = CLIParamHexToBuf(arg_get_str(ctx, 6), data, sizeof(data), &data_len);
|
||||
if (res != 0) {
|
||||
CLIParserFree(ctx);
|
||||
return PM3_EINVARG;
|
||||
|
@ -222,8 +248,8 @@ static int CmdLFHitagSWrite(const char *Cmd) {
|
|||
|
||||
CLIParserFree(ctx);
|
||||
|
||||
if (key_len && key_len != HITAGS_CRYPTOKEY_SIZE) {
|
||||
PrintAndLogEx(WARNING, "Wrong KEY len expected %d, got %d", HITAGS_CRYPTOKEY_SIZE, key_len);
|
||||
if (key_len != 0 && key_len != 4 && key_len != 6) {
|
||||
PrintAndLogEx(WARNING, "Wrong KEY len expected 0, 4 or 6, got %d", key_len);
|
||||
return PM3_EINVARG;
|
||||
}
|
||||
|
||||
|
@ -232,13 +258,24 @@ static int CmdLFHitagSWrite(const char *Cmd) {
|
|||
return PM3_EINVARG;
|
||||
}
|
||||
|
||||
if (!key_len && use_crypto) {
|
||||
// complete options
|
||||
if (key_len == 4) {
|
||||
use_82xx = true;
|
||||
}
|
||||
if (key_len == 6) {
|
||||
use_crypto = true;
|
||||
}
|
||||
if ((key_len == 0) && use_82xx) {
|
||||
memcpy(key, (uint8_t[]){0xBB, 0xDD, 0x33, 0x99}, 4);
|
||||
key_len = 4;
|
||||
}
|
||||
if ((key_len == 0) && use_crypto) {
|
||||
memcpy(key, "ONMIKR", 6);
|
||||
key_len = 6;
|
||||
}
|
||||
|
||||
// check coherence
|
||||
uint8_t auth_methods = (use_plain + use_nrar + use_crypto);
|
||||
uint8_t auth_methods = (use_plain + use_nrar + use_82xx + use_crypto);
|
||||
if (auth_methods > 1) {
|
||||
PrintAndLogEx(WARNING, "Specify only one authentication mode");
|
||||
return PM3_EINVARG;
|
||||
|
@ -257,6 +294,11 @@ static int CmdLFHitagSWrite(const char *Cmd) {
|
|||
memcpy(packet.NrAr, nrar, sizeof(packet.NrAr));
|
||||
}
|
||||
|
||||
if (use_82xx) {
|
||||
packet.cmd = WHTSF_82xx;
|
||||
memcpy(packet.pwd, key, sizeof(packet.pwd));
|
||||
}
|
||||
|
||||
if (use_crypto) {
|
||||
packet.cmd = WHTSF_KEY;
|
||||
memcpy(packet.key, key, sizeof(packet.key));
|
||||
|
@ -292,13 +334,10 @@ static int CmdLFHitagSList(const char *Cmd) {
|
|||
static command_t CommandTable[] = {
|
||||
{"help", CmdHelp, AlwaysAvailable, "This help"},
|
||||
{"list", CmdLFHitagSList, AlwaysAvailable, "List Hitag S trace history"},
|
||||
{
|
||||
"-----------", CmdHelp, IfPm3Hitag, "----------------------- " _CYAN_(
|
||||
"General") " ------------------------"
|
||||
},
|
||||
{"-----------", CmdHelp, IfPm3Hitag, "----------------------- " _CYAN_("General") " ------------------------"},
|
||||
{"read", CmdLFHitagSRead, IfPm3Hitag, "Read Hitag S memory"},
|
||||
{"write", CmdLFHitagSWrite, IfPm3Hitag, "Write Hitag S page"},
|
||||
{NULL, NULL, 0, NULL}
|
||||
{NULL, NULL, 0, NULL}
|
||||
};
|
||||
|
||||
static int CmdHelp(const char *Cmd) {
|
||||
|
|
|
@ -48,6 +48,8 @@
|
|||
typedef enum {
|
||||
RHTSF_PLAIN,
|
||||
WHTSF_PLAIN,
|
||||
RHTSF_82xx,
|
||||
WHTSF_82xx,
|
||||
RHTSF_CHALLENGE,
|
||||
WHTSF_CHALLENGE,
|
||||
RHTSF_KEY,
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue