Some tunings of otptear:

- make tearoff_delay_us and tearoff_enabled globals
- use tearoff_hook and remove Dbprintf in critical tearoff timing
- move initial write from MifareU_Otp_Tearoff to CmdHF14AMfuOtpTearoff and make it optional (old behavior was writing initial 00000000 when -d was not provided)
- tearoff: compare with initial write, not with previous tearoff outcome
- rephrase some messages
- track all begin and end of erase and write phases, with quite complex logic to cover multiple cases (starting in middle of erased phase, starting with write 0, ...) and report them
- check against initial write error
- repeat same timing (up to 10x) in case of write/read errors then quit
- typos
This commit is contained in:
Philippe Teuwen 2021-03-07 23:43:53 +01:00
commit e5c5629cf2
9 changed files with 121 additions and 93 deletions

View file

@ -2713,20 +2713,15 @@ void Mifare_DES_Auth2(uint32_t arg0, uint8_t *datain) {
//
// Tear-off attack against MFU.
// - Moebius et al
void MifareU_Otp_Tearoff(uint8_t blno, uint32_t tearoff_time, uint8_t *datain) {
void MifareU_Otp_Tearoff(uint8_t blno, uint32_t tearoff_time, uint8_t *data_testwrite) {
uint8_t blockNo = blno;
uint8_t data_fullwrite[4] = {0x00};
uint8_t data_testwrite[4] = {0x00};
memcpy(data_fullwrite, datain, 4);
memcpy(data_testwrite, datain + 4, 4);
if (DBGLEVEL >= DBG_DEBUG) DbpString("Preparing OTP tear-off");
if (tearoff_time > 43000)
tearoff_time = 43000;
MifareUWriteBlockEx(blockNo, 0, data_fullwrite, false);
tearoff_delay_us = tearoff_time;
tearoff_enabled = true;
LEDsoff();
iso14443a_setup(FPGA_HF_ISO14443A_READER_LISTEN);
@ -2750,15 +2745,9 @@ void MifareU_Otp_Tearoff(uint8_t blno, uint32_t tearoff_time, uint8_t *datain) {
return;
};
// send
ReaderTransmit(cmd, sizeof(cmd), NULL);
// Wait before cutting power. aka tear-off
LED_D_ON();
SpinDelayUsPrecision(tearoff_time);
if (DBGLEVEL >= DBG_DEBUG) Dbprintf(_YELLOW_("OTP tear-off triggered!"));
switch_off();
ReaderTransmit(cmd, sizeof(cmd), NULL);
tearoff_hook();
reply_ng(CMD_HF_MFU_OTP_TEAROFF, PM3_SUCCESS, NULL, 0);
}