From 81740aa519046d407faa39411973347db593f0b7 Mon Sep 17 00:00:00 2001 From: iceman1001 Date: Tue, 20 Jan 2015 21:29:55 +0100 Subject: [PATCH] STEP 3 - the actual new files for Ultralight. ADD: script remagic.lua -- a script to make a "dead" Mifare s50 generation 1 alive again. ADD: tracetest.lua - This script will load several traces files in ../traces/ folder and do "data load" "lf search" ADD: test_t55x7_psk.lua - iterates thru a lot of calls to check the new psk demods. all new scripts implements the "-h" for help text. --- client/cmdhfmfu.c | 649 ++++++++++++++++++++++++++++++ client/cmdhfmfu.h | 19 + client/scripts/remagic.lua | 63 +++ client/scripts/test_t55x7_psk.lua | 173 ++++++++ client/scripts/tracetest.lua | 132 ++++++ 5 files changed, 1036 insertions(+) create mode 100644 client/cmdhfmfu.c create mode 100644 client/cmdhfmfu.h create mode 100644 client/scripts/remagic.lua create mode 100644 client/scripts/test_t55x7_psk.lua create mode 100644 client/scripts/tracetest.lua diff --git a/client/cmdhfmfu.c b/client/cmdhfmfu.c new file mode 100644 index 00000000..8bd6ec87 --- /dev/null +++ b/client/cmdhfmfu.c @@ -0,0 +1,649 @@ +//----------------------------------------------------------------------------- +// Ultralight Code (c) 2013,2014 Midnitesnake & Andy Davies of Pentura +// +// 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 MIFARE ULTRALIGHT (C) commands +//----------------------------------------------------------------------------- +#include +#include "cmdhfmfu.h" +#include "cmdhfmf.h" +#include "cmdhf14a.h" + + +#define MAX_ULTRA_BLOCKS 0x0f +#define MAX_ULTRAC_BLOCKS 0x2f +//#define MAX_ULTRAC_BLOCKS 0x2c +uint8_t key1_blnk_data[16] = { 0x00 }; +uint8_t key2_defa_data[16] = { 0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09,0x0a,0x0b,0x0c,0x0d,0x0e,0x0f }; +uint8_t key3_3des_data[16] = { 0x49,0x45,0x4D,0x4B,0x41,0x45,0x52,0x42,0x21,0x4E,0x41,0x43,0x55,0x4F,0x59,0x46 }; +uint8_t key4_nfc_data[16] = { 0x42,0x52,0x45,0x41,0x4b,0x4d,0x45,0x49,0x46,0x59,0x4f,0x55,0x43,0x41,0x4e,0x21 }; +uint8_t key5_ones_data[16] = { 0x01 }; + +static int CmdHelp(const char *Cmd); + +int CmdHF14AMfUInfo(const char *Cmd){ + + uint8_t datatemp[7] = {0x00}; + uint8_t isOK = 0; + uint8_t *data = NULL; + + UsbCommand c = {CMD_MIFAREU_READCARD, {0, 4}}; + SendCommand(&c); + UsbCommand resp; + + if (WaitForResponseTimeout(CMD_ACK, &resp, 1500)) { + isOK = resp.arg[0] & 0xff; + data = resp.d.asBytes; + + if (!isOK) { + PrintAndLog("Error reading from tag"); + return -1; + } + } else { + PrintAndLog("Command execute timed out"); + return -1; + } + + PrintAndLog(""); + PrintAndLog("-- Mifare Ultralight / Ultralight-C Tag Information ---------"); + PrintAndLog("-------------------------------------------------------------"); + + // UID + memcpy( datatemp, data, 3); + memcpy( datatemp+3, data+4, 4); + + PrintAndLog("MANUFACTURER : %s", getTagInfo(datatemp[0])); + PrintAndLog(" UID : %s ", sprint_hex(datatemp, 7)); + // BBC + // CT (cascade tag byte) 0x88 xor SN0 xor SN1 xor SN2 + int crc0 = 0x88 ^ data[0] ^ data[1] ^data[2]; + if ( data[3] == crc0 ) + PrintAndLog(" BCC0 : %02x - Ok", data[3]); + else + PrintAndLog(" BCC0 : %02x - crc should be %02x", data[3], crc0); + + int crc1 = data[4] ^ data[5] ^ data[6] ^data[7]; + if ( data[8] == crc1 ) + PrintAndLog(" BCC1 : %02x - Ok", data[8]); + else + PrintAndLog(" BCC1 : %02x - crc should be %02x", data[8], crc1 ); + + PrintAndLog(" Internal : %s ", sprint_hex(data + 9, 1)); + + memcpy(datatemp, data+10, 2); + PrintAndLog(" Lock : %s - %s", sprint_hex(datatemp, 2),printBits( 2, &datatemp) ); + PrintAndLog(" OneTimePad : %s ", sprint_hex(data + 3*4, 4)); + PrintAndLog(""); + + int len = CmdHF14AMfucAuth("K 0"); +// PrintAndLog("CODE: %d",len); + + PrintAndLog("Seems to be a Ultralight %s", (len==0) ? "-C" :""); + return 0; +} + +// +// Mifare Ultralight Write Single Block +// +int CmdHF14AMfUWrBl(const char *Cmd){ + uint8_t blockNo = -1; + bool chinese_card = FALSE; + uint8_t bldata[16] = {0x00}; + UsbCommand resp; + + char cmdp = param_getchar(Cmd, 0); + if (strlen(Cmd) < 3 || cmdp == 'h' || cmdp == 'H') { + PrintAndLog("Usage: hf mfu wrbl [w]"); + PrintAndLog(" [block number]"); + PrintAndLog(" [block data] - (8 hex symbols)"); + PrintAndLog(" [w] - Chinese magic ultralight tag"); + PrintAndLog(""); + PrintAndLog(" sample: hf mfu wrbl 0 01020304"); + PrintAndLog(""); + return 0; + } + + blockNo = param_get8(Cmd, 0); + + if (blockNo > MAX_ULTRA_BLOCKS){ + PrintAndLog("Error: Maximum number of blocks is 15 for Ultralight Cards!"); + return 1; + } + + if (param_gethex(Cmd, 1, bldata, 8)) { + PrintAndLog("Block data must include 8 HEX symbols"); + return 1; + } + + if (strchr(Cmd,'w') != 0 || strchr(Cmd,'W') != 0 ) { + chinese_card = TRUE; + } + + if ( blockNo <= 3) { + if (!chinese_card){ + PrintAndLog("Access Denied"); + } else { + PrintAndLog("--specialblock no:%02x", blockNo); + PrintAndLog("--data: %s", sprint_hex(bldata, 4)); + UsbCommand d = {CMD_MIFAREU_WRITEBL, {blockNo}}; + memcpy(d.d.asBytes,bldata, 4); + SendCommand(&d); + if (WaitForResponseTimeout(CMD_ACK,&resp,1500)) { + uint8_t isOK = resp.arg[0] & 0xff; + PrintAndLog("isOk:%02x", isOK); + } else { + PrintAndLog("Command execute timeout"); + } + } + } else { + PrintAndLog("--block no:%02x", blockNo); + PrintAndLog("--data: %s", sprint_hex(bldata, 4)); + UsbCommand e = {CMD_MIFAREU_WRITEBL, {blockNo}}; + memcpy(e.d.asBytes,bldata, 4); + SendCommand(&e); + if (WaitForResponseTimeout(CMD_ACK,&resp,1500)) { + uint8_t isOK = resp.arg[0] & 0xff; + PrintAndLog("isOk:%02x", isOK); + } else { + PrintAndLog("Command execute timeout"); + } + } + return 0; +} + +// +// Mifare Ultralight Read Single Block +// +int CmdHF14AMfURdBl(const char *Cmd){ + + uint8_t blockNo = -1; + + char cmdp = param_getchar(Cmd, 0); + + if (strlen(Cmd) < 1 || cmdp == 'h' || cmdp == 'H') { + PrintAndLog("Usage: hf mfu rdbl "); + PrintAndLog(" sample: hfu mfu rdbl 0"); + return 0; + } + + blockNo = param_get8(Cmd, 0); + + if (blockNo > MAX_ULTRA_BLOCKS){ + PrintAndLog("Error: Maximum number of blocks is 15 for Ultralight Cards!"); + return 1; + } + + PrintAndLog("--block no:0x%02X (%d)", (int)blockNo, blockNo); + UsbCommand c = {CMD_MIFAREU_READBL, {blockNo}}; + SendCommand(&c); + + UsbCommand resp; + if (WaitForResponseTimeout(CMD_ACK,&resp,1500)) { + uint8_t isOK = resp.arg[0] & 0xff; + uint8_t * data = resp.d.asBytes; + + PrintAndLog("isOk: %02x", isOK); + + if (isOK) + PrintAndLog("Data: %s", sprint_hex(data, 4)); + } else { + PrintAndLog("Command execute timeout"); + } + return 0; +} + +// +// Mifare Ultralight / Ultralight-C; Read and Dump Card Contents +// +int CmdHF14AMfUDump(const char *Cmd){ + + FILE *fout; + char filename[FILE_PATH_SIZE] = {0x00}; + char * fnameptr = filename; + + uint8_t *lockbytes_t = NULL; + uint8_t lockbytes[2] = {0x00}; + + uint8_t *lockbytes_t2 = NULL; + uint8_t lockbytes2[2] = {0x00}; + + bool bit[16] = {0x00}; + bool bit2[16] = {0x00}; + + int i; + uint8_t BlockNo = 0; + int Pages = 16; + + bool tmplockbit = false; + uint8_t isOK = 0; + uint8_t *data = NULL; + + char cmdp = param_getchar(Cmd, 0); + + if (cmdp == 'h' || cmdp == 'H') { + PrintAndLog("Reads all pages from Mifare Ultralight or Ultralight-C tag."); + PrintAndLog("It saves binary dump into the file `filename.bin` or `cardUID.bin`"); + PrintAndLog("Usage: hf mfu dump "); + PrintAndLog(" optional cardtype c == Ultralight-C, if not defaults to Ultralight"); + PrintAndLog(" sample: hf mfu dump"); + PrintAndLog(" : hf mfu dump myfile"); + PrintAndLog(" : hf mfu dump c myfile"); + return 0; + } + + // UL or UL-C? + Pages = (cmdp == 'c' || cmdp == 'C') ? 44 : 16; + + PrintAndLog("Dumping Ultralight%s Card Data...", (Pages ==16)?"":"-C"); + + UsbCommand c = {CMD_MIFAREU_READCARD, {BlockNo,Pages}}; + SendCommand(&c); + UsbCommand resp; + + if (WaitForResponseTimeout(CMD_ACK,&resp,1500)) { + isOK = resp.arg[0] & 0xff; + if (!isOK) { + PrintAndLog("Command error"); + return 0; + } + data = resp.d.asBytes; + } else { + PrintAndLog("Command execute timeout"); + return 0; + } + + // Load lock bytes. + int j = 0; + + lockbytes_t = data + 8; + lockbytes[0] = lockbytes_t[2]; + lockbytes[1] = lockbytes_t[3]; + for(j = 0; j < 16; j++){ + bit[j] = lockbytes[j/8] & ( 1 <<(7-j%8)); + } + + // Load bottom lockbytes if available + if ( Pages == 44 ) { + + lockbytes_t2 = data + (40*4); + lockbytes2[0] = lockbytes_t2[2]; + lockbytes2[1] = lockbytes_t2[3]; + for (j = 0; j < 16; j++) { + bit2[j] = lockbytes2[j/8] & ( 1 <<(7-j%8)); + } + } + + for (i = 0; i < Pages; ++i) { + + if ( i < 3 ) { + PrintAndLog("Block %02x:%s ", i,sprint_hex(data + i * 4, 4)); + continue; + } + + switch(i){ + case 3: tmplockbit = bit[4]; break; + case 4: tmplockbit = bit[3]; break; + case 5: tmplockbit = bit[2]; break; + case 6: tmplockbit = bit[1]; break; + case 7: tmplockbit = bit[0]; break; + case 8: tmplockbit = bit[15]; break; + case 9: tmplockbit = bit[14]; break; + case 10: tmplockbit = bit[13]; break; + case 11: tmplockbit = bit[12]; break; + case 12: tmplockbit = bit[11]; break; + case 13: tmplockbit = bit[10]; break; + case 14: tmplockbit = bit[9]; break; + case 15: tmplockbit = bit[8]; break; + case 16: + case 17: + case 18: + case 19: tmplockbit = bit2[6]; break; + case 20: + case 21: + case 22: + case 23: tmplockbit = bit2[5]; break; + case 24: + case 25: + case 26: + case 27: tmplockbit = bit2[4]; break; + case 28: + case 29: + case 30: + case 31: tmplockbit = bit2[2]; break; + case 32: + case 33: + case 34: + case 35: tmplockbit = bit2[1]; break; + case 36: + case 37: + case 38: + case 39: tmplockbit = bit2[0]; break; + case 40: tmplockbit = bit2[12]; break; + case 41: tmplockbit = bit2[11]; break; + case 42: tmplockbit = bit2[10]; break; //auth0 + case 43: tmplockbit = bit2[9]; break; //auth1 + default: break; + } + PrintAndLog("Block %02x:%s [%d]", i,sprint_hex(data + i * 4, 4),tmplockbit); + } + + int len = 0; + if ( Pages == 16 ) + len = param_getstr(Cmd,0,filename); + else + len = param_getstr(Cmd,1,filename); + + if (len > FILE_PATH_SIZE) len = FILE_PATH_SIZE; + + // user supplied filename? + if (len < 1) { + + // UID = data 0-1-2 4-5-6-7 (skips a beat) + sprintf(fnameptr, "%02X", data[0]); + fnameptr += 2; + sprintf(fnameptr, "%02X", data[1]); + fnameptr += 2; + sprintf(fnameptr, "%02X", data[2]); + fnameptr += 2; + sprintf(fnameptr, "%02X", data[4]); + fnameptr += 2; + sprintf(fnameptr, "%02X", data[5]); + fnameptr += 2; + sprintf(fnameptr, "%02X", data[6]); + fnameptr += 2; + sprintf(fnameptr, "%02X", data[7]); + fnameptr += 2; + + } else { + fnameptr += len; + } + + // add file extension + sprintf(fnameptr, ".bin"); + + if ((fout = fopen(filename,"wb")) == NULL) { + PrintAndLog("Could not create file name %s", filename); + return 1; + } + fwrite( data, 1, Pages*4, fout ); + fclose(fout); + + PrintAndLog("Dumped %d pages, wrote %d bytes to %s", Pages, Pages*4, filename); + return 0; +} + +// Needed to Authenticate to Ultralight C tags +void rol (uint8_t *data, const size_t len){ + uint8_t first = data[0]; + for (size_t i = 0; i < len-1; i++) { + data[i] = data[i+1]; + } + data[len-1] = first; +} + +//------------------------------------------------------------------------------- +// Ultralight C Methods +//------------------------------------------------------------------------------- + +// +// Ultralight C Authentication Demo {currently uses hard-coded key} +// +int CmdHF14AMfucAuth(const char *Cmd){ + + uint8_t blockNo = 0, keyNo = 0; + uint8_t e_RndB[8] = {0x00}; + uint32_t cuid = 0; + unsigned char RndARndB[16] = {0x00}; + uint8_t key[16] = {0x00}; + DES_cblock RndA, RndB; + DES_cblock iv; + DES_key_schedule ks1,ks2; + DES_cblock key1,key2; + + char cmdp = param_getchar(Cmd, 0); + // + memset(iv, 0, 8); + + if (cmdp == 'h' || cmdp == 'H') { + PrintAndLog("Usage: hf mfu cauth k "); + PrintAndLog(" 1 = all zeros key"); + PrintAndLog(" 2 = 0x00-0x0F key"); + PrintAndLog(" 3 = nfc key"); + PrintAndLog(" 4 = all ones key"); + PrintAndLog(" defaults to 3DES standard key"); + PrintAndLog(" sample : hf mfu cauth k"); + PrintAndLog(" : hf mfu cauth k 3"); + return 0; + } + + //Change key to user defined one + if (cmdp == 'k' || cmdp == 'K'){ + + keyNo = param_get8(Cmd, 1); + + switch(keyNo){ + case 0: + memcpy(key,key1_blnk_data,16); + break; + case 1: + memcpy(key,key2_defa_data,16); + break; + case 2: + memcpy(key,key4_nfc_data,16); + break; + case 3: + memcpy(key,key5_ones_data,16); + break; + default: + memcpy(key,key3_3des_data,16); + break; + } + } else { + memcpy(key,key3_3des_data,16); + } + + memcpy(key1,key,8); + memcpy(key2,key+8,8); + DES_set_key((DES_cblock *)key1,&ks1); + DES_set_key((DES_cblock *)key2,&ks2); + + //Auth1 + UsbCommand c = {CMD_MIFAREUC_AUTH1, {blockNo}}; + SendCommand(&c); + UsbCommand resp; + if (WaitForResponseTimeout(CMD_ACK,&resp,1500)) { + uint8_t isOK = resp.arg[0] & 0xff; + cuid = resp.arg[1]; + uint8_t * data= resp.d.asBytes; + + if (isOK){ + PrintAndLog("enc(RndB):%s", sprint_hex(data+1, 8)); + memcpy(e_RndB,data+1,8); + } else { + return 2; // auth failed. + } + } else { + PrintAndLog("Command execute timeout"); + return 1; + } + + //Do crypto magic + DES_random_key(&RndA); + DES_ede2_cbc_encrypt(e_RndB,RndB,sizeof(e_RndB),&ks1,&ks2,&iv,0); + PrintAndLog(" RndB:%s",sprint_hex(RndB, 8)); + PrintAndLog(" RndA:%s",sprint_hex(RndA, 8)); + rol(RndB,8); + memcpy(RndARndB,RndA,8); + memcpy(RndARndB+8,RndB,8); + PrintAndLog(" RA+B:%s",sprint_hex(RndARndB, 16)); + DES_ede2_cbc_encrypt(RndARndB,RndARndB,sizeof(RndARndB),&ks1,&ks2,&e_RndB,1); + PrintAndLog("enc(RA+B):%s",sprint_hex(RndARndB, 16)); + + //Auth2 + UsbCommand d = {CMD_MIFAREUC_AUTH2, {cuid}}; + memcpy(d.d.asBytes,RndARndB, 16); + SendCommand(&d); + + UsbCommand respb; + if (WaitForResponseTimeout(CMD_ACK,&respb,1500)) { + uint8_t isOK = respb.arg[0] & 0xff; + uint8_t * data2= respb.d.asBytes; + + if (isOK){ + PrintAndLog("enc(RndA'):%s", sprint_hex(data2+1, 8)); + } else { + return 2; + } + + } else { + PrintAndLog("Command execute timeout"); + return 1; + } + return 0; +} + +// +// Ultralight C Read Single Block +// +int CmdHF14AMfUCRdBl(const char *Cmd) +{ + uint8_t blockNo = -1; + char cmdp = param_getchar(Cmd, 0); + + if (strlen(Cmd) < 1 || cmdp == 'h' || cmdp == 'H') { + PrintAndLog("Usage: hf mfu crdbl "); + PrintAndLog(" sample: hf mfu crdbl 0"); + return 0; + } + + blockNo = param_get8(Cmd, 0); + if (blockNo < 0) { + PrintAndLog("Wrong block number"); + return 1; + } + + if (blockNo > MAX_ULTRAC_BLOCKS ){ + PrintAndLog("Error: Maximum number of readable blocks is 47 for Ultralight-C Cards!"); + return 1; + } + + PrintAndLog("--block no: 0x%02X (%d)", (int)blockNo, blockNo); + + //Read Block + UsbCommand e = {CMD_MIFAREU_READBL, {blockNo}}; + SendCommand(&e); + UsbCommand resp_c; + if (WaitForResponseTimeout(CMD_ACK,&resp_c,1500)) { + uint8_t isOK = resp_c.arg[0] & 0xff; + uint8_t *data = resp_c.d.asBytes; + + PrintAndLog("isOk: %02x", isOK); + if (isOK) + PrintAndLog("Data: %s", sprint_hex(data, 4)); + + } else { + PrintAndLog("Command execute timeout"); + } + return 0; +} + +// +// Mifare Ultralight C Write Single Block +// +int CmdHF14AMfUCWrBl(const char *Cmd){ + + uint8_t blockNo = -1; + bool chinese_card = FALSE; + uint8_t bldata[16] = {0x00}; + UsbCommand resp; + + char cmdp = param_getchar(Cmd, 0); + + if (strlen(Cmd) < 3 || cmdp == 'h' || cmdp == 'H') { + PrintAndLog("Usage: hf mfu cwrbl [w]"); + PrintAndLog(" [block number]"); + PrintAndLog(" [block data] - (8 hex symbols)"); + PrintAndLog(" [w] - Chinese magic ultralight tag"); + PrintAndLog(""); + PrintAndLog(" sample: hf mfu cwrbl 0 01020304"); + PrintAndLog(""); + return 0; + } + + blockNo = param_get8(Cmd, 0); + if (blockNo > MAX_ULTRAC_BLOCKS ){ + PrintAndLog("Error: Maximum number of blocks is 47 for Ultralight-C Cards!"); + return 1; + } + + if (param_gethex(Cmd, 1, bldata, 8)) { + PrintAndLog("Block data must include 8 HEX symbols"); + return 1; + } + + if (strchr(Cmd,'w') != 0 || strchr(Cmd,'W') != 0 ) { + chinese_card = TRUE; + } + + if ( blockNo <= 3 ) { + if (!chinese_card){ + PrintAndLog("Access Denied"); + } else { + PrintAndLog("--Special block no: 0x%02x", blockNo); + PrintAndLog("--Data: %s", sprint_hex(bldata, 4)); + UsbCommand d = {CMD_MIFAREU_WRITEBL, {blockNo}}; + memcpy(d.d.asBytes,bldata, 4); + SendCommand(&d); + if (WaitForResponseTimeout(CMD_ACK,&resp,1500)) { + uint8_t isOK = resp.arg[0] & 0xff; + PrintAndLog("isOk:%02x", isOK); + } else { + PrintAndLog("Command execute timeout"); + } + } + } else { + PrintAndLog("--Block no : 0x%02x", blockNo); + PrintAndLog("--Data: %s", sprint_hex(bldata, 4)); + UsbCommand e = {CMD_MIFAREU_WRITEBL, {blockNo}}; + memcpy(e.d.asBytes,bldata, 4); + SendCommand(&e); + if (WaitForResponseTimeout(CMD_ACK,&resp,1500)) { + uint8_t isOK = resp.arg[0] & 0xff; + PrintAndLog("isOk : %02x", isOK); + } else { + PrintAndLog("Command execute timeout"); + } + } + return 0; +} + +//------------------------------------ +// Menu Stuff +//------------------------------------ +static command_t CommandTable[] = +{ + {"help", CmdHelp, 1,"This help"}, + {"dbg", CmdHF14AMfDbg, 0,"Set default debug mode"}, + {"info", CmdHF14AMfUInfo, 0,"Taginfo"}, + {"dump", CmdHF14AMfUDump, 0,"Dump MIFARE Ultralight / Ultralight-C tag to binary file"}, + {"rdbl", CmdHF14AMfURdBl, 0,"Read block - MIFARE Ultralight"}, + {"wrbl", CmdHF14AMfUWrBl, 0,"Write block - MIFARE Ultralight"}, + {"crdbl", CmdHF14AMfUCRdBl, 0,"Read block - MIFARE Ultralight C"}, + {"cwrbl", CmdHF14AMfUCWrBl, 0,"Write MIFARE Ultralight C block"}, + {"cauth", CmdHF14AMfucAuth, 0,"try a Ultralight C Authentication"}, + {NULL, NULL, 0, NULL} +}; + +int CmdHFMFUltra(const char *Cmd){ + WaitForResponseTimeout(CMD_ACK,NULL,100); + CmdsParse(CommandTable, Cmd); + return 0; +} + +int CmdHelp(const char *Cmd){ + CmdsHelp(CommandTable); + return 0; +} \ No newline at end of file diff --git a/client/cmdhfmfu.h b/client/cmdhfmfu.h new file mode 100644 index 00000000..c4bc0341 --- /dev/null +++ b/client/cmdhfmfu.h @@ -0,0 +1,19 @@ +#include "cmdhfmf.h" +#include "cmdhf14a.h" + +//standard ultralight +int CmdHF14AMfUWrBl(const char *Cmd); +int CmdHF14AMfURdBl(const char *Cmd); + +//Crypto Cards +int CmdHF14AMfUCRdBl(const char *Cmd); +int CmdHF14AMfUCRdCard(const char *Cmd); +int CmdHF14AMfucAuth(const char *Cmd); + +//general stuff +int CmdHF14AMfUDump(const char *Cmd); +void rol (uint8_t *data, const size_t len); + + +int CmdHFMFUltra(const char *Cmd); +int CmdHF14AMfUInfo(const char *Cmd); diff --git a/client/scripts/remagic.lua b/client/scripts/remagic.lua new file mode 100644 index 00000000..d2b869c3 --- /dev/null +++ b/client/scripts/remagic.lua @@ -0,0 +1,63 @@ +local getopt = require('getopt') + +example = "script run remagic" +author = "Iceman" + +desc = +[[ +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. + +Arguments: + -h this help +]] +--- +-- A debug printout-function +function dbg(args) + if DEBUG then + print("###", args) + end +end +--- +-- This is only meant to be used when errors occur +function oops(err) + print("ERROR: ",err) +end + +--- +-- Usage help +function help() + print(desc) + print("Example usage") + print(example) +end + +--- +-- The main entry point +function main(args) + + + -- Read the parameters + for o, a in getopt.getopt(args, 'h') do + if o == "h" then help() return end + end + + local _cmds = { + --[[ + --]] + [0] = "hf 14a raw -p -a -b 7 40", + [1] = "hf 14a raw -p -a 43", + [2] = "hf 14a raw -c -p -a A000", + [3] = "hf 14a raw -c -p -a 01 02 03 04 04 98 02 00 00 00 00 00 00 00 10 01", + } + core.clearCommandBuffer() + + local i + --for _,c in pairs(_cmds) do + for i = 0, 3 do + print ( _cmds[i] ) + core.console( _cmds[i] ) + end +end + +main(args) diff --git a/client/scripts/test_t55x7_psk.lua b/client/scripts/test_t55x7_psk.lua new file mode 100644 index 00000000..1b964094 --- /dev/null +++ b/client/scripts/test_t55x7_psk.lua @@ -0,0 +1,173 @@ +local cmds = require('commands') +local getopt = require('getopt') +local bin = require('bin') +local utils = require('utils') +local dumplib = require('html_dumplib') + +example =[[ + 1. script run tracetest + 2. script run tracetest -o + +]] +author = "Iceman" +usage = "script run test_t55x7_psk -o " +desc =[[ +This script will program a T55x7 TAG with the configuration: block 0x00 data 0x00088040 +The outlined procedure is as following: + +"lf t55xx write 0 00088040" +"lf read" +"data samples" +"data pskdet" +"data psknrz" +"data pskindala" +"data psknrzraw" + +Loop OUTER: + change the configuretion block 0 with: + -xxxx8xxx = PSK RF/2 with Manchester modulation + -xxxx1xxx = PSK RF/2 with PSK1 modulation (phase change when input changes) + -xxxx2xxx = PSK RF/2 with PSk2 modulation (phase change on bitclk if input high) + -xxxx3xxx = PSK RF/2 with PSk3 modulation (phase change on rising edge of input) + Loop INNER + for each outer configuration, also do + XXXXX0XX = PSK RF/2 + XXXXX4XX = PSK RF/4 + XXXXX8XX = PSK RF/8 + +In all 12 individual test for the PSK demod + +Arguments: + -h : this help + -o : logfile name +]] + +local TIMEOUT = 2000 -- Shouldn't take longer than 2 seconds +local DEBUG = true -- the debug flag + +--BLOCK 0 = 00088040 +local config1 = '0008' +local config2 = '40' + +local procedurecmds = { + [1] = '%s%s%s%s', + [2] = 'lf read', + --[3] = '', + [3] = 'data samples', + [4] = 'data pskdetectclock', + [5] = 'data psknrzrawdemod', + [6] = 'data pskindalademod', +} + +--- +-- A debug printout-function +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 +function oops(err) + print("ERROR: ",err) +end +--- +-- Usage help +function help() + print(desc) + print("Example usage") + print(example) +end +-- +-- Exit message +function ExitMsg(msg) + print( string.rep('--',20) ) + print( string.rep('--',20) ) + print(msg) + print() +end + +function pskTest(modulation) + local y + for y = 0, 8, 4 do + for _ = 1, #procedurecmds do + local cmd = procedurecmds[_] + + if #cmd == 0 then + + elseif _ == 1 then + + dbg("Writing to T55x7 TAG") + + local configdata = cmd:format( config1, modulation , y, config2) + + dbg( configdata) + + local writecommand = Command:new{cmd = cmds.CMD_T55XX_WRITE_BLOCK, arg1 = configdata ,arg2 = 0, arg3 = 0} + local err = core.SendCommand(writecommand:getBytes()) + if err then return oops(err) end + local response = core.WaitForResponseTimeout(cmds.CMD_ACK,TIMEOUT) + + if response then + local count,cmd,arg0 = bin.unpack('LL',response) + if(arg0==1) then + dbg("Writing success") + else + return nil, "Couldn't read block.." + end + end + + else + dbg(cmd) + core.console( cmd ) + end + end + core.clearCommandBuffer() + end + print( string.rep('--',20) ) + +end + +local function main(args) + + print( string.rep('--',20) ) + print( string.rep('--',20) ) + + local outputTemplate = os.date("testpsk_%Y-%m-%d_%H%M%S") + + -- Arguments for the script + for o, arg in getopt.getopt(args, 'ho:') do + if o == "h" then return help() end + if o == "o" then outputTemplate = arg end + end + + core.clearCommandBuffer() + + pskTest(1) + pskTest(2) + pskTest(3) + pskTest(8) + + print( string.rep('--',20) ) +end +main(args) + +-- Where it iterates over + -- xxxx8xxx = PSK RF/2 with Manchester modulation + -- xxxx1xxx = PSK RF/2 with PSK1 modulation (phase change when input changes) + -- xxxx2xxx = PSK RF/2 with PSk2 modulation (phase change on bitclk if input high) + -- xxxx3xxx = PSK RF/2 with PSk3 modulation (phase change on rising edge of input) + + -- XXXXX0XX = PSK RF/2 + -- XXXXX4XX = PSK RF/4 + -- XXXXX8XX = PSK RF/8 \ No newline at end of file diff --git a/client/scripts/tracetest.lua b/client/scripts/tracetest.lua new file mode 100644 index 00000000..e4a9215c --- /dev/null +++ b/client/scripts/tracetest.lua @@ -0,0 +1,132 @@ +local cmds = require('commands') +local getopt = require('getopt') +local bin = require('bin') +local utils = require('utils') +local dumplib = require('html_dumplib') + +example =[[ + 1. script run tracetest + 2. script run tracetest -o + +]] +author = "Iceman" +usage = "script run tracetest -o " +desc =[[ +This script will load several traces files in ../traces/ folder and do +"data load" +"lf search" + +Arguments: + -h : this help + -o : logfile name +]] + +local TIMEOUT = 2000 -- Shouldn't take longer than 2 seconds +local DEBUG = true -- the debug flag +--- +-- A debug printout-function +function dbg(args) + if not DEBUG then + return + end + + if type(args) == "table" then + local i = 1 + while result[i] do + dbg(result[i]) + i = i+1 + end + else + print("###", args) + end +end +--- +-- This is only meant to be used when errors occur +function oops(err) + print("ERROR: ",err) +end +--- +-- Usage help +function help() + print(desc) + print("Example usage") + print(example) +end +-- +-- Exit message +function ExitMsg(msg) + print( string.rep('--',20) ) + print( string.rep('--',20) ) + print(msg) + print() +end + + +local function main(args) + + print( string.rep('--',20) ) + print( string.rep('--',20) ) + + local cmdDataLoad = 'data load %s'; + local tracesEM = "find '../traces/' -iname 'em*.pm3' -type f" + local tracesMOD = "find '../traces/' -iname 'm*.pm3' -type f" + + local outputTemplate = os.date("testtest_%Y-%m-%d_%H%M%S") + + -- Arguments for the script + for o, arg in getopt.getopt(args, 'ho:') do + if o == "h" then return help() end + if o == "o" then outputTemplate = arg end + end + + core.clearCommandBuffer() + + local files = {} + + -- Find a set of traces staring with EM + local p = assert( io.popen(tracesEM)) + for file in p:lines() do + table.insert(files, file) + end + p.close(); + + -- Find a set of traces staring with MOD + p = assert( io.popen(tracesMOD) ) + for file in p:lines() do + table.insert(files, file) + end + p.close(); + + local cmdLFSEARCH = "lf search 1" + + -- main loop + io.write('Starting to test traces > ') + for _,file in pairs(files) do + + local x = "data load "..file + dbg(x) + core.console(x) + + dbg(cmdLFSEARCH) + core.console(cmdLFSEARCH) + + core.clearCommandBuffer() + + if core.ukbhit() then + print("aborted by user") + break + end + end + io.write('\n') + + -- Write dump to files + if not DEBUG then + local bar = dumplib.SaveAsText(emldata, outputTemplate..'.txt') + print(("Wrote output to: %s"):format(bar)) + end + + -- Show info + print( string.rep('--',20) ) + +end +main(args) \ No newline at end of file -- 2.39.2