From 64badf124acc011777871a2a7b7d0cd4cff6e084 Mon Sep 17 00:00:00 2001 From: "g3gg0.de" Date: Sat, 21 Jan 2023 01:49:02 +0100 Subject: [PATCH] also added DSFID/AFI handling and locking --- .../main/nfc/scenes/nfc_scene_nfc_data_info.c | 12 +- lib/nfc/nfc_device.c | 7 +- lib/nfc/protocols/nfcv.c | 103 +++++++++++++++++- lib/nfc/protocols/nfcv.h | 7 +- 4 files changed, 123 insertions(+), 6 deletions(-) diff --git a/applications/main/nfc/scenes/nfc_scene_nfc_data_info.c b/applications/main/nfc/scenes/nfc_scene_nfc_data_info.c index 87a23c8ef..38f3e75c7 100644 --- a/applications/main/nfc/scenes/nfc_scene_nfc_data_info.c +++ b/applications/main/nfc/scenes/nfc_scene_nfc_data_info.c @@ -87,8 +87,16 @@ void nfc_scene_nfc_data_info_on_enter(void* context) { } furi_string_cat_printf(temp_str, "\n"); - furi_string_cat_printf(temp_str, "DSFID: %02X\n", nfcv_data->dsfid); - furi_string_cat_printf(temp_str, "AFI: %02X\n", nfcv_data->afi); + furi_string_cat_printf( + temp_str, + "DSFID: %02X %s\n", + nfcv_data->dsfid, + (nfcv_data->security_status[0] & NfcVLockBitDsfid) ? "(locked)" : ""); + furi_string_cat_printf( + temp_str, + "AFI: %02X %s\n", + nfcv_data->afi, + (nfcv_data->security_status[0] & NfcVLockBitAfi) ? "(locked)" : ""); furi_string_cat_printf(temp_str, "IC Ref: %02X\n", nfcv_data->ic_ref); furi_string_cat_printf(temp_str, "Blocks: %02X\n", nfcv_data->block_num); furi_string_cat_printf(temp_str, "Blocksize: %02X\n", nfcv_data->block_size); diff --git a/lib/nfc/nfc_device.c b/lib/nfc/nfc_device.c index 0aec74f0f..9646c262e 100644 --- a/lib/nfc/nfc_device.c +++ b/lib/nfc/nfc_device.c @@ -858,8 +858,11 @@ static bool nfc_device_save_nfcv_data(FlipperFormat* file, NfcDevice* dev) { if(!flipper_format_write_hex( file, "Data Content", data->data, data->block_num * data->block_size)) break; + if(!flipper_format_write_comment_cstr( + file, "First byte: DSFID (0x01) / AFI (0x02) lock info, others: block lock info")) + break; if(!flipper_format_write_hex( - file, "Security Status", data->security_status, data->block_num)) + file, "Security Status", data->security_status, 1 + data->block_num)) break; if(!flipper_format_write_comment_cstr( file, @@ -916,7 +919,7 @@ bool nfc_device_load_nfcv_data(FlipperFormat* file, NfcDevice* dev) { /* optional, as added later */ if(flipper_format_key_exist(file, "Security Status")) { if(!flipper_format_read_hex( - file, "Security Status", data->security_status, data->block_num)) + file, "Security Status", data->security_status, 1 + data->block_num)) break; } if(!flipper_format_read_hex(file, "Subtype", &temp_value, 1)) break; diff --git a/lib/nfc/protocols/nfcv.c b/lib/nfc/protocols/nfcv.c index c9982f156..b2b04f878 100644 --- a/lib/nfc/protocols/nfcv.c +++ b/lib/nfc/protocols/nfcv.c @@ -586,10 +586,73 @@ void nfcv_emu_handle_packet( uint8_t block = nfcv_data->frame[ctx->payload_offset]; nfcv_data->security_status[block] |= 0x01; nfcv_data->modified = true; + + ctx->response_buffer[0] = ISO15693_NOERROR; + nfcv_emu_send( + tx_rx, nfcv_data, ctx->response_buffer, 1, ctx->response_flags, ctx->send_time); + snprintf(nfcv_data->last_command, sizeof(nfcv_data->last_command), "LOCK BLOCK %d", block); break; } + case ISO15693_WRITE_DSFID: { + uint8_t id = nfcv_data->frame[ctx->payload_offset]; + + if(!(nfcv_data->security_status[0] & NfcVLockBitDsfid)) { + nfcv_data->dsfid = id; + nfcv_data->modified = true; + ctx->response_buffer[0] = ISO15693_NOERROR; + nfcv_emu_send( + tx_rx, nfcv_data, ctx->response_buffer, 1, ctx->response_flags, ctx->send_time); + } + + snprintf(nfcv_data->last_command, sizeof(nfcv_data->last_command), "WRITE DSFID %02X", id); + break; + } + + case ISO15693_WRITE_AFI: { + uint8_t id = nfcv_data->frame[ctx->payload_offset]; + + if(!(nfcv_data->security_status[0] & NfcVLockBitAfi)) { + nfcv_data->afi = id; + nfcv_data->modified = true; + ctx->response_buffer[0] = ISO15693_NOERROR; + nfcv_emu_send( + tx_rx, nfcv_data, ctx->response_buffer, 1, ctx->response_flags, ctx->send_time); + } + + snprintf(nfcv_data->last_command, sizeof(nfcv_data->last_command), "WRITE AFI %02X", id); + break; + } + + case ISO15693_LOCK_DSFID: { + if(!(nfcv_data->security_status[0] & NfcVLockBitDsfid)) { + nfcv_data->security_status[0] |= NfcVLockBitDsfid; + nfcv_data->modified = true; + + ctx->response_buffer[0] = ISO15693_NOERROR; + nfcv_emu_send( + tx_rx, nfcv_data, ctx->response_buffer, 1, ctx->response_flags, ctx->send_time); + } + + snprintf(nfcv_data->last_command, sizeof(nfcv_data->last_command), "LOCK DSFID"); + break; + } + + case ISO15693_LOCK_AFI: { + if(!(nfcv_data->security_status[0] & NfcVLockBitAfi)) { + nfcv_data->security_status[0] |= NfcVLockBitAfi; + nfcv_data->modified = true; + + ctx->response_buffer[0] = ISO15693_NOERROR; + nfcv_emu_send( + tx_rx, nfcv_data, ctx->response_buffer, 1, ctx->response_flags, ctx->send_time); + } + + snprintf(nfcv_data->last_command, sizeof(nfcv_data->last_command), "LOCK AFI"); + break; + } + case ISO15693_SELECT: { ctx->response_buffer[0] = ISO15693_NOERROR; nfcv_data->selected = true; @@ -631,7 +694,8 @@ void nfcv_emu_handle_packet( int block_current = block + block_index; /* prepend security status */ if(ctx->flags & RFAL_NFCV_REQ_FLAG_OPTION) { - ctx->response_buffer[buffer_pos++] = nfcv_data->security_status[block_current]; + ctx->response_buffer[buffer_pos++] = + nfcv_data->security_status[1 + block_current]; } /* then the data block */ memcpy( @@ -794,6 +858,43 @@ void nfcv_emu_sniff_packet( break; } + case ISO15693_WRITE_DSFID: { + uint8_t id = nfcv_data->frame[ctx->payload_offset]; + snprintf( + nfcv_data->last_command, + sizeof(nfcv_data->last_command), + "%s WR DSFID %d", + flags_string, + id); + break; + } + + case ISO15693_WRITE_AFI: { + uint8_t id = nfcv_data->frame[ctx->payload_offset]; + snprintf( + nfcv_data->last_command, + sizeof(nfcv_data->last_command), + "%s WR AFI %d", + flags_string, + id); + break; + } + + case ISO15693_LOCK_DSFID: { + snprintf( + nfcv_data->last_command, + sizeof(nfcv_data->last_command), + "%s LOCK DSFID", + flags_string); + break; + } + + case ISO15693_LOCK_AFI: { + snprintf( + nfcv_data->last_command, sizeof(nfcv_data->last_command), "%s LOCK AFI", flags_string); + break; + } + case ISO15693_SELECT: { snprintf( nfcv_data->last_command, sizeof(nfcv_data->last_command), "%s SELECT", flags_string); diff --git a/lib/nfc/protocols/nfcv.h b/lib/nfc/protocols/nfcv.h index fde1c933b..f1d6e0127 100644 --- a/lib/nfc/protocols/nfcv.h +++ b/lib/nfc/protocols/nfcv.h @@ -85,6 +85,11 @@ extern "C" { #define ISO15693_ERROR_BLOCK_WRITE 0x13 // Writing was unsuccessful #define ISO15693_ERROR_BLOCL_WRITELOCK 0x14 // Locking was unsuccessful +typedef enum { + NfcVLockBitDsfid = 1, + NfcVLockBitAfi = 2, +} NfcVLockBits; + typedef enum { NfcVAuthMethodManual, NfcVAuthMethodTonieBox, @@ -174,7 +179,7 @@ typedef struct { uint16_t block_num; uint8_t block_size; uint8_t data[NFCV_MEMSIZE_MAX]; - uint8_t security_status[NFCV_BLOCKS_MAX]; + uint8_t security_status[1 + NFCV_BLOCKS_MAX]; bool selected; bool quiet;