Skip to content

Commit

Permalink
Merge branch 'dev' into gsurkov/3608_crash_on_missing_file
Browse files Browse the repository at this point in the history
  • Loading branch information
skotopes authored Nov 15, 2023
2 parents b085876 + c00776c commit 732bb5a
Show file tree
Hide file tree
Showing 64 changed files with 1,747 additions and 743 deletions.
63 changes: 38 additions & 25 deletions applications/debug/unit_tests/nfc/nfc_test.c
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,10 @@
#include <nfc/nfc_poller.h>
#include <nfc/nfc_listener.h>
#include <nfc/protocols/iso14443_3a/iso14443_3a.h>
#include <nfc/protocols/iso14443_3a/iso14443_3a_poller_sync_api.h>
#include <nfc/protocols/iso14443_3a/iso14443_3a_poller_sync.h>
#include <nfc/protocols/mf_ultralight/mf_ultralight.h>
#include <nfc/protocols/mf_ultralight/mf_ultralight_poller_sync_api.h>
#include <nfc/protocols/mf_classic/mf_classic_poller_sync_api.h>
#include <nfc/protocols/mf_ultralight/mf_ultralight_poller_sync.h>
#include <nfc/protocols/mf_classic/mf_classic_poller_sync.h>

#include <nfc/helpers/nfc_dict.h>
#include <nfc/nfc.h>
Expand Down Expand Up @@ -182,8 +182,8 @@ MU_TEST(iso14443_3a_reader) {

Iso14443_3aData iso14443_3a_poller_data = {};
mu_assert(
iso14443_3a_poller_read(poller, &iso14443_3a_poller_data) == Iso14443_3aErrorNone,
"iso14443_3a_poller_read() failed");
iso14443_3a_poller_sync_read(poller, &iso14443_3a_poller_data) == Iso14443_3aErrorNone,
"iso14443_3a_poller_sync_read() failed");

nfc_listener_stop(iso3_listener);
mu_assert(
Expand All @@ -203,15 +203,26 @@ static void mf_ultralight_reader_test(const char* path) {
NfcDevice* nfc_device = nfc_device_alloc();
mu_assert(nfc_device_load(nfc_device, path), "nfc_device_load() failed\r\n");

NfcListener* mfu_listener = nfc_listener_alloc(
listener,
NfcProtocolMfUltralight,
nfc_device_get_data(nfc_device, NfcProtocolMfUltralight));
MfUltralightData* data =
(MfUltralightData*)nfc_device_get_data(nfc_device, NfcProtocolMfUltralight);

uint32_t features = mf_ultralight_get_feature_support_set(data->type);
bool pwd_supported =
mf_ultralight_support_feature(features, MfUltralightFeatureSupportPasswordAuth);
uint8_t pwd_num = mf_ultralight_get_pwd_page_num(data->type);
const uint8_t zero_pwd[4] = {0, 0, 0, 0};

if(pwd_supported && !memcmp(data->page[pwd_num].data, zero_pwd, sizeof(zero_pwd))) {
data->pages_read -= 2;
}

NfcListener* mfu_listener = nfc_listener_alloc(listener, NfcProtocolMfUltralight, data);

nfc_listener_start(mfu_listener, NULL, NULL);

MfUltralightData* mfu_data = mf_ultralight_alloc();
MfUltralightError error = mf_ultralight_poller_read_card(poller, mfu_data);
mu_assert(error == MfUltralightErrorNone, "mf_ultralight_poller_read_card() failed");
MfUltralightError error = mf_ultralight_poller_sync_read_card(poller, mfu_data);
mu_assert(error == MfUltralightErrorNone, "mf_ultralight_poller_sync_read_card() failed");

nfc_listener_stop(mfu_listener);
nfc_listener_free(mfu_listener);
Expand Down Expand Up @@ -259,8 +270,8 @@ MU_TEST(ntag_213_locked_reader) {
nfc_listener_start(mfu_listener, NULL, NULL);

MfUltralightData* mfu_data = mf_ultralight_alloc();
MfUltralightError error = mf_ultralight_poller_read_card(poller, mfu_data);
mu_assert(error == MfUltralightErrorNone, "mf_ultralight_poller_read_card() failed");
MfUltralightError error = mf_ultralight_poller_sync_read_card(poller, mfu_data);
mu_assert(error == MfUltralightErrorNone, "mf_ultralight_poller_sync_read_card() failed");

nfc_listener_stop(mfu_listener);
nfc_listener_free(mfu_listener);
Expand Down Expand Up @@ -297,8 +308,8 @@ static void mf_ultralight_write() {
MfUltralightData* mfu_data = mf_ultralight_alloc();

// Initial read
MfUltralightError error = mf_ultralight_poller_read_card(poller, mfu_data);
mu_assert(error == MfUltralightErrorNone, "mf_ultralight_poller_read_card() failed");
MfUltralightError error = mf_ultralight_poller_sync_read_card(poller, mfu_data);
mu_assert(error == MfUltralightErrorNone, "mf_ultralight_poller_sync_read_card() failed");

mu_assert(
mf_ultralight_is_equal(mfu_data, nfc_device_get_data(nfc_device, NfcProtocolMfUltralight)),
Expand All @@ -310,13 +321,13 @@ static void mf_ultralight_write() {
FURI_LOG_D(TAG, "Writing page %d", i);
furi_hal_random_fill_buf(page.data, sizeof(MfUltralightPage));
mfu_data->page[i] = page;
error = mf_ultralight_poller_write_page(poller, i, &page);
mu_assert(error == MfUltralightErrorNone, "mf_ultralight_poller_write_page() failed");
error = mf_ultralight_poller_sync_write_page(poller, i, &page);
mu_assert(error == MfUltralightErrorNone, "mf_ultralight_poller_sync_write_page() failed");
}

// Verification read
error = mf_ultralight_poller_read_card(poller, mfu_data);
mu_assert(error == MfUltralightErrorNone, "mf_ultralight_poller_read_card() failed");
error = mf_ultralight_poller_sync_read_card(poller, mfu_data);
mu_assert(error == MfUltralightErrorNone, "mf_ultralight_poller_sync_read_card() failed");

nfc_listener_stop(mfu_listener);
const MfUltralightData* mfu_listener_data =
Expand Down Expand Up @@ -344,7 +355,7 @@ static void mf_classic_reader() {
MfClassicBlock block = {};
MfClassicKey key = {.data = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff}};

mf_classic_poller_read_block(poller, 0, &key, MfClassicKeyTypeA, &block);
mf_classic_poller_sync_read_block(poller, 0, &key, MfClassicKeyTypeA, &block);

nfc_listener_stop(mfc_listener);
nfc_listener_free(mfc_listener);
Expand Down Expand Up @@ -372,8 +383,8 @@ static void mf_classic_write() {
furi_hal_random_fill_buf(block_write.data, sizeof(MfClassicBlock));
MfClassicKey key = {.data = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff}};

mf_classic_poller_write_block(poller, 1, &key, MfClassicKeyTypeA, &block_write);
mf_classic_poller_read_block(poller, 1, &key, MfClassicKeyTypeA, &block_read);
mf_classic_poller_sync_write_block(poller, 1, &key, MfClassicKeyTypeA, &block_write);
mf_classic_poller_sync_read_block(poller, 1, &key, MfClassicKeyTypeA, &block_read);

nfc_listener_stop(mfc_listener);
nfc_listener_free(mfc_listener);
Expand Down Expand Up @@ -402,16 +413,18 @@ static void mf_classic_value_block() {
mf_classic_value_to_block(value, 1, &block_write);

MfClassicError error = MfClassicErrorNone;
error = mf_classic_poller_write_block(poller, 1, &key, MfClassicKeyTypeA, &block_write);
error = mf_classic_poller_sync_write_block(poller, 1, &key, MfClassicKeyTypeA, &block_write);
mu_assert(error == MfClassicErrorNone, "Write failed");

int32_t data = 200;
int32_t new_value = 0;
error = mf_classic_poller_change_value(poller, 1, &key, MfClassicKeyTypeA, data, &new_value);
error =
mf_classic_poller_sync_change_value(poller, 1, &key, MfClassicKeyTypeA, data, &new_value);
mu_assert(error == MfClassicErrorNone, "Value increment failed");
mu_assert(new_value == value + data, "Value not match");

error = mf_classic_poller_change_value(poller, 1, &key, MfClassicKeyTypeA, -data, &new_value);
error =
mf_classic_poller_sync_change_value(poller, 1, &key, MfClassicKeyTypeA, -data, &new_value);
mu_assert(error == MfClassicErrorNone, "Value decrement failed");
mu_assert(new_value == value, "Value not match");

Expand Down
8 changes: 4 additions & 4 deletions applications/main/nfc/plugins/supported_cards/plantain.c
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

#include <nfc/nfc_device.h>
#include <nfc/helpers/nfc_util.h>
#include <nfc/protocols/mf_classic/mf_classic_poller_sync_api.h>
#include <nfc/protocols/mf_classic/mf_classic_poller_sync.h>

#define TAG "Plantain"

Expand Down Expand Up @@ -91,7 +91,7 @@ static bool plantain_verify_type(Nfc* nfc, MfClassicType type) {

MfClassicAuthContext auth_context;
MfClassicError error =
mf_classic_poller_auth(nfc, block_num, &key, MfClassicKeyTypeA, &auth_context);
mf_classic_poller_sync_auth(nfc, block_num, &key, MfClassicKeyTypeA, &auth_context);
if(error != MfClassicErrorNone) {
FURI_LOG_D(TAG, "Failed to read block %u: %d", block_num, error);
break;
Expand Down Expand Up @@ -119,7 +119,7 @@ static bool plantain_read(Nfc* nfc, NfcDevice* device) {

do {
MfClassicType type = MfClassicTypeMini;
MfClassicError error = mf_classic_poller_detect_type(nfc, &type);
MfClassicError error = mf_classic_poller_sync_detect_type(nfc, &type);
if(error != MfClassicErrorNone) break;

data->type = type;
Expand All @@ -134,7 +134,7 @@ static bool plantain_read(Nfc* nfc, NfcDevice* device) {
FURI_BIT_SET(keys.key_b_mask, i);
}

error = mf_classic_poller_read(nfc, &keys, data);
error = mf_classic_poller_sync_read(nfc, &keys, data);
if(error != MfClassicErrorNone) {
FURI_LOG_W(TAG, "Failed to read data");
break;
Expand Down
8 changes: 4 additions & 4 deletions applications/main/nfc/plugins/supported_cards/troika.c
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

#include <nfc/nfc_device.h>
#include <nfc/helpers/nfc_util.h>
#include <nfc/protocols/mf_classic/mf_classic_poller_sync_api.h>
#include <nfc/protocols/mf_classic/mf_classic_poller_sync.h>

#define TAG "Troika"

Expand Down Expand Up @@ -91,7 +91,7 @@ static bool troika_verify_type(Nfc* nfc, MfClassicType type) {

MfClassicAuthContext auth_context;
MfClassicError error =
mf_classic_poller_auth(nfc, block_num, &key, MfClassicKeyTypeA, &auth_context);
mf_classic_poller_sync_auth(nfc, block_num, &key, MfClassicKeyTypeA, &auth_context);
if(error != MfClassicErrorNone) {
FURI_LOG_D(TAG, "Failed to read block %u: %d", block_num, error);
break;
Expand All @@ -118,7 +118,7 @@ static bool troika_read(Nfc* nfc, NfcDevice* device) {

do {
MfClassicType type = MfClassicTypeMini;
MfClassicError error = mf_classic_poller_detect_type(nfc, &type);
MfClassicError error = mf_classic_poller_sync_detect_type(nfc, &type);
if(error != MfClassicErrorNone) break;

data->type = type;
Expand All @@ -136,7 +136,7 @@ static bool troika_read(Nfc* nfc, NfcDevice* device) {
FURI_BIT_SET(keys.key_b_mask, i);
}

error = mf_classic_poller_read(nfc, &keys, data);
error = mf_classic_poller_sync_read(nfc, &keys, data);
if(error != MfClassicErrorNone) {
FURI_LOG_W(TAG, "Failed to read data");
break;
Expand Down
8 changes: 4 additions & 4 deletions applications/main/nfc/plugins/supported_cards/two_cities.c
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

#include <nfc/nfc_device.h>
#include <nfc/helpers/nfc_util.h>
#include <nfc/protocols/mf_classic/mf_classic_poller_sync_api.h>
#include <nfc/protocols/mf_classic/mf_classic_poller_sync.h>

#define TAG "TwoCities"

Expand Down Expand Up @@ -49,7 +49,7 @@ bool two_cities_verify(Nfc* nfc) {

MfClassicAuthContext auth_ctx = {};
MfClassicError error =
mf_classic_poller_auth(nfc, block_num, &key, MfClassicKeyTypeA, &auth_ctx);
mf_classic_poller_sync_auth(nfc, block_num, &key, MfClassicKeyTypeA, &auth_ctx);
if(error != MfClassicErrorNone) {
FURI_LOG_D(TAG, "Failed to read block %u: %d", block_num, error);
break;
Expand All @@ -72,7 +72,7 @@ static bool two_cities_read(Nfc* nfc, NfcDevice* device) {

do {
MfClassicType type = MfClassicTypeMini;
MfClassicError error = mf_classic_poller_detect_type(nfc, &type);
MfClassicError error = mf_classic_poller_sync_detect_type(nfc, &type);
if(error != MfClassicErrorNone) break;

data->type = type;
Expand All @@ -84,7 +84,7 @@ static bool two_cities_read(Nfc* nfc, NfcDevice* device) {
FURI_BIT_SET(keys.key_b_mask, i);
}

error = mf_classic_poller_read(nfc, &keys, data);
error = mf_classic_poller_sync_read(nfc, &keys, data);
if(error != MfClassicErrorNone) {
FURI_LOG_W(TAG, "Failed to read data");
break;
Expand Down
2 changes: 2 additions & 0 deletions lib/drivers/SConscript
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@ env.Append(
],
SDK_HEADERS=[
File("cc1101_regs.h"),
File("st25r3916_reg.h"),
File("st25r3916.h"),
],
)

Expand Down
6 changes: 3 additions & 3 deletions lib/nfc/SConscript
Original file line number Diff line number Diff line change
Expand Up @@ -36,9 +36,9 @@ env.Append(
File("protocols/mf_ultralight/mf_ultralight_listener.h"),
File("protocols/mf_classic/mf_classic_listener.h"),
# Sync API
File("protocols/iso14443_3a/iso14443_3a_poller_sync_api.h"),
File("protocols/mf_ultralight/mf_ultralight_poller_sync_api.h"),
File("protocols/mf_classic/mf_classic_poller_sync_api.h"),
File("protocols/iso14443_3a/iso14443_3a_poller_sync.h"),
File("protocols/mf_ultralight/mf_ultralight_poller_sync.h"),
File("protocols/mf_classic/mf_classic_poller_sync.h"),
# Misc
File("helpers/nfc_util.h"),
File("helpers/iso14443_crc.h"),
Expand Down
72 changes: 72 additions & 0 deletions lib/nfc/nfc_poller.c
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,9 @@ struct NfcPoller {
NfcPollerList list;
NfcPollerSessionState session_state;
bool protocol_detected;

NfcGenericCallbackEx callback;
void* context;
};

static void nfc_poller_list_alloc(NfcPoller* instance) {
Expand Down Expand Up @@ -127,6 +130,75 @@ void nfc_poller_start(NfcPoller* instance, NfcGenericCallback callback, void* co
nfc_start(instance->nfc, nfc_poller_start_callback, instance);
}

static NfcCommand nfc_poller_start_ex_tail_callback(NfcGenericEvent event, void* context) {
furi_assert(context);
furi_assert(event.protocol != NfcProtocolInvalid);

NfcPoller* instance = context;
NfcCommand command = NfcCommandContinue;

NfcGenericEventEx poller_event = {
.poller = instance->list.tail->poller,
.parent_event_data = event.event_data,
};

command = instance->callback(poller_event, instance->context);

return command;
}

static NfcCommand nfc_poller_start_ex_head_callback(NfcEvent event, void* context) {
furi_assert(context);

NfcCommand command = NfcCommandContinue;
NfcPoller* instance = context;

NfcProtocol parent_protocol = nfc_protocol_get_parent(instance->protocol);

if(parent_protocol == NfcProtocolInvalid) {
NfcGenericEventEx poller_event = {
.poller = instance->list.tail->poller,
.parent_event_data = &event,
};

command = instance->callback(poller_event, instance->context);
} else {
NfcGenericEvent poller_event = {
.protocol = NfcProtocolInvalid,
.instance = instance->nfc,
.event_data = &event,
};
NfcPollerListElement* head_poller = instance->list.head;
command = head_poller->poller_api->run(poller_event, head_poller->poller);
}

if(instance->session_state == NfcPollerSessionStateStopRequest) {
command = NfcCommandStop;
}

return command;
}

void nfc_poller_start_ex(NfcPoller* instance, NfcGenericCallbackEx callback, void* context) {
furi_assert(instance);
furi_assert(callback);
furi_assert(instance->session_state == NfcPollerSessionStateIdle);

instance->callback = callback;
instance->context = context;

NfcProtocol parent_protocol = nfc_protocol_get_parent(instance->protocol);
if(parent_protocol != NfcProtocolInvalid) {
NfcPollerListElement* iter = instance->list.head;
while(iter->protocol != parent_protocol) iter = iter->child;

iter->poller_api->set_callback(iter->poller, nfc_poller_start_ex_tail_callback, instance);
}

instance->session_state = NfcPollerSessionStateActive;
nfc_start(instance->nfc, nfc_poller_start_ex_head_callback, instance);
}

void nfc_poller_stop(NfcPoller* instance) {
furi_assert(instance);
furi_assert(instance->nfc);
Expand Down
Loading

0 comments on commit 732bb5a

Please sign in to comment.