mirror of
https://github.com/DarkFlippers/unleashed-firmware.git
synced 2025-12-12 04:34:43 +04:00
NFC: Custom UID entry when adding manually (#3363)
* NFC: Custom UID entry when adding manually * Fix incorrect types * Add Change UID option post-generation * Update UID derived data when using set_uid method * Fix PVS warnings Co-authored-by: gornekich <n.gorbadey@gmail.com> Co-authored-by: あく <alleteam@gmail.com>
This commit is contained in:
@@ -199,6 +199,9 @@ static bool nfc_scene_read_menu_on_event_mf_classic(NfcApp* instance, SceneManag
|
|||||||
} else if(event.event == SubmenuIndexDictAttack) {
|
} else if(event.event == SubmenuIndexDictAttack) {
|
||||||
scene_manager_next_scene(instance->scene_manager, NfcSceneMfClassicDictAttack);
|
scene_manager_next_scene(instance->scene_manager, NfcSceneMfClassicDictAttack);
|
||||||
consumed = true;
|
consumed = true;
|
||||||
|
} else if(event.event == SubmenuIndexCommonEdit) {
|
||||||
|
scene_manager_next_scene(instance->scene_manager, NfcSceneSetUid);
|
||||||
|
consumed = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -266,16 +266,21 @@ static void nfc_scene_emulate_on_enter_mf_ultralight(NfcApp* instance) {
|
|||||||
static bool nfc_scene_read_and_saved_menu_on_event_mf_ultralight(
|
static bool nfc_scene_read_and_saved_menu_on_event_mf_ultralight(
|
||||||
NfcApp* instance,
|
NfcApp* instance,
|
||||||
SceneManagerEvent event) {
|
SceneManagerEvent event) {
|
||||||
|
bool consumed = false;
|
||||||
|
|
||||||
if(event.type == SceneManagerEventTypeCustom) {
|
if(event.type == SceneManagerEventTypeCustom) {
|
||||||
if(event.event == SubmenuIndexUnlock) {
|
if(event.event == SubmenuIndexUnlock) {
|
||||||
scene_manager_next_scene(instance->scene_manager, NfcSceneMfUltralightUnlockMenu);
|
scene_manager_next_scene(instance->scene_manager, NfcSceneMfUltralightUnlockMenu);
|
||||||
return true;
|
consumed = true;
|
||||||
} else if(event.event == SubmenuIndexWrite) {
|
} else if(event.event == SubmenuIndexWrite) {
|
||||||
scene_manager_next_scene(instance->scene_manager, NfcSceneMfUltralightWrite);
|
scene_manager_next_scene(instance->scene_manager, NfcSceneMfUltralightWrite);
|
||||||
return true;
|
consumed = true;
|
||||||
|
} else if(event.event == SubmenuIndexCommonEdit) {
|
||||||
|
scene_manager_next_scene(instance->scene_manager, NfcSceneSetUid);
|
||||||
|
consumed = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return false;
|
return consumed;
|
||||||
}
|
}
|
||||||
|
|
||||||
const NfcProtocolSupportBase nfc_protocol_support_mf_ultralight = {
|
const NfcProtocolSupportBase nfc_protocol_support_mf_ultralight = {
|
||||||
|
|||||||
@@ -233,6 +233,15 @@ static void nfc_protocol_support_scene_read_menu_on_enter(NfcApp* instance) {
|
|||||||
nfc_protocol_support_common_submenu_callback,
|
nfc_protocol_support_common_submenu_callback,
|
||||||
instance);
|
instance);
|
||||||
|
|
||||||
|
if(scene_manager_has_previous_scene(instance->scene_manager, NfcSceneGenerateInfo)) {
|
||||||
|
submenu_add_item(
|
||||||
|
submenu,
|
||||||
|
"Change UID",
|
||||||
|
SubmenuIndexCommonEdit,
|
||||||
|
nfc_protocol_support_common_submenu_callback,
|
||||||
|
instance);
|
||||||
|
}
|
||||||
|
|
||||||
if(nfc_protocol_support_has_feature(protocol, NfcProtocolFeatureEmulateUid)) {
|
if(nfc_protocol_support_has_feature(protocol, NfcProtocolFeatureEmulateUid)) {
|
||||||
submenu_add_item(
|
submenu_add_item(
|
||||||
submenu,
|
submenu,
|
||||||
|
|||||||
@@ -88,7 +88,7 @@ static bool hi_verify_type(Nfc* nfc, MfClassicType type) {
|
|||||||
if(!hi_get_card_config(&cfg, type)) break;
|
if(!hi_get_card_config(&cfg, type)) break;
|
||||||
|
|
||||||
const uint8_t block_num = mf_classic_get_first_block_num_of_sector(cfg.verify_sector);
|
const uint8_t block_num = mf_classic_get_first_block_num_of_sector(cfg.verify_sector);
|
||||||
FURI_LOG_D(TAG, "Verifying sector %li", cfg.verify_sector);
|
FURI_LOG_D(TAG, "Verifying sector %lu", cfg.verify_sector);
|
||||||
|
|
||||||
MfClassicKey key = {0};
|
MfClassicKey key = {0};
|
||||||
nfc_util_num2bytes(cfg.keys[cfg.verify_sector].b, COUNT_OF(key.data), key.data);
|
nfc_util_num2bytes(cfg.keys[cfg.verify_sector].b, COUNT_OF(key.data), key.data);
|
||||||
|
|||||||
@@ -99,7 +99,7 @@ static bool mizip_verify_type(Nfc* nfc, MfClassicType type) {
|
|||||||
if(!mizip_get_card_config(&cfg, type)) break;
|
if(!mizip_get_card_config(&cfg, type)) break;
|
||||||
|
|
||||||
const uint8_t block_num = mf_classic_get_first_block_num_of_sector(cfg.verify_sector);
|
const uint8_t block_num = mf_classic_get_first_block_num_of_sector(cfg.verify_sector);
|
||||||
FURI_LOG_D(TAG, "Verifying sector %li", cfg.verify_sector);
|
FURI_LOG_D(TAG, "Verifying sector %lu", cfg.verify_sector);
|
||||||
|
|
||||||
MfClassicKey key = {0};
|
MfClassicKey key = {0};
|
||||||
nfc_util_num2bytes(cfg.keys[cfg.verify_sector].b, COUNT_OF(key.data), key.data);
|
nfc_util_num2bytes(cfg.keys[cfg.verify_sector].b, COUNT_OF(key.data), key.data);
|
||||||
|
|||||||
@@ -44,6 +44,10 @@ bool nfc_scene_set_uid_on_event(void* context, SceneManagerEvent event) {
|
|||||||
scene_manager_next_scene(instance->scene_manager, NfcSceneSaveSuccess);
|
scene_manager_next_scene(instance->scene_manager, NfcSceneSaveSuccess);
|
||||||
consumed = true;
|
consumed = true;
|
||||||
}
|
}
|
||||||
|
} else if(scene_manager_has_previous_scene(instance->scene_manager, NfcSceneReadMenu)) {
|
||||||
|
scene_manager_search_and_switch_to_previous_scene(
|
||||||
|
instance->scene_manager, NfcSceneReadMenu);
|
||||||
|
consumed = true;
|
||||||
} else {
|
} else {
|
||||||
scene_manager_next_scene(instance->scene_manager, NfcSceneSaveName);
|
scene_manager_next_scene(instance->scene_manager, NfcSceneSaveName);
|
||||||
consumed = true;
|
consumed = true;
|
||||||
|
|||||||
@@ -35,26 +35,16 @@ static void nfc_generate_mf_ul_uid(uint8_t* uid) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
static void nfc_generate_mf_ul_common(MfUltralightData* mfu_data) {
|
static void nfc_generate_mf_ul_common(MfUltralightData* mfu_data) {
|
||||||
|
uint8_t uid[7];
|
||||||
mfu_data->iso14443_3a_data->uid_len = 7;
|
mfu_data->iso14443_3a_data->uid_len = 7;
|
||||||
nfc_generate_mf_ul_uid(mfu_data->iso14443_3a_data->uid);
|
nfc_generate_mf_ul_uid(uid);
|
||||||
|
mf_ultralight_set_uid(mfu_data, uid, 7);
|
||||||
|
|
||||||
mfu_data->iso14443_3a_data->atqa[0] = 0x44;
|
mfu_data->iso14443_3a_data->atqa[0] = 0x44;
|
||||||
mfu_data->iso14443_3a_data->atqa[1] = 0x00;
|
mfu_data->iso14443_3a_data->atqa[1] = 0x00;
|
||||||
mfu_data->iso14443_3a_data->sak = 0x00;
|
mfu_data->iso14443_3a_data->sak = 0x00;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void nfc_generate_calc_bcc(uint8_t* uid, uint8_t* bcc0, uint8_t* bcc1) {
|
|
||||||
*bcc0 = 0x88 ^ uid[0] ^ uid[1] ^ uid[2];
|
|
||||||
*bcc1 = uid[3] ^ uid[4] ^ uid[5] ^ uid[6];
|
|
||||||
}
|
|
||||||
|
|
||||||
static void nfc_generate_mf_ul_copy_uid_with_bcc(MfUltralightData* mfu_data) {
|
|
||||||
memcpy(mfu_data->page[0].data, mfu_data->iso14443_3a_data->uid, 3);
|
|
||||||
memcpy(mfu_data->page[1].data, &mfu_data->iso14443_3a_data->uid[3], 4);
|
|
||||||
|
|
||||||
nfc_generate_calc_bcc(
|
|
||||||
mfu_data->iso14443_3a_data->uid, &mfu_data->page[0].data[3], &mfu_data->page[2].data[0]);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void nfc_generate_mf_ul_orig(NfcDevice* nfc_device) {
|
static void nfc_generate_mf_ul_orig(NfcDevice* nfc_device) {
|
||||||
MfUltralightData* mfu_data = mf_ultralight_alloc();
|
MfUltralightData* mfu_data = mf_ultralight_alloc();
|
||||||
nfc_generate_mf_ul_common(mfu_data);
|
nfc_generate_mf_ul_common(mfu_data);
|
||||||
@@ -62,7 +52,6 @@ static void nfc_generate_mf_ul_orig(NfcDevice* nfc_device) {
|
|||||||
mfu_data->type = MfUltralightTypeUnknown;
|
mfu_data->type = MfUltralightTypeUnknown;
|
||||||
mfu_data->pages_total = 16;
|
mfu_data->pages_total = 16;
|
||||||
mfu_data->pages_read = 16;
|
mfu_data->pages_read = 16;
|
||||||
nfc_generate_mf_ul_copy_uid_with_bcc(mfu_data);
|
|
||||||
memset(&mfu_data->page[4], 0xff, sizeof(MfUltralightPage));
|
memset(&mfu_data->page[4], 0xff, sizeof(MfUltralightPage));
|
||||||
|
|
||||||
nfc_device_set_data(nfc_device, NfcProtocolMfUltralight, mfu_data);
|
nfc_device_set_data(nfc_device, NfcProtocolMfUltralight, mfu_data);
|
||||||
@@ -74,7 +63,7 @@ static void nfc_generate_mf_ul_with_config_common(MfUltralightData* mfu_data, ui
|
|||||||
|
|
||||||
mfu_data->pages_total = num_pages;
|
mfu_data->pages_total = num_pages;
|
||||||
mfu_data->pages_read = num_pages;
|
mfu_data->pages_read = num_pages;
|
||||||
nfc_generate_mf_ul_copy_uid_with_bcc(mfu_data);
|
|
||||||
uint16_t config_index = (num_pages - 4);
|
uint16_t config_index = (num_pages - 4);
|
||||||
mfu_data->page[config_index].data[0] = 0x04; // STRG_MOD_EN
|
mfu_data->page[config_index].data[0] = 0x04; // STRG_MOD_EN
|
||||||
mfu_data->page[config_index].data[3] = 0xff; // AUTH0
|
mfu_data->page[config_index].data[3] = 0xff; // AUTH0
|
||||||
@@ -150,7 +139,6 @@ static void nfc_generate_ntag203(NfcDevice* nfc_device) {
|
|||||||
mfu_data->type = MfUltralightTypeNTAG203;
|
mfu_data->type = MfUltralightTypeNTAG203;
|
||||||
mfu_data->pages_total = 42;
|
mfu_data->pages_total = 42;
|
||||||
mfu_data->pages_read = 42;
|
mfu_data->pages_read = 42;
|
||||||
nfc_generate_mf_ul_copy_uid_with_bcc(mfu_data);
|
|
||||||
mfu_data->page[2].data[1] = 0x48; // Internal byte
|
mfu_data->page[2].data[1] = 0x48; // Internal byte
|
||||||
memcpy(&mfu_data->page[3], default_data_ntag203, sizeof(MfUltralightPage)); //-V1086
|
memcpy(&mfu_data->page[3], default_data_ntag203, sizeof(MfUltralightPage)); //-V1086
|
||||||
|
|
||||||
@@ -379,14 +367,7 @@ static void nfc_generate_mf_classic_block_0(
|
|||||||
furi_assert(uid_len == 4 || uid_len == 7);
|
furi_assert(uid_len == 4 || uid_len == 7);
|
||||||
furi_assert(block);
|
furi_assert(block);
|
||||||
|
|
||||||
if(uid_len == 4) {
|
if(uid_len == 7) {
|
||||||
// Calculate BCC
|
|
||||||
block[uid_len] = 0;
|
|
||||||
|
|
||||||
for(int i = 0; i < uid_len; i++) {
|
|
||||||
block[uid_len] ^= block[i];
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
uid_len -= 1;
|
uid_len -= 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -402,14 +383,12 @@ static void nfc_generate_mf_classic_block_0(
|
|||||||
static void nfc_generate_mf_classic(NfcDevice* nfc_device, uint8_t uid_len, MfClassicType type) {
|
static void nfc_generate_mf_classic(NfcDevice* nfc_device, uint8_t uid_len, MfClassicType type) {
|
||||||
MfClassicData* mfc_data = mf_classic_alloc();
|
MfClassicData* mfc_data = mf_classic_alloc();
|
||||||
|
|
||||||
nfc_generate_mf_classic_uid(mfc_data->block[0].data, uid_len);
|
uint8_t uid[ISO14443_3A_MAX_UID_SIZE];
|
||||||
nfc_generate_mf_classic_common(mfc_data, uid_len, type);
|
|
||||||
|
|
||||||
// Set the UID
|
nfc_generate_mf_classic_uid(uid, uid_len);
|
||||||
mfc_data->iso14443_3a_data->uid[0] = NXP_MANUFACTURER_ID;
|
mf_classic_set_uid(mfc_data, uid, uid_len);
|
||||||
for(int i = 1; i < uid_len; i++) {
|
|
||||||
mfc_data->iso14443_3a_data->uid[i] = mfc_data->block[0].data[i];
|
nfc_generate_mf_classic_common(mfc_data, uid_len, type);
|
||||||
}
|
|
||||||
|
|
||||||
mf_classic_set_block_read(mfc_data, 0, &mfc_data->block[0]);
|
mf_classic_set_block_read(mfc_data, 0, &mfc_data->block[0]);
|
||||||
|
|
||||||
|
|||||||
@@ -346,7 +346,25 @@ const uint8_t* mf_classic_get_uid(const MfClassicData* data, size_t* uid_len) {
|
|||||||
bool mf_classic_set_uid(MfClassicData* data, const uint8_t* uid, size_t uid_len) {
|
bool mf_classic_set_uid(MfClassicData* data, const uint8_t* uid, size_t uid_len) {
|
||||||
furi_assert(data);
|
furi_assert(data);
|
||||||
|
|
||||||
return iso14443_3a_set_uid(data->iso14443_3a_data, uid, uid_len);
|
bool uid_valid = iso14443_3a_set_uid(data->iso14443_3a_data, uid, uid_len);
|
||||||
|
|
||||||
|
if(uid_valid) {
|
||||||
|
uint8_t* block = data->block[0].data;
|
||||||
|
|
||||||
|
// Copy UID to block 0
|
||||||
|
memcpy(block, data->iso14443_3a_data->uid, uid_len);
|
||||||
|
|
||||||
|
if(uid_len == 4) {
|
||||||
|
// Calculate BCC byte
|
||||||
|
block[uid_len] = 0;
|
||||||
|
|
||||||
|
for(size_t i = 0; i < uid_len; i++) {
|
||||||
|
block[uid_len] ^= block[i];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return uid_valid;
|
||||||
}
|
}
|
||||||
|
|
||||||
Iso14443_3aData* mf_classic_get_base_data(const MfClassicData* data) {
|
Iso14443_3aData* mf_classic_get_base_data(const MfClassicData* data) {
|
||||||
|
|||||||
@@ -482,7 +482,19 @@ const uint8_t* mf_ultralight_get_uid(const MfUltralightData* data, size_t* uid_l
|
|||||||
bool mf_ultralight_set_uid(MfUltralightData* data, const uint8_t* uid, size_t uid_len) {
|
bool mf_ultralight_set_uid(MfUltralightData* data, const uint8_t* uid, size_t uid_len) {
|
||||||
furi_assert(data);
|
furi_assert(data);
|
||||||
|
|
||||||
return iso14443_3a_set_uid(data->iso14443_3a_data, uid, uid_len);
|
bool uid_valid = iso14443_3a_set_uid(data->iso14443_3a_data, uid, uid_len);
|
||||||
|
|
||||||
|
if(uid_valid) {
|
||||||
|
// Copy UID across first 2 pages
|
||||||
|
memcpy(data->page[0].data, data->iso14443_3a_data->uid, 3);
|
||||||
|
memcpy(data->page[1].data, &data->iso14443_3a_data->uid[3], 4);
|
||||||
|
|
||||||
|
// Calculate BCC bytes
|
||||||
|
data->page[0].data[3] = 0x88 ^ uid[0] ^ uid[1] ^ uid[2];
|
||||||
|
data->page[2].data[0] = uid[3] ^ uid[4] ^ uid[5] ^ uid[6];
|
||||||
|
}
|
||||||
|
|
||||||
|
return uid_valid;
|
||||||
}
|
}
|
||||||
|
|
||||||
Iso14443_3aData* mf_ultralight_get_base_data(const MfUltralightData* data) {
|
Iso14443_3aData* mf_ultralight_get_base_data(const MfUltralightData* data) {
|
||||||
|
|||||||
Reference in New Issue
Block a user