From c68b22d51815ae0a7a1ddc41e5233e67c5dcde43 Mon Sep 17 00:00:00 2001 From: Enrico Pozzobon Date: Thu, 7 Nov 2019 10:48:51 +0100 Subject: [PATCH] ISO14443A ApplicationProcess delayed responses ApplicationProcess can return ISO14443A_APP_DELAYED_RESPONSE, in which case the response will be sent later from the ApplicationTask using ISO14443ASendResponse. This allows the computation of the response to be done outside of the Chameleon, and can be used to forward messages and perform a relay attacks. --- Firmware/Chameleon-Mini/Codec/ISO14443-2A.c | 34 ++++++++++++++++++++- Firmware/Chameleon-Mini/Codec/ISO14443-2A.h | 2 ++ 2 files changed, 35 insertions(+), 1 deletion(-) diff --git a/Firmware/Chameleon-Mini/Codec/ISO14443-2A.c b/Firmware/Chameleon-Mini/Codec/ISO14443-2A.c index b807543a..8cc75a75 100644 --- a/Firmware/Chameleon-Mini/Codec/ISO14443-2A.c +++ b/Firmware/Chameleon-Mini/Codec/ISO14443-2A.c @@ -29,6 +29,7 @@ typedef enum { DEMOD_PARITY_BIT, /* Loadmod */ + LOADMOD_PREPARING, LOADMOD_FDT, LOADMOD_START, LOADMOD_START_BIT0, @@ -448,7 +449,9 @@ void ISO14443ACodecTask(void) { } } - if (AnswerBitCount != ISO14443A_APP_NO_RESPONSE) { + if (AnswerBitCount == ISO14443A_APP_DELAYED_RESPONSE) { + StateRegister = LOADMOD_PREPARING; + } else if (AnswerBitCount != ISO14443A_APP_NO_RESPONSE) { LogEntry(LOG_INFO_CODEC_TX_DATA, CodecBuffer, (AnswerBitCount + 7) / 8); LEDHook(LED_CODEC_TX, LED_PULSE); @@ -474,3 +477,32 @@ void ISO14443ACodecTask(void) { } } +void ISO14443ASendResponse(const uint8_t *buffer, uint16_t AnswerBitCount) +{ + /* Start sending a delayed response from the AppTask, if the last call + * to ApplicationProcess returned ISO14443A_APP_DELAYED_RESPONSE */ + if (StateRegister != LOADMOD_PREPARING) { + return; + } + + memcpy(CodecBuffer, buffer, (AnswerBitCount + 7) / 8); + + if (AnswerBitCount & ISO14443A_APP_CUSTOM_PARITY) { + /* Application has generated it's own parity bits. + * Clear this option bit. */ + AnswerBitCount &= ~ISO14443A_APP_CUSTOM_PARITY; + ParityBufferPtr = &CodecBuffer[ISO14443A_BUFFER_PARITY_OFFSET]; + } else { + /* We have to generate the parity bits ourself */ + ParityBufferPtr = 0; + } + + LogEntry(LOG_INFO_CODEC_TX_DATA, CodecBuffer, (AnswerBitCount + 7) / 8); + LEDHook(LED_CODEC_TX, LED_PULSE); + + BitCount = AnswerBitCount; + CodecBufferPtr = CodecBuffer; + CodecSetSubcarrier(CODEC_SUBCARRIERMOD_OOK, ISO14443A_SUBCARRIER_DIVIDER); + + StateRegister = LOADMOD_START; +} diff --git a/Firmware/Chameleon-Mini/Codec/ISO14443-2A.h b/Firmware/Chameleon-Mini/Codec/ISO14443-2A.h index 73919413..32f6af04 100644 --- a/Firmware/Chameleon-Mini/Codec/ISO14443-2A.h +++ b/Firmware/Chameleon-Mini/Codec/ISO14443-2A.h @@ -12,6 +12,7 @@ #define ISO14443A_APP_NO_RESPONSE 0x0000 #define ISO14443A_APP_CUSTOM_PARITY 0x1000 +#define ISO14443A_APP_DELAYED_RESPONSE 0x2000 #define ISO14443A_BUFFER_PARITY_OFFSET (CODEC_BUFFER_SIZE/2) @@ -19,6 +20,7 @@ void ISO14443ACodecInit(void); void ISO14443ACodecDeInit(void); void ISO14443ACodecTask(void); +void ISO14443ASendResponse(const uint8_t *buffer, uint16_t bitCount);