This commit is contained in:
Willy-JL
2023-05-31 16:45:55 +01:00
parent dd72f21108
commit c35406689b
158 changed files with 8052 additions and 4090 deletions

27
.gitignore vendored
View File

@@ -30,31 +30,29 @@ bindings/
.mxproject
Brewfile.lock.json
# Visual Studio Code
/.vscode/
# Visual Studio
.vs/
# Kate
.kateproject
.kateconfig
# legendary cmake's
build
CMakeLists.txt
# bundle output
dist
# kde
.directory
null.d
# SCons
.sconsign.dblite
# Visual Studio Code
/.vscode
# Visual Studio
/.vs
# bundle output
/dist
# SCons build dir
build/
/build
# Toolchain
/toolchain
@@ -69,6 +67,7 @@ PVS-Studio.log
.gdbinit
/fbt_options_local.py
# XFW-specific:

View File

@@ -14,9 +14,7 @@ void lfrfid_debug_scene_tune_on_enter(void* context) {
furi_hal_rfid_comp_set_callback(comparator_trigger_callback, app);
furi_hal_rfid_comp_start();
furi_hal_rfid_pins_read();
furi_hal_rfid_tim_read(125000, 0.5);
furi_hal_rfid_tim_read_start();
furi_hal_rfid_tim_read_start(125000, 0.5);
view_dispatcher_switch_to_view(app->view_dispatcher, LfRfidDebugViewTune);
}
@@ -43,6 +41,5 @@ void lfrfid_debug_scene_tune_on_exit(void* context) {
furi_hal_gpio_init_simple(&gpio_ext_pa7, GpioModeAnalog);
furi_hal_rfid_tim_read_stop();
furi_hal_rfid_tim_reset();
furi_hal_rfid_pins_reset();
}

View File

@@ -13,5 +13,5 @@ App(
fap_author="AloneLiberty",
fap_description="Recover Mifare Classic keys",
fap_weburl="https://github.com/AloneLiberty/FlipperNested",
fap_version=(1, 4),
fap_version="1.5.0",
)

View File

@@ -5,28 +5,6 @@
#include "../../lib/crypto1/crypto1.h"
#define TAG "Nested"
void nfc_util_num2bytes(uint64_t src, uint8_t len, uint8_t* dest) {
furi_assert(dest);
furi_assert(len <= 8);
while(len--) {
dest[len] = (uint8_t)src;
src >>= 8;
}
}
uint64_t nfc_util_bytes2num(const uint8_t* src, uint8_t len) {
furi_assert(src);
furi_assert(len <= 8);
uint64_t res = 0;
while(len--) {
res = (res << 8) | (*src);
src++;
}
return res;
}
uint16_t nfca_get_crc16(uint8_t* buff, uint16_t len) {
uint16_t crc = 0x6363; // NFCA_CRC_INIT
uint8_t byte = 0;

View File

@@ -396,6 +396,7 @@ void mifare_nested_blink_stop(MifareNested* mifare_nested) {
int32_t mifare_nested_app(void* p) {
UNUSED(p);
MifareNested* mifare_nested = mifare_nested_alloc();
scene_manager_next_scene(mifare_nested->scene_manager, MifareNestedSceneStart);

View File

@@ -21,7 +21,7 @@
#include <gui/modules/variable_item_list.h>
#include "mifare_nested_icons.h"
#define NESTED_VERSION_APP "1.4.6"
#define NESTED_VERSION_APP "1.5.0"
#define NESTED_GITHUB_LINK "https://github.com/AloneLiberty/FlipperNested"
#define NESTED_RECOVER_KEYS_GITHUB_LINK "https://github.com/AloneLiberty/FlipperNestedRecovery"
#define NESTED_NONCE_FORMAT_VERSION "3"
@@ -99,6 +99,7 @@ struct MifareNested {
NestedState* nested_state;
CheckKeysState* keys_state;
SaveNoncesResult_t* save_state;
MifareNestedWorkerState collecting_type;

View File

@@ -296,7 +296,7 @@ uint32_t mifare_nested_worker_predict_delay(
}
// This part of attack is my attempt to implement it on Flipper.
// Proxmark can do this in 2 fucking steps, but idk how.
// Check README.md for more info
// First, we find RPNG rounds per 1000 us
for(uint32_t rtr = 0; rtr < 25; rtr++) {
@@ -448,7 +448,7 @@ uint32_t mifare_nested_worker_predict_delay(
return 1;
}
void mifare_nested_worker_write_nonces(
SaveNoncesResult_t* mifare_nested_worker_write_nonces(
FuriHalNfcDevData* data,
Storage* storage,
NonceList_t* nonces,
@@ -459,6 +459,11 @@ void mifare_nested_worker_write_nonces(
uint32_t distance) {
FuriString* path = furi_string_alloc();
Stream* file_stream = file_stream_alloc(storage);
SaveNoncesResult_t* result = malloc(sizeof(SaveNoncesResult_t));
result->saved = 0;
result->invalid = 0;
result->skipped = 0;
mifare_nested_worker_get_nonces_file_path(data, path);
file_stream_open(file_stream, furi_string_get_cstr(path), FSAM_READ_WRITE, FSOM_CREATE_ALWAYS);
@@ -472,23 +477,26 @@ void mifare_nested_worker_write_nonces(
for(uint8_t tries = 0; tries < tries_count; tries++) {
for(uint8_t sector = 0; sector < sector_count; sector++) {
for(uint8_t key_type = 0; key_type < 2; key_type++) {
if(nonces->nonces[sector][key_type][tries]->collected &&
!nonces->nonces[sector][key_type][tries]->skipped) {
if(nonces->nonces[sector][key_type][tries]->invalid) {
result->invalid++;
} else if(nonces->nonces[sector][key_type][tries]->skipped) {
result->skipped++;
} else if(nonces->nonces[sector][key_type][tries]->collected) {
if(nonces->nonces[sector][key_type][tries]->hardnested) {
FuriString* path = furi_string_alloc();
FuriString* hardnested_path = furi_string_alloc();
mifare_nested_worker_get_hardnested_file_path(
data, path, sector, key_type);
data, hardnested_path, sector, key_type);
FuriString* str = furi_string_alloc_printf(
"HardNested: Key %c cuid 0x%08lx file %s sec %u\n",
!key_type ? 'A' : 'B',
nonces->cuid,
furi_string_get_cstr(path),
furi_string_get_cstr(hardnested_path),
sector);
stream_write_string(file_stream, str);
furi_string_free(path);
furi_string_free(hardnested_path);
furi_string_free(str);
} else {
FuriString* str = furi_string_alloc_printf(
@@ -515,6 +523,8 @@ void mifare_nested_worker_write_nonces(
stream_write_string(file_stream, str);
furi_string_free(str);
}
result->saved++;
}
}
}
@@ -529,10 +539,20 @@ void mifare_nested_worker_write_nonces(
}
free_nonces(nonces, sector_count, free_tries_count);
furi_string_free(path);
file_stream_close(file_stream);
free(file_stream);
if(!result->saved) {
FURI_LOG_E(TAG, "No nonces collected, removing file...");
if(!storage_simply_remove(storage, furi_string_get_cstr(path))) {
FURI_LOG_E(TAG, "Failed to remove .nonces file");
}
}
furi_string_free(path);
furi_record_close(RECORD_STORAGE);
return result;
}
bool mifare_nested_worker_check_initial_keys(
@@ -760,7 +780,7 @@ void mifare_nested_worker_collect_nonces_static(MifareNestedWorker* mifare_neste
mifare_nested_worker_get_block_by_sector(sector),
key_type);
info->skipped = true;
info->invalid = true;
nonces.nonces[sector][key_type][0] = info;
@@ -819,12 +839,20 @@ void mifare_nested_worker_collect_nonces_static(MifareNestedWorker* mifare_neste
break;
}
SaveNoncesResult_t* result =
mifare_nested_worker_write_nonces(&data, storage, &nonces, 1, 1, sector_count, 0, 0);
free(mf_data);
if(result->saved) {
mifare_nested_worker->callback(
MifareNestedWorkerEventNoncesCollected, mifare_nested_worker->context);
} else {
mifare_nested_worker->context->save_state = result;
mifare_nested_worker->callback(
MifareNestedWorkerEventNoNoncesCollected, mifare_nested_worker->context);
}
nfc_deactivate();
}
@@ -932,7 +960,7 @@ void mifare_nested_worker_collect_nonces_hard(MifareNestedWorker* mifare_nested_
mifare_nested_worker_get_block_by_sector(sector),
key_type);
info->skipped = true;
info->invalid = true;
nonces.nonces[sector][key_type][0] = info;
mifare_nested_worker->context->nonces = &nonces;
@@ -1061,12 +1089,20 @@ void mifare_nested_worker_collect_nonces_hard(MifareNestedWorker* mifare_nested_
}
}
SaveNoncesResult_t* result =
mifare_nested_worker_write_nonces(&data, storage, &nonces, 1, 1, sector_count, 0, 0);
free(mf_data);
if(result->saved) {
mifare_nested_worker->callback(
MifareNestedWorkerEventNoncesCollected, mifare_nested_worker->context);
} else {
mifare_nested_worker->context->save_state = result;
mifare_nested_worker->callback(
MifareNestedWorkerEventNoNoncesCollected, mifare_nested_worker->context);
}
nfc_deactivate();
}
@@ -1371,13 +1407,20 @@ void mifare_nested_worker_collect_nonces(MifareNestedWorker* mifare_nested_worke
break;
}
mifare_nested_worker_write_nonces(
SaveNoncesResult_t* result = mifare_nested_worker_write_nonces(
&data, storage, &nonces, tries_count, 3, sector_count, delay, distance);
free(mf_data);
if(result->saved) {
mifare_nested_worker->callback(
MifareNestedWorkerEventNoncesCollected, mifare_nested_worker->context);
} else {
mifare_nested_worker->context->save_state = result;
mifare_nested_worker->callback(
MifareNestedWorkerEventNoNoncesCollected, mifare_nested_worker->context);
}
nfc_deactivate();
}

View File

@@ -22,6 +22,7 @@ typedef enum {
MifareNestedWorkerEventReserved = 1000,
MifareNestedWorkerEventNoTagDetected,
MifareNestedWorkerEventNoNoncesCollected,
MifareNestedWorkerEventNoncesCollected,
MifareNestedWorkerEventCollecting,
@@ -64,8 +65,9 @@ typedef struct {
uint32_t target_nt[2];
uint32_t target_ks[2];
uint8_t parity[2][4];
bool collected;
bool skipped;
bool invalid;
bool collected;
bool hardnested;
} Nonces;
@@ -87,3 +89,9 @@ typedef struct {
uint32_t sector_keys;
bool tag_lost;
} KeyInfo_t;
typedef struct {
uint32_t saved;
uint32_t invalid;
uint32_t skipped;
} SaveNoncesResult_t;

View File

@@ -51,7 +51,7 @@ void mifare_nested_scene_about_on_enter(void* context) {
14,
AlignCenter,
AlignBottom,
"\e#\e! Flipper (Mifare) Nested \e!\n",
"\e#\e! Flipper Nested \e!\n",
false);
widget_add_text_scroll_element(
mifare_nested->widget, 0, 16, 128, 50, furi_string_get_cstr(temp_str));

View File

@@ -56,14 +56,7 @@ bool mifare_nested_scene_check_on_event(void* context, SceneManagerEvent event)
bool consumed = false;
if(event.type == SceneManagerEventTypeCustom) {
if(event.event == MifareNestedWorkerEventNoncesCollected) {
scene_manager_next_scene(
mifare_nested->scene_manager, MifareNestedSceneNoncesCollected);
consumed = true;
} else if(event.event == MifareNestedWorkerEventAttackFailed) {
scene_manager_next_scene(mifare_nested->scene_manager, MifareNestedSceneFailed);
consumed = true;
} else if(event.event == MifareNestedWorkerEventCollecting) {
if(event.event == MifareNestedWorkerEventCollecting) {
if(mifare_nested->run == NestedRunAttack) {
if(mifare_nested->settings->only_hardnested) {
FURI_LOG_I("MifareNested", "Using Hard Nested because user settings");

View File

@@ -84,13 +84,6 @@ bool mifare_nested_scene_check_keys_on_event(void* context, SceneManagerEvent ev
if(event.event == GuiButtonTypeCenter) {
scene_manager_search_and_switch_to_previous_scene(mifare_nested->scene_manager, 0);
consumed = true;
} else if(event.event == MifareNestedWorkerEventNoncesCollected) {
scene_manager_next_scene(
mifare_nested->scene_manager, MifareNestedSceneNoncesCollected);
consumed = true;
} else if(event.event == MifareNestedWorkerEventNeedKey) {
scene_manager_next_scene(mifare_nested->scene_manager, MifareNestedSceneNoKeys);
consumed = true;
} else if(event.event == MifareNestedWorkerEventKeysFound) {
scene_manager_next_scene(mifare_nested->scene_manager, MifareNestedSceneAddedKeys);
consumed = true;

View File

@@ -120,6 +120,10 @@ bool mifare_nested_scene_collecting_on_event(void* context, SceneManagerEvent ev
scene_manager_next_scene(
mifare_nested->scene_manager, MifareNestedSceneNoncesCollected);
consumed = true;
} else if(event.event == MifareNestedWorkerEventNoNoncesCollected) {
scene_manager_next_scene(
mifare_nested->scene_manager, MifareNestedSceneNoNoncesCollected);
consumed = true;
} else if(event.event == MifareNestedWorkerEventAttackFailed) {
scene_manager_next_scene(mifare_nested->scene_manager, MifareNestedSceneFailed);
consumed = true;

View File

@@ -11,3 +11,4 @@ ADD_SCENE(mifare_nested, static_encrypted_nonce, StaticEncryptedNonce)
ADD_SCENE(mifare_nested, need_key_recovery, NeedKeyRecovery)
ADD_SCENE(mifare_nested, need_collection, NeedCollection)
ADD_SCENE(mifare_nested, settings, Settings)
ADD_SCENE(mifare_nested, no_nonces_collected, NoNoncesCollected)

View File

@@ -0,0 +1,94 @@
#include "../mifare_nested_i.h"
void mifare_nested_scene_no_nonces_collected_widget_callback(
GuiButtonType result,
InputType type,
void* context) {
MifareNested* mifare_nested = context;
if(type == InputTypeShort) {
view_dispatcher_send_custom_event(mifare_nested->view_dispatcher, result);
}
}
void mifare_nested_scene_no_nonces_collected_on_enter(void* context) {
MifareNested* mifare_nested = context;
Widget* widget = mifare_nested->widget;
SaveNoncesResult_t* save_state = mifare_nested->save_state;
notification_message(mifare_nested->notifications, &sequence_error);
widget_add_icon_element(widget, 73, 12, &I_DolphinCry);
widget_add_string_element(
widget, 0, 0, AlignLeft, AlignTop, FontPrimary, "No nonces collected");
uint32_t index = 12;
if(save_state->skipped) {
char append_skipped[8] = {'s', 'e', 'c', 't', 'o', 'r', ' ', '\0'};
if(save_state->skipped != 1) {
append_skipped[6] = 's';
}
char draw_str[32] = {};
snprintf(
draw_str, sizeof(draw_str), "Skipped: %lu %s", save_state->skipped, append_skipped);
widget_add_string_element(widget, 0, index, AlignLeft, AlignTop, FontSecondary, draw_str);
widget_add_string_element(
widget, 0, index + 10, AlignLeft, AlignTop, FontSecondary, "(already has keys)");
index += 20;
}
if(save_state->invalid) {
char append_invalid[8] = {'s', 'e', 'c', 't', 'o', 'r', ' ', '\0'};
if(save_state->invalid != 1) {
append_invalid[6] = 's';
}
char draw_str[32] = {};
snprintf(
draw_str, sizeof(draw_str), "Invalid: %lu %s", save_state->invalid, append_invalid);
widget_add_string_element(widget, 0, index, AlignLeft, AlignTop, FontSecondary, draw_str);
widget_add_string_element(
widget, 0, index + 10, AlignLeft, AlignTop, FontSecondary, "(can't auth)");
}
free(save_state);
widget_add_button_element(
widget,
GuiButtonTypeLeft,
"Back",
mifare_nested_scene_no_nonces_collected_widget_callback,
mifare_nested);
// Setup and start worker
view_dispatcher_switch_to_view(mifare_nested->view_dispatcher, MifareNestedViewWidget);
}
bool mifare_nested_scene_no_nonces_collected_on_event(void* context, SceneManagerEvent event) {
MifareNested* mifare_nested = context;
bool consumed = false;
if(event.type == SceneManagerEventTypeCustom) {
if(event.event == GuiButtonTypeCenter || event.event == GuiButtonTypeLeft) {
scene_manager_search_and_switch_to_previous_scene(mifare_nested->scene_manager, 0);
consumed = true;
}
} else if(event.type == SceneManagerEventTypeBack) {
scene_manager_search_and_switch_to_previous_scene(mifare_nested->scene_manager, 0);
consumed = true;
}
return consumed;
}
void mifare_nested_scene_no_nonces_collected_on_exit(void* context) {
MifareNested* mifare_nested = context;
widget_reset(mifare_nested->widget);
}

View File

@@ -11,7 +11,7 @@ App(
"gui",
"dialogs",
],
stack_size=4 * 1024,
stack_size=2 * 1024,
order=11,
fap_libs=["assets"],
fap_icon="subghz_remote_10px.png",

View File

@@ -1,12 +1,14 @@
#pragma once
typedef enum {
//SubmenuIndex
SubmenuIndexSubRemOpenMapFile,
// StartSubmenuIndex
SubmenuIndexSubRemOpenMapFile = 0,
#if FURI_DEBUG
SubmenuIndexSubRemRemoteView,
SubmenuIndexSubRemAbout,
#endif
// SubmenuIndexSubRemAbout,
//SubRemCustomEvent
// SubRemCustomEvent
SubRemCustomEventViewRemoteStartUP = 100,
SubRemCustomEventViewRemoteStartDOWN,
SubRemCustomEventViewRemoteStartLEFT,

View File

@@ -8,7 +8,7 @@ SubRemSubFilePreset* subrem_sub_file_preset_alloc() {
sub_preset->fff_data = flipper_format_string_alloc();
sub_preset->file_path = furi_string_alloc();
sub_preset->protocaol_name = furi_string_alloc();
sub_preset->label = furi_string_alloc_set_str("N/A");
sub_preset->label = furi_string_alloc();
sub_preset->freq_preset.name = furi_string_alloc();
@@ -34,7 +34,7 @@ void subrem_sub_file_preset_free(SubRemSubFilePreset* sub_preset) {
void subrem_sub_file_preset_reset(SubRemSubFilePreset* sub_preset) {
furi_assert(sub_preset);
furi_string_set_str(sub_preset->label, "N/A");
furi_string_set_str(sub_preset->label, "");
furi_string_reset(sub_preset->protocaol_name);
furi_string_reset(sub_preset->file_path);
@@ -77,7 +77,7 @@ SubRemLoadSubState subrem_sub_preset_load(
break;
}
SubGhzSetting* setting = subghz_txrx_get_setting(txrx); // txrx->setting;
SubGhzSetting* setting = subghz_txrx_get_setting(txrx);
//Load frequency or using default from settings
ret = SubRemLoadSubStateErrorFreq;
@@ -147,8 +147,7 @@ SubRemLoadSubState subrem_sub_preset_load(
if(protocol->flag & SubGhzProtocolFlag_Send) {
if((protocol->type == SubGhzProtocolTypeStatic) ||
(protocol->type == SubGhzProtocolTypeDynamic) ||
// TODO: BINRAW It probably works, but checks are needed.
// (protocol->type == SubGhzProtocolTypeBinRAW) ||
(protocol->type == SubGhzProtocolTypeBinRAW) ||
(protocol->type == SubGhzProtocolTypeRAW)) {
sub_preset->type = protocol->type;
} else {
@@ -175,5 +174,6 @@ SubRemLoadSubState subrem_sub_preset_load(
} while(false);
furi_string_free(temp_str);
sub_preset->load_state = ret;
return ret;
}

View File

@@ -1,9 +1,10 @@
#pragma once
#include "subrem_types.h"
#include "txrx/subghz_txrx.h"
#include <flipper_format/flipper_format_i.h>
#include <lib/subghz/protocols/protocol_items.h>
#include "applications/main/subghz/helpers/subghz_txrx.h"
#include <lib/subghz/types.h>
typedef struct {
FuriString* name;

View File

@@ -3,9 +3,8 @@
#include <furi.h>
#include <furi_hal.h>
// TODO: File version/type logic
// #define SUBREM_APP_APP_FILE_VERSION 1
// #define SUBREM_APP_APP_FILE_TYPE "Flipper SubRem Map file"
#define SUBREM_APP_APP_FILE_VERSION 1
#define SUBREM_APP_APP_FILE_TYPE "Flipper SubRem Map file"
#define SUBREM_APP_EXTENSION ".txt"
typedef enum {
@@ -18,10 +17,7 @@ typedef enum {
} SubRemSubKeyName;
typedef enum {
SubRemViewSubmenu,
SubRemViewWidget,
SubRemViewPopup,
SubRemViewTextInput,
SubRemViewIDSubmenu,
SubRemViewIDRemote,
} SubRemViewID;
@@ -29,6 +25,7 @@ typedef enum {
SubRemLoadSubStateNotSet = 0,
SubRemLoadSubStatePreloaded,
SubRemLoadSubStateError,
SubRemLoadSubStateErrorIncorectPath,
SubRemLoadSubStateErrorNoFile,
SubRemLoadSubStateErrorFreq,
SubRemLoadSubStateErrorMod,

View File

@@ -0,0 +1,3 @@
#pragma once
#include "../../../../main/subghz/helpers/subghz_txrx.h"

View File

@@ -1,3 +1,5 @@
#ifndef SUBREM_LIGHT
ADD_SCENE(subrem, start, Start)
ADD_SCENE(subrem, openmapfile, OpenMapFile)
#endif
ADD_SCENE(subrem, open_map_file, OpenMapFile)
ADD_SCENE(subrem, remote, Remote)

View File

@@ -0,0 +1,43 @@
#include "../subghz_remote_app_i.h"
void subrem_scene_open_map_file_on_enter(void* context) {
furi_assert(context);
SubGhzRemoteApp* app = context;
SubRemLoadMapState load_state = subrem_load_from_file(app);
if(load_state == SubRemLoadMapStateOK || load_state == SubRemLoadMapStateNotAllOK) {
scene_manager_next_scene(app->scene_manager, SubRemSceneRemote);
} else {
if(load_state != SubRemLoadMapStateBack) {
#ifdef SUBREM_LIGHT
dialog_message_show_storage_error(app->dialogs, "Can't load\nMap file");
#else
DialogMessage* message = dialog_message_alloc();
dialog_message_set_header(message, "Map File Error", 64, 8, AlignCenter, AlignCenter);
dialog_message_set_text(
message, "Can't load\nMap file", 64, 32, AlignCenter, AlignCenter);
dialog_message_set_buttons(message, "Back", NULL, NULL);
dialog_message_show(app->dialogs, message);
dialog_message_free(message);
#endif
}
// TODO: Map Preset Reset
if(!scene_manager_previous_scene(app->scene_manager)) {
scene_manager_stop(app->scene_manager);
view_dispatcher_stop(app->view_dispatcher);
}
}
}
bool subrem_scene_open_map_file_on_event(void* context, SceneManagerEvent event) {
UNUSED(context);
UNUSED(event);
return false;
}
void subrem_scene_open_map_file_on_exit(void* context) {
UNUSED(context);
}

View File

@@ -1,42 +0,0 @@
#include "../subghz_remote_app_i.h"
void subrem_scene_openmapfile_on_enter(void* context) {
SubGhzRemoteApp* app = context;
SubRemLoadMapState load_state = subrem_load_from_file(app);
if(load_state != SubRemLoadMapStateOK && load_state != SubRemLoadMapStateNotAllOK &&
load_state != SubRemLoadMapStateBack) {
#ifdef SUBREM_LIGHT
dialog_message_show_storage_error(app->dialogs, "Can't load\nMap file");
#else
DialogMessage* message = dialog_message_alloc();
dialog_message_set_header(message, "Map File Error", 64, 8, AlignCenter, AlignCenter);
dialog_message_set_text(message, "Can't load\nMap file", 64, 32, AlignCenter, AlignCenter);
dialog_message_set_buttons(message, "Back", NULL, NULL);
dialog_message_show(app->dialogs, message);
dialog_message_free(message);
#endif
}
if(load_state == SubRemLoadMapStateOK || load_state == SubRemLoadMapStateNotAllOK) {
scene_manager_next_scene(app->scene_manager, SubRemSceneRemote);
} else {
// TODO: Map Preset Reset
if(!scene_manager_search_and_switch_to_previous_scene(
app->scene_manager, SubRemSceneStart)) {
scene_manager_stop(app->scene_manager);
view_dispatcher_stop(app->view_dispatcher);
}
}
}
bool subrem_scene_openmapfile_on_event(void* context, SceneManagerEvent event) {
UNUSED(context);
UNUSED(event);
return false;
}
void subrem_scene_openmapfile_on_exit(void* context) {
UNUSED(context);
}

View File

@@ -35,24 +35,10 @@ static uint8_t subrem_scene_remote_event_to_index(SubRemCustomEvent event_id) {
return ret;
}
static bool subrem_scene_remote_update_data_show(void* context) {
SubGhzRemoteApp* app = context;
const char* labels[SubRemSubKeyNameMaxCount];
for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) {
labels[i] = furi_string_get_cstr(app->map_preset->subs_preset[i]->label);
}
subrem_view_remote_add_data_to_show(app->subrem_remote_view, labels);
return true;
}
void subrem_scene_remote_on_enter(void* context) {
SubGhzRemoteApp* app = context;
subrem_scene_remote_update_data_show(app);
subrem_view_remote_update_data_labels(app->subrem_remote_view, app->map_preset->subs_preset);
subrem_view_remote_set_callback(app->subrem_remote_view, subrem_scene_remote_callback, app);
@@ -63,14 +49,10 @@ bool subrem_scene_remote_on_event(void* context, SceneManagerEvent event) {
SubGhzRemoteApp* app = context;
if(event.type == SceneManagerEventTypeCustom) {
if(event.event == SubRemCustomEventViewRemoteBack) {
if(!scene_manager_search_and_switch_to_previous_scene(
app->scene_manager, SubRemSceneOpenMapFile)) {
if(!scene_manager_search_and_switch_to_previous_scene(
app->scene_manager, SubRemSceneStart)) {
if(!scene_manager_previous_scene(app->scene_manager)) {
scene_manager_stop(app->scene_manager);
view_dispatcher_stop(app->view_dispatcher);
}
}
return true;
} else if(
event.event == SubRemCustomEventViewRemoteStartUP ||

View File

@@ -33,13 +33,11 @@ void subrem_scene_start_on_enter(void* context) {
// SubmenuIndexSubGhzRemoteAbout,
// subrem_scene_start_submenu_callback,
// app);
// TODO: set scene state in subrem alloc
// submenu_set_selected_item(
// submenu, scene_manager_get_scene_state(app->scene_manager, SubRemSceneStart));
submenu_set_selected_item(submenu, SubmenuIndexSubRemOpenMapFile);
view_dispatcher_switch_to_view(app->view_dispatcher, SubRemViewSubmenu);
#ifndef SUBREM_LIGHT
submenu_set_selected_item(
submenu, scene_manager_get_scene_state(app->scene_manager, SubRemSceneStart));
#endif
view_dispatcher_switch_to_view(app->view_dispatcher, SubRemViewIDSubmenu);
}
bool subrem_scene_start_on_event(void* context, SceneManagerEvent event) {
@@ -50,6 +48,10 @@ bool subrem_scene_start_on_event(void* context, SceneManagerEvent event) {
if(event.type == SceneManagerEventTypeCustom) {
if(event.event == SubmenuIndexSubRemOpenMapFile) {
#ifndef SUBREM_LIGHT
scene_manager_set_scene_state(
app->scene_manager, SubRemSceneStart, SubmenuIndexSubRemOpenMapFile);
#endif
scene_manager_next_scene(app->scene_manager, SubRemSceneOpenMapFile);
consumed = true;
}

View File

@@ -1,8 +1,6 @@
#include "subghz_remote_app_i.h"
#include <dolphin/dolphin.h>
#include <lib/subghz/protocols/protocol_items.h>
static bool subghz_remote_app_custom_event_callback(void* context, uint32_t event) {
furi_assert(context);
SubGhzRemoteApp* app = context;
@@ -71,9 +69,9 @@ SubGhzRemoteApp* subghz_remote_app_alloc() {
// SubMenu
app->submenu = submenu_alloc();
view_dispatcher_add_view(
app->view_dispatcher, SubRemViewSubmenu, submenu_get_view(app->submenu));
app->view_dispatcher, SubRemViewIDSubmenu, submenu_get_view(app->submenu));
//Dialog
// Dialog
app->dialogs = furi_record_open(RECORD_DIALOGS);
// Remote view
@@ -92,13 +90,13 @@ SubGhzRemoteApp* subghz_remote_app_alloc() {
subghz_txrx_set_need_save_callback(app->txrx, subrem_save_active_sub, app);
app->tx_running = false;
// #ifdef SUBREM_LIGHT
#ifdef SUBREM_LIGHT
scene_manager_next_scene(app->scene_manager, SubRemSceneOpenMapFile);
// #else
// scene_manager_next_scene(app->scene_manager, SubRemSceneStart);
// #endif
#else
scene_manager_next_scene(app->scene_manager, SubRemSceneStart);
scene_manager_set_scene_state(
app->scene_manager, SubRemSceneStart, SubmenuIndexSubRemOpenMapFile);
#endif
return app;
}
@@ -114,10 +112,10 @@ void subghz_remote_app_free(SubGhzRemoteApp* app) {
furi_hal_subghz_init_radio_type(SubGhzRadioInternal);
// Submenu
view_dispatcher_remove_view(app->view_dispatcher, SubRemViewSubmenu);
view_dispatcher_remove_view(app->view_dispatcher, SubRemViewIDSubmenu);
submenu_free(app->submenu);
//Dialog
// Dialog
furi_record_close(RECORD_DIALOGS);
// Remote view

View File

@@ -2,23 +2,18 @@
#include <lib/toolbox/path.h>
#include <flipper_format/flipper_format_i.h>
#include <lib/subghz/protocols/protocol_items.h>
#include "applications/main/subghz/helpers/subghz_txrx_i.h"
#include "helpers/txrx/subghz_txrx.h"
// #include <lib/subghz/protocols/keeloq.h>
// #include <lib/subghz/protocols/star_line.h>
#ifdef APP_SUBGHZREMOTE
#include <lib/subghz/protocols/protocol_items.h>
#include <lib/subghz/blocks/custom_btn.h>
#endif
#define TAG "SubGhzRemote"
// XXX Using TxRx
// [x] use TxRx preset subrem_sub_preset_load & subrem_tx_start_sub
// [x] subrem_sub_preset_load & drop subrem_set_preset_data
// [x] subrem_tx_start_sub
// [x] subrem_tx_stop_sub
static const char* map_file_labels[SubRemSubKeyNameMaxCount][2] = {
[SubRemSubKeyNameUp] = {"UP", "ULABEL"},
[SubRemSubKeyNameDown] = {"DOWN", "DLABEL"},
@@ -45,30 +40,25 @@ static SubRemLoadMapState subrem_map_preset_check(
bool all_loaded = true;
SubRemLoadMapState ret = SubRemLoadMapStateErrorBrokenFile;
SubRemLoadSubState sub_preset_loaded;
SubRemLoadSubState sub_loadig_state;
SubRemSubFilePreset* sub_preset;
for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) {
sub_preset = map_preset->subs_preset[i];
sub_preset_loaded = SubRemLoadSubStateErrorNoFile;
sub_loadig_state = SubRemLoadSubStateErrorNoFile;
if(furi_string_empty(sub_preset->file_path)) {
// FURI_LOG_I(TAG, "Empty file path");
} else if(!flipper_format_file_open_existing(
fff_data_file, furi_string_get_cstr(sub_preset->file_path))) {
sub_preset->load_state = SubRemLoadSubStateErrorNoFile;
FURI_LOG_W(TAG, "Error open file %s", furi_string_get_cstr(sub_preset->file_path));
} else {
sub_preset_loaded = subrem_sub_preset_load(sub_preset, txrx, fff_data_file);
sub_loadig_state = subrem_sub_preset_load(sub_preset, txrx, fff_data_file);
}
// TODO:
// Load file state logic
// Label depending on the state
// Move to remote scene
if(sub_preset_loaded != SubRemLoadSubStateOK) {
furi_string_set_str(sub_preset->label, "N/A");
if(sub_loadig_state != SubRemLoadSubStateOK) {
all_loaded = false;
} else {
ret = SubRemLoadMapStateNotAllOK;
@@ -96,6 +86,9 @@ static bool subrem_map_preset_load(SubRemMapPreset* map_preset, FlipperFormat* f
FURI_LOG_W(TAG, "No file patch for %s", map_file_labels[i][0]);
#endif
sub_preset->type = SubGhzProtocolTypeUnknown;
} else if(!path_contains_only_ascii(furi_string_get_cstr(sub_preset->file_path))) {
FURI_LOG_E(TAG, "Incorrect characters in [%s] file path", map_file_labels[i][0]);
sub_preset->type = SubGhzProtocolTypeUnknown;
} else if(!flipper_format_rewind(fff_data_file)) {
// Rewind error
} else if(!flipper_format_read_string(
@@ -103,8 +96,6 @@ static bool subrem_map_preset_load(SubRemMapPreset* map_preset, FlipperFormat* f
#if FURI_DEBUG
FURI_LOG_W(TAG, "No Label for %s", map_file_labels[i][0]);
#endif
// TODO move to remote scene
path_extract_filename(sub_preset->file_path, sub_preset->label, true);
ret = true;
} else {
ret = true;
@@ -237,17 +228,15 @@ bool subrem_tx_start_sub(SubGhzRemoteApp* app, SubRemSubFilePreset* sub_preset)
NULL,
0);
subghz_custom_btn_set(SUBGHZ_CUSTOM_BTN_OK);
keeloq_reset_original_btn();
#ifdef APP_SUBGHZREMOTE
subghz_custom_btns_reset();
#endif
if(subghz_txrx_tx_start(app->txrx, sub_preset->fff_data) == SubGhzTxRxStartTxStateOk) {
ret = true;
}
}
app->tx_running = ret;
return ret;
}
@@ -256,23 +245,15 @@ bool subrem_tx_stop_sub(SubGhzRemoteApp* app, bool forced) {
SubRemSubFilePreset* sub_preset = app->map_preset->subs_preset[app->chusen_sub];
if(forced || (sub_preset->type != SubGhzProtocolTypeRAW)) {
// XXX drop app->tx_running
if(app->tx_running) {
subghz_txrx_stop(app->txrx);
#ifdef APP_SUBGHZREMOTE
if(sub_preset->type == SubGhzProtocolTypeDynamic) {
keeloq_reset_mfname();
keeloq_reset_kl_type();
keeloq_reset_original_btn();
subghz_txrx_reset_dynamic_and_custom_btns(app->txrx);
}
subghz_custom_btns_reset();
star_line_reset_mfname();
star_line_reset_kl_type();
}
app->tx_running = false;
#endif
return true;
}
}
return false;
}
@@ -284,7 +265,7 @@ SubRemLoadMapState subrem_load_from_file(SubGhzRemoteApp* app) {
SubRemLoadMapState ret = SubRemLoadMapStateBack;
DialogsFileBrowserOptions browser_options;
dialog_file_browser_set_basic_options(&browser_options, SUBREM_APP_EXTENSION, &I_sub1_10px);
dialog_file_browser_set_basic_options(&browser_options, SUBREM_APP_EXTENSION, &I_subrem_10px);
browser_options.base_path = SUBREM_APP_FOLDER;
// Input events and views are managed by file_select

View File

@@ -2,34 +2,31 @@
#include "helpers/subrem_types.h"
#include "helpers/subrem_presets.h"
#include "scenes/subrem_scene.h"
#include "applications/main/subghz/helpers/subghz_txrx.h"
#include "helpers/txrx/subghz_txrx.h"
#ifdef APP_SUBGHZREMOTE
#include <assets_icons.h>
#else
#include <subrem_remote_fap_icons.h>
#endif
#include "views/remote.h"
#include "scenes/subrem_scene.h"
#include <gui/gui.h>
#include <gui/view_dispatcher.h>
#include <gui/scene_manager.h>
#include <gui/modules/submenu.h>
#include <gui/modules/widget.h>
#include <notification/notification_messages.h>
#include <gui/modules/text_input.h>
#include <dialogs/dialogs.h>
#include <storage/storage.h>
#include <gui/modules/popup.h>
#include <dialogs/dialogs.h>
#include <notification/notification_messages.h>
#include <storage/storage.h>
#include <flipper_format/flipper_format_i.h>
#include <lib/subghz/protocols/raw.h>
#include <lib/subghz/subghz_setting.h>
#include <lib/subghz/receiver.h>
#include <lib/subghz/transmitter.h>
#define SUBREM_APP_FOLDER EXT_PATH("subghz/remote")
#define SUBREM_MAX_LEN_NAME 64
@@ -42,7 +39,6 @@ typedef struct {
Submenu* submenu;
FuriString* file_path;
// char file_name_tmp[SUBREM_MAX_LEN_NAME];
SubRemViewRemote* subrem_remote_view;
@@ -50,8 +46,6 @@ typedef struct {
SubGhzTxRx* txrx;
bool tx_running;
uint8_t chusen_sub;
} SubGhzRemoteApp;

View File

@@ -4,7 +4,11 @@
#include <input/input.h>
#include <gui/elements.h>
#define SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH 12
#include <lib/toolbox/path.h>
#define SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH 30
#define SUBREM_VIEW_REMOTE_LEFT_OFFSET 10
#define SUBREM_VIEW_REMOTE_RIGHT_OFFSET 22
struct SubRemViewRemote {
View* view;
@@ -12,19 +16,8 @@ struct SubRemViewRemote {
void* context;
};
// TODO: model
typedef struct {
// FuriString* up_label;
// FuriString* down_label;
// FuriString* left_label;
// FuriString* right_label;
// FuriString* ok_label;
char* up_label;
char* down_label;
char* left_label;
char* right_label;
char* ok_label;
char* labels[SubRemSubKeyNameMaxCount];
SubRemViewRemoteState state;
@@ -41,26 +34,61 @@ void subrem_view_remote_set_callback(
subrem_view_remote->context = context;
}
void subrem_view_remote_add_data_to_show(SubRemViewRemote* subrem_view_remote, const char** labels) {
void subrem_view_remote_update_data_labels(
SubRemViewRemote* subrem_view_remote,
SubRemSubFilePreset** subs_presets) {
furi_assert(subrem_view_remote);
furi_assert(subs_presets);
FuriString* labels[SubRemSubKeyNameMaxCount];
SubRemSubFilePreset* sub_preset;
for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) {
sub_preset = subs_presets[i];
switch(sub_preset->load_state) {
case SubRemLoadSubStateOK:
if(!furi_string_empty(sub_preset->label)) {
labels[i] = furi_string_alloc_set(sub_preset->label);
} else if(!furi_string_empty(sub_preset->file_path)) {
labels[i] = furi_string_alloc();
path_extract_filename(sub_preset->file_path, labels[i], true);
} else {
labels[i] = furi_string_alloc_set("Empty Label");
}
break;
case SubRemLoadSubStateErrorNoFile:
labels[i] = furi_string_alloc_set("[X] Can't open file");
break;
case SubRemLoadSubStateErrorFreq:
case SubRemLoadSubStateErrorMod:
case SubRemLoadSubStateErrorProtocol:
labels[i] = furi_string_alloc_set("[X] Error in .sub file");
break;
default:
labels[i] = furi_string_alloc_set("");
break;
}
}
with_view_model(
subrem_view_remote->view,
SubRemViewRemoteModel * model,
{
strncpy(model->up_label, labels[0], SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH);
strncpy(model->down_label, labels[1], SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH);
strncpy(model->left_label, labels[2], SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH);
strncpy(model->right_label, labels[3], SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH);
strncpy(model->ok_label, labels[4], SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH);
// furi_string_set(model->up_label, up_label);
// furi_string_set(model->down_label, down_label);
// furi_string_set(model->left_label, left_label);
// furi_string_set(model->right_label, right_label);
// furi_string_set(model->ok_label, ok_label);
for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) {
strncpy(
model->labels[i],
furi_string_get_cstr(labels[i]),
SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH);
}
},
true);
for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) {
furi_string_free(labels[i]);
}
}
void subrem_view_remote_set_state(
@@ -95,24 +123,32 @@ void subrem_view_remote_draw(Canvas* canvas, SubRemViewRemoteModel* model) {
//Labels
canvas_set_font(canvas, FontSecondary);
canvas_draw_str(canvas, 10, 10, model->up_label);
canvas_draw_str(canvas, 10, 20, model->down_label);
canvas_draw_str(canvas, 10, 30, model->left_label);
canvas_draw_str(canvas, 10, 40, model->right_label);
canvas_draw_str(canvas, 10, 50, model->ok_label);
// canvas_draw_str(canvas, 10, 10, furi_string_get_cstr(model->up_label));
// canvas_draw_str(canvas, 10, 10, furi_string_get_cstr(model->up_label));
// canvas_draw_str(canvas, 10, 10, furi_string_get_cstr(model->up_label));
// canvas_draw_str(canvas, 10, 10, furi_string_get_cstr(model->up_label));
// canvas_draw_str(canvas, 10, 10, furi_string_get_cstr(model->up_label));
uint8_t y = 0;
for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) {
elements_text_box(
canvas,
SUBREM_VIEW_REMOTE_LEFT_OFFSET,
y + 2,
126 - SUBREM_VIEW_REMOTE_LEFT_OFFSET - SUBREM_VIEW_REMOTE_RIGHT_OFFSET,
12,
AlignLeft,
AlignBottom,
model->labels[i],
false);
y += 10;
}
if(model->state == SubRemViewRemoteStateOFF) {
elements_button_left(canvas, "Back");
elements_button_right(canvas, "Save");
} else {
canvas_draw_str_aligned(canvas, 11, 62, AlignLeft, AlignBottom, "Hold=Exit.");
}
//Status text and indicator
canvas_draw_icon(canvas, 113, 15, &I_Pin_cell_13x13);
if(model->state == SubRemViewRemoteStateIdle) {
if(model->state == SubRemViewRemoteStateIdle || model->state == SubRemViewRemoteStateOFF) {
canvas_draw_str_aligned(canvas, 126, 10, AlignRight, AlignBottom, "Idle");
} else {
switch(model->state) {
@@ -147,10 +183,6 @@ void subrem_view_remote_draw(Canvas* canvas, SubRemViewRemoteModel* model) {
break;
}
}
//Repeat indicator
//canvas_draw_str_aligned(canvas, 125, 40, AlignRight, AlignBottom, "Repeat:");
//canvas_draw_icon(canvas, 115, 39, &I_SubGHzRemote_Repeat_12x14);
//canvas_draw_str_aligned(canvas, 125, 62, AlignRight, AlignBottom, int_to_char(app->repeat));
}
bool subrem_view_remote_input(InputEvent* event, void* context) {
@@ -158,17 +190,6 @@ bool subrem_view_remote_input(InputEvent* event, void* context) {
SubRemViewRemote* subrem_view_remote = context;
if(event->key == InputKeyBack && event->type == InputTypeLong) {
with_view_model(
subrem_view_remote->view,
SubRemViewRemoteModel * model,
{
strcpy(model->up_label, "N/A");
strcpy(model->down_label, "N/A");
strcpy(model->left_label, "N/A");
strcpy(model->right_label, "N/A");
strcpy(model->ok_label, "N/A");
},
false);
subrem_view_remote->callback(SubRemCustomEventViewRemoteBack, subrem_view_remote->context);
return true;
} else if(event->key == InputKeyBack && event->type == InputTypeShort) {
@@ -240,23 +261,10 @@ SubRemViewRemote* subrem_view_remote_alloc() {
{
model->state = SubRemViewRemoteStateIdle;
model->up_label = malloc(sizeof(char) * SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH + 1);
model->down_label = malloc(sizeof(char) * SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH + 1);
model->left_label = malloc(sizeof(char) * SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH + 1);
model->right_label = malloc(sizeof(char) * SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH + 1);
model->ok_label = malloc(sizeof(char) * SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH + 1);
strcpy(model->up_label, "N/A");
strcpy(model->down_label, "N/A");
strcpy(model->left_label, "N/A");
strcpy(model->right_label, "N/A");
strcpy(model->ok_label, "N/A");
// model->up_label = furi_string_alloc_set_str("N/A");
// model->down_label = furi_string_alloc_set_str("N/A");
// model->left_label = furi_string_alloc_set_str("N/A");
// model->right_label = furi_string_alloc_set_str("N/A");
// model->ok_label = furi_string_alloc_set_str("N/A");
for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) {
model->labels[i] = malloc(sizeof(char) * SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH + 1);
strcpy(model->labels[i], "");
}
model->pressed_btn = 0;
},
@@ -271,17 +279,9 @@ void subrem_view_remote_free(SubRemViewRemote* subghz_remote) {
subghz_remote->view,
SubRemViewRemoteModel * model,
{
free(model->up_label);
free(model->down_label);
free(model->left_label);
free(model->right_label);
free(model->ok_label);
// furi_string_free(model->up_label);
// furi_string_free(model->down_label);
// furi_string_free(model->left_label);
// furi_string_free(model->right_label);
// furi_string_free(model->ok_label);
for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) {
free(model->labels[i]);
}
},
true);
view_free(subghz_remote->view);

View File

@@ -2,11 +2,13 @@
#include <gui/view.h>
#include "../helpers/subrem_custom_event.h"
#include "../helpers/subrem_presets.h"
typedef enum {
SubRemViewRemoteStateIdle,
SubRemViewRemoteStateLoading,
SubRemViewRemoteStateSending,
SubRemViewRemoteStateOFF,
} SubRemViewRemoteState;
typedef struct SubRemViewRemote SubRemViewRemote;
@@ -24,7 +26,9 @@ void subrem_view_remote_free(SubRemViewRemote* subrem_view_remote);
View* subrem_view_remote_get_view(SubRemViewRemote* subrem_view_remote);
void subrem_view_remote_add_data_to_show(SubRemViewRemote* subrem_view_remote, const char** labels);
void subrem_view_remote_update_data_labels(
SubRemViewRemote* subrem_view_remote,
SubRemSubFilePreset** subs_presets);
void subrem_view_remote_set_state(
SubRemViewRemote* subrem_view_remote,

View File

@@ -9,11 +9,13 @@ typedef enum {
} SubRemEditMenuState;
typedef enum {
// SubmenuIndex
// StartSubmenuIndex
SubmenuIndexSubRemEditMapFile = 0,
SubmenuIndexSubRemNewMapFile,
#if FURI_DEBUG
SubmenuIndexSubRemRemoteView,
SubmenuIndexSubRemAbout,
#endif
// SubmenuIndexSubRemAbout,
// EditSubmenuIndex
EditSubmenuIndexEditLabel,
@@ -45,8 +47,4 @@ typedef enum {
SubRemCustomEventSceneEditPreviewSaved,
SubRemCustomEventSceneNewName,
// // SceneStates
// SubRemSceneOpenMapFileStateOpen,
// SubRemSceneOpenMapFileStateEdit,
} SubRemCustomEvent;

View File

@@ -147,8 +147,7 @@ SubRemLoadSubState subrem_sub_preset_load(
if(protocol->flag & SubGhzProtocolFlag_Send) {
if((protocol->type == SubGhzProtocolTypeStatic) ||
(protocol->type == SubGhzProtocolTypeDynamic) ||
// TODO: BINRAW It probably works, but checks are needed.
// (protocol->type == SubGhzProtocolTypeBinRAW) ||
(protocol->type == SubGhzProtocolTypeBinRAW) ||
(protocol->type == SubGhzProtocolTypeRAW)) {
sub_preset->type = protocol->type;
} else {

View File

@@ -23,10 +23,6 @@
#include <flipper_format/flipper_format_i.h>
#include <lib/subghz/subghz_setting.h>
#include <lib/subghz/receiver.h>
#include <lib/subghz/transmitter.h>
#define SUBREM_APP_FOLDER EXT_PATH("subghz/remote")
#define SUBREM_MAX_LEN_NAME 64

View File

@@ -12,3 +12,6 @@
// Target firmware to build for
#define TOTP_TARGET_FIRMWARE TOTP_FIRMWARE_UL_XFW
// Max custom fonts value
#define MAX_CUSTOM_FONTS (9)

View File

@@ -10,3 +10,6 @@
#include "712serif/712serif.h"
#include "graph35pix/graph35pix.h"
#include "karma_future/karma_future.h"
#include "funclimbing/funclimbing.h"
#include "dpcomic/dpcomic.h"
#include "pixelflag/pixelflag.h"

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,7 @@
#pragma once
/* GENERATED BY https://github.com/pavius/the-dot-factory */
#include "../font_info.h"
extern const FONT_INFO dPComic_18ptFontInfo;

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,7 @@
#pragma once
/* GENERATED BY https://github.com/pavius/the-dot-factory */
#include "../font_info.h"
extern const FONT_INFO funclimbingDemo_18ptFontInfo;

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,7 @@
#pragma once
/* GENERATED BY https://github.com/pavius/the-dot-factory */
#include "../font_info.h"
extern const FONT_INFO pixelFlag_18ptFontInfo;

View File

@@ -250,7 +250,7 @@ bool totp_scene_app_settings_handle_event(
#endif
else if(scene_state->selected_control == FontSelector) {
totp_roll_value_uint8_t(
&scene_state->selected_font, 1, 0, 6, RollOverflowBehaviorStop);
&scene_state->selected_font, 1, 0, MAX_CUSTOM_FONTS, RollOverflowBehaviorStop);
}
break;
case InputKeyLeft:
@@ -274,7 +274,7 @@ bool totp_scene_app_settings_handle_event(
#endif
else if(scene_state->selected_control == FontSelector) {
totp_roll_value_uint8_t(
&scene_state->selected_font, -1, 0, 6, RollOverflowBehaviorStop);
&scene_state->selected_font, -1, 0, MAX_CUSTOM_FONTS, RollOverflowBehaviorStop);
}
break;
case InputKeyOk:

View File

@@ -165,6 +165,15 @@ static void draw_totp_code(Canvas* const canvas, const PluginState* const plugin
case 6:
current_font = &karmaFuture_14ptFontInfo;
break;
case 7:
current_font = &funclimbingDemo_18ptFontInfo;
break;
case 8:
current_font = &dPComic_18ptFontInfo;
break;
case 9:
current_font = &pixelFlag_18ptFontInfo;
break;
default:
current_font = &modeNine_15ptFontInfo;
break;
@@ -222,6 +231,15 @@ static void on_new_token_code_generated(bool time_left, void* context) {
case 6:
current_font = &karmaFuture_14ptFontInfo;
break;
case 7:
current_font = &funclimbingDemo_18ptFontInfo;
break;
case 8:
current_font = &dPComic_18ptFontInfo;
break;
case 9:
current_font = &pixelFlag_18ptFontInfo;
break;
default:
current_font = &modeNine_15ptFontInfo;
break;

View File

@@ -28,7 +28,7 @@ const UART_TerminalItem items[NUM_MENU_ITEMS] = {
9,
{"115200", "2400", "9600", "19200", "38400", "57600", "230400", "460800", "921600"},
NO_ARGS,
FOCUS_CONSOLE_TOGGLE,
FOCUS_CONSOLE_END,
NO_TIP},
{"Send command", {""}, 1, {""}, INPUT_ARGS, FOCUS_CONSOLE_END, NO_TIP},
{"Send AT command", {""}, 1, {"AT"}, INPUT_ARGS, FOCUS_CONSOLE_END, NO_TIP},

View File

@@ -4,7 +4,7 @@
extern "C" {
#endif
#define WIFI_MARAUDER_APP_VERSION "v0.3.7"
#define WIFI_MARAUDER_APP_VERSION "v0.4.0"
typedef struct WifiMarauderApp WifiMarauderApp;

View File

@@ -11,7 +11,6 @@ void infrared_scene_universal_ac_on_enter(void* context) {
infrared_brute_force_set_db_filename(brute_force, EXT_PATH("infrared/assets/ac.ir"));
//TODO Improve A/C universal remote
button_panel_reserve(button_panel, 2, 3);
uint32_t i = 0;
button_panel_add_item(
@@ -20,77 +19,74 @@ void infrared_scene_universal_ac_on_enter(void* context) {
0,
0,
3,
24,
&I_Power_25x27,
&I_Power_hvr_25x27,
22,
&I_Off_25x27,
&I_Off_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "POWER");
infrared_brute_force_add_record(brute_force, i++, "Off");
button_panel_add_item(
button_panel,
i,
1,
0,
36,
24,
&I_Mode_25x27,
&I_Mode_hvr_25x27,
22,
&I_Dehumidify_25x27,
&I_Dehumidify_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "MODE");
infrared_brute_force_add_record(brute_force, i++, "Dh");
button_panel_add_item(
button_panel,
i,
0,
1,
3,
66,
&I_Vol_up_25x27,
&I_Vol_up_hvr_25x27,
59,
&I_CoolHi_25x27,
&I_CoolHi_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "TEMP+");
infrared_brute_force_add_record(brute_force, i++, "Cool_hi");
button_panel_add_item(
button_panel,
i,
1,
1,
36,
66,
&I_Vol_down_25x27,
&I_Vol_down_hvr_25x27,
59,
&I_HeatHi_25x27,
&I_HeatHi_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "TEMP-");
infrared_brute_force_add_record(brute_force, i++, "Heat_hi");
button_panel_add_item(
button_panel,
i,
0,
2,
3,
98,
&I_Swing_25x27,
&I_Swing_hvr_25x27,
91,
&I_CoolLo_25x27,
&I_CoolLo_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "SWING");
infrared_brute_force_add_record(brute_force, i++, "Cool_lo");
button_panel_add_item(
button_panel,
i,
1,
2,
36,
98,
&I_Timer_25x27,
&I_Timer_hvr_25x27,
91,
&I_HeatLo_25x27,
&I_HeatLo_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "TIMER");
infrared_brute_force_add_record(brute_force, i++, "Heat_lo");
button_panel_add_label(button_panel, 6, 11, FontPrimary, "AC remote");
button_panel_add_label(button_panel, 20, 63, FontSecondary, "Temp");
button_panel_add_label(button_panel, 8, 23, FontSecondary, "Pwr");
button_panel_add_label(button_panel, 40, 23, FontSecondary, "Mod");
button_panel_add_label(button_panel, 6, 10, FontPrimary, "AC remote");
view_set_orientation(view_stack_get_view(infrared->view_stack), ViewOrientationVertical);
view_dispatcher_switch_to_view(infrared->view_dispatcher, InfraredViewStack);

View File

@@ -10,8 +10,8 @@ void infrared_scene_universal_audio_on_enter(void* context) {
InfraredBruteForce* brute_force = infrared->brute_force;
infrared_brute_force_set_db_filename(brute_force, EXT_PATH("infrared/assets/audio.ir"));
//TODO Improve Audio universal remote
button_panel_reserve(button_panel, 2, 2);
button_panel_reserve(button_panel, 2, 4);
uint32_t i = 0;
button_panel_add_item(
button_panel,
@@ -19,51 +19,98 @@ void infrared_scene_universal_audio_on_enter(void* context) {
0,
0,
3,
19,
11,
&I_Power_25x27,
&I_Power_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "POWER");
infrared_brute_force_add_record(brute_force, i++, "Power");
button_panel_add_item(
button_panel,
i,
1,
0,
36,
19,
11,
&I_Mute_25x27,
&I_Mute_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "MUTE");
infrared_brute_force_add_record(brute_force, i++, "Mute");
button_panel_add_item(
button_panel,
i,
0,
1,
3,
64,
&I_Vol_up_25x27,
&I_Vol_up_hvr_25x27,
41,
&I_Play_25x27,
&I_Play_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "VOL+");
infrared_brute_force_add_record(brute_force, i++, "Play");
button_panel_add_item(
button_panel,
i,
1,
1,
36,
64,
41,
&I_Pause_25x27,
&I_Pause_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "Pause");
button_panel_add_item(
button_panel,
i,
0,
2,
3,
71,
&I_TrackPrev_25x27,
&I_TrackPrev_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "Prev");
button_panel_add_item(
button_panel,
i,
1,
2,
36,
71,
&I_TrackNext_25x27,
&I_TrackNext_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "Next");
button_panel_add_item(
button_panel,
i,
0,
3,
3,
101,
&I_Vol_down_25x27,
&I_Vol_down_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "VOL-");
infrared_brute_force_add_record(brute_force, i++, "Vol_dn");
button_panel_add_item(
button_panel,
i,
1,
3,
36,
101,
&I_Vol_up_25x27,
&I_Vol_up_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "Vol_up");
button_panel_add_label(button_panel, 5, 11, FontSecondary, "Audio remote");
button_panel_add_label(button_panel, 17, 60, FontSecondary, "Volume");
button_panel_add_label(button_panel, 1, 8, FontPrimary, "Mus. remote");
view_set_orientation(view_stack_get_view(infrared->view_stack), ViewOrientationVertical);
view_dispatcher_switch_to_view(infrared->view_dispatcher, InfraredViewStack);

View File

@@ -25,7 +25,7 @@ void infrared_scene_universal_fan_on_enter(void* context) {
&I_Power_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "POWER");
infrared_brute_force_add_record(brute_force, i++, "Power");
button_panel_add_item(
button_panel,
i,
@@ -37,7 +37,7 @@ void infrared_scene_universal_fan_on_enter(void* context) {
&I_Mode_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "MODE");
infrared_brute_force_add_record(brute_force, i++, "Mode");
button_panel_add_item(
button_panel,
i,
@@ -49,7 +49,7 @@ void infrared_scene_universal_fan_on_enter(void* context) {
&I_Vol_up_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "SPEED+");
infrared_brute_force_add_record(brute_force, i++, "Speed_up");
button_panel_add_item(
button_panel,
i,
@@ -61,7 +61,7 @@ void infrared_scene_universal_fan_on_enter(void* context) {
&I_Vol_down_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "SPEED-");
infrared_brute_force_add_record(brute_force, i++, "Speed_dn");
button_panel_add_item(
button_panel,
i,
@@ -73,7 +73,7 @@ void infrared_scene_universal_fan_on_enter(void* context) {
&I_Rotate_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "ROTATE");
infrared_brute_force_add_record(brute_force, i++, "Rotate");
button_panel_add_item(
button_panel,
i,
@@ -85,7 +85,7 @@ void infrared_scene_universal_fan_on_enter(void* context) {
&I_Timer_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "TIMER");
infrared_brute_force_add_record(brute_force, i++, "Timer");
button_panel_add_label(button_panel, 5, 11, FontPrimary, "Fan remote");
button_panel_add_label(button_panel, 20, 63, FontSecondary, "Speed");

View File

@@ -24,7 +24,7 @@ void infrared_scene_universal_projector_on_enter(void* context) {
&I_Power_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "POWER");
infrared_brute_force_add_record(brute_force, i++, "Power");
button_panel_add_item(
button_panel,
i,
@@ -36,7 +36,7 @@ void infrared_scene_universal_projector_on_enter(void* context) {
&I_Mute_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "MUTE");
infrared_brute_force_add_record(brute_force, i++, "Mute");
button_panel_add_item(
button_panel,
i,
@@ -48,7 +48,7 @@ void infrared_scene_universal_projector_on_enter(void* context) {
&I_Vol_up_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "VOL+");
infrared_brute_force_add_record(brute_force, i++, "Vol_up");
button_panel_add_item(
button_panel,
i,
@@ -60,7 +60,7 @@ void infrared_scene_universal_projector_on_enter(void* context) {
&I_Vol_down_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "VOL-");
infrared_brute_force_add_record(brute_force, i++, "Vol_dn");
button_panel_add_label(button_panel, 10, 11, FontPrimary, "Projector");
button_panel_add_label(button_panel, 17, 60, FontSecondary, "Volume");

View File

@@ -24,7 +24,7 @@ void infrared_scene_universal_tv_on_enter(void* context) {
&I_Power_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "POWER");
infrared_brute_force_add_record(brute_force, i++, "Power");
button_panel_add_item(
button_panel,
i,
@@ -36,7 +36,7 @@ void infrared_scene_universal_tv_on_enter(void* context) {
&I_Mute_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "MUTE");
infrared_brute_force_add_record(brute_force, i++, "Mute");
button_panel_add_item(
button_panel,
i,
@@ -48,7 +48,7 @@ void infrared_scene_universal_tv_on_enter(void* context) {
&I_Vol_up_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "VOL+");
infrared_brute_force_add_record(brute_force, i++, "Vol_up");
button_panel_add_item(
button_panel,
i,
@@ -60,7 +60,7 @@ void infrared_scene_universal_tv_on_enter(void* context) {
&I_Up_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "CH+");
infrared_brute_force_add_record(brute_force, i++, "Ch_next");
button_panel_add_item(
button_panel,
i,
@@ -72,7 +72,7 @@ void infrared_scene_universal_tv_on_enter(void* context) {
&I_Vol_down_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "VOL-");
infrared_brute_force_add_record(brute_force, i++, "Vol_dn");
button_panel_add_item(
button_panel,
i,
@@ -84,7 +84,7 @@ void infrared_scene_universal_tv_on_enter(void* context) {
&I_Down_hvr_25x27,
infrared_scene_universal_common_item_callback,
context);
infrared_brute_force_add_record(brute_force, i++, "CH-");
infrared_brute_force_add_record(brute_force, i++, "Ch_prev");
button_panel_add_label(button_panel, 6, 11, FontPrimary, "TV remote");
button_panel_add_label(button_panel, 9, 64, FontSecondary, "Vol");

View File

@@ -1,96 +0,0 @@
#include "rfid_writer.h"
#include <furi_hal.h>
void writer_start() {
furi_hal_rfid_tim_read(125000, 0.5);
furi_hal_rfid_pins_read();
furi_hal_rfid_tim_read_start();
// do not ground the antenna
furi_hal_rfid_pin_pull_release();
}
void writer_stop() {
furi_hal_rfid_tim_read_stop();
furi_hal_rfid_tim_reset();
furi_hal_rfid_pins_reset();
}
void write_gap(uint32_t gap_time) {
furi_hal_rfid_tim_read_stop();
furi_delay_us(gap_time * 8);
furi_hal_rfid_tim_read_start();
}
void write_bit(T55xxTiming* t55xxtiming, bool value) {
if(value) {
furi_delay_us(t55xxtiming->data_1 * 8);
} else {
furi_delay_us(t55xxtiming->data_0 * 8);
}
write_gap(t55xxtiming->write_gap);
}
void write_block(
T55xxTiming* t55xxtiming,
uint8_t page,
uint8_t block,
bool lock_bit,
uint32_t data,
bool password_enable,
uint32_t password) {
furi_delay_us(t55xxtiming->wait_time * 8);
//client: https://github.com/Proxmark/proxmark3/blob/6116334485ca77343eda51c557cdc81032afcf38/client/cmdlft55xx.c#L944
//hardware: https://github.com/Proxmark/proxmark3/blob/555fa197730c061bbf0ab01334e99bc47fb3dc06/armsrc/lfops.c#L1465
//hardware: https://github.com/Proxmark/proxmark3/blob/555fa197730c061bbf0ab01334e99bc47fb3dc06/armsrc/lfops.c#L1396
// start gap
write_gap(t55xxtiming->start_gap);
// opcode
switch(page) {
case 0:
write_bit(t55xxtiming, 1);
write_bit(t55xxtiming, 0);
break;
case 1:
write_bit(t55xxtiming, 1);
write_bit(t55xxtiming, 1);
break;
default:
furi_check(false);
break;
}
// password
if(password_enable) {
for(uint8_t i = 0; i < 32; i++) {
write_bit(t55xxtiming, (password >> (31 - i)) & 1);
}
}
// lock bit
write_bit(t55xxtiming, lock_bit);
// data
for(uint8_t i = 0; i < 32; i++) {
write_bit(t55xxtiming, (data >> (31 - i)) & 1);
}
// block address
write_bit(t55xxtiming, (block >> 2) & 1);
write_bit(t55xxtiming, (block >> 1) & 1);
write_bit(t55xxtiming, (block >> 0) & 1);
furi_delay_us(t55xxtiming->program * 8);
furi_delay_us(t55xxtiming->wait_time * 8);
write_reset(t55xxtiming);
}
void write_reset(T55xxTiming* t55xxtiming) {
write_gap(t55xxtiming->start_gap);
write_bit(t55xxtiming, 1);
write_bit(t55xxtiming, 0);
}

View File

@@ -1,26 +0,0 @@
#include <stdint.h>
#include <stdbool.h>
typedef struct {
uint16_t wait_time;
uint8_t start_gap;
uint8_t write_gap;
uint8_t data_0;
uint8_t data_1;
uint16_t program;
} T55xxTiming;
void writer_start();
void writer_stop();
void write_gap(uint32_t gap_time);
void write_bit(T55xxTiming* t55xxtiming, bool value);
void write_block(
T55xxTiming* t55xxtiming,
uint8_t page,
uint8_t block,
bool lock_bit,
uint32_t data,
bool password_enable,
uint32_t password);
void write_reset(T55xxTiming* t55xxtiming);

View File

@@ -1,17 +1,7 @@
#include "../lfrfid_i.h"
#include "../helpers/rfid_writer.h"
static void writer_initialize(T55xxTiming* t55xxtiming) {
t55xxtiming->wait_time = 400;
t55xxtiming->start_gap = 30;
t55xxtiming->write_gap = 18;
t55xxtiming->data_0 = 24;
t55xxtiming->data_1 = 56;
t55xxtiming->program = 700;
}
#define TAG "Clear T5577"
static void lfrfid_clear_t5577_password_and_config_to_EM(LfRfid* app) {
T55xxTiming* t55xxtiming = malloc(sizeof(T55xxTiming));
Popup* popup = app->popup;
char curr_buf[32] = {};
@@ -36,30 +26,27 @@ static void lfrfid_clear_t5577_password_and_config_to_EM(LfRfid* app) {
0x07d7bb0b, 0x9636ef8f, 0xb5f44686, 0x9E3779B9, 0xC6EF3720, 0x7854794A, 0xF1EA5EED,
0x69314718, 0x57721566, 0x93C467E3, 0x27182818, 0x50415353};
const uint8_t default_passwords_len = sizeof(default_passwords) / sizeof(uint32_t);
const uint32_t em_config_block_data =
0b00000000000101001000000001000000; //no pwd&aor config block
writer_initialize(t55xxtiming);
popup_set_header(popup, "Removing\npassword", 90, 36, AlignCenter, AlignCenter);
popup_set_icon(popup, 0, 3, &I_RFIDDolphinSend_97x61);
popup_set_text(popup, curr_buf, 90, 56, AlignCenter, AlignCenter);
notification_message(app->notifications, &sequence_blink_start_magenta);
LFRFIDT5577 data = {
.block[0] = 0b00000000000101001000000001000000,
.blocks_to_write = 1,
};
for(uint8_t i = 0; i < default_passwords_len; i++) {
FURI_CRITICAL_ENTER();
snprintf(curr_buf, sizeof(curr_buf), "Pass %d of %d", i, default_passwords_len);
view_dispatcher_switch_to_view(app->view_dispatcher, LfRfidViewPopup);
writer_start();
write_block(t55xxtiming, 0, 0, false, em_config_block_data, true, default_passwords[i]);
write_reset(t55xxtiming);
writer_stop();
FURI_CRITICAL_EXIT();
t5577_write_with_pass(&data, default_passwords[i]);
furi_delay_ms(8);
}
notification_message(app->notifications, &sequence_blink_stop);
popup_reset(app->popup);
free(t55xxtiming);
}
void lfrfid_scene_clear_t5577_on_enter(void* context) {

View File

@@ -53,7 +53,7 @@ void nfc_scene_nfc_data_info_on_enter(void* context) {
furi_string_cat_printf(
temp_str, "\e#%s\n", nfc_mf_classic_type(dev_data->mf_classic_data.type));
} else if(protocol == NfcDeviceProtocolMifareDesfire) {
furi_string_cat_printf(temp_str, "\e#MIFARE DESfire\n");
furi_string_cat_printf(temp_str, "\e#MIFARE DESFire\n");
} else if(protocol == NfcDeviceProtocolNfcV) {
switch(dev_data->nfcv_data.sub_type) {
case NfcVTypePlain:

View File

@@ -1,5 +1,6 @@
#include "subghz_txrx_i.h"
#include <lib/subghz/protocols/protocol_items.h>
#include <lib/subghz/blocks/custom_btn.h>
#define TAG "SubGhz"
@@ -557,6 +558,13 @@ bool subghz_txrx_get_debug_pin_state(SubGhzTxRx* instance) {
return instance->debug_pin_state;
}
void subghz_txrx_reset_dynamic_and_custom_btns(SubGhzTxRx* instance) {
furi_assert(instance);
subghz_environment_reset_keeloq(instance->environment);
subghz_custom_btns_reset();
}
SubGhzReceiver* subghz_txrx_get_receiver(SubGhzTxRx* instance) {
furi_assert(instance);
return instance->receiver;

View File

@@ -297,6 +297,8 @@ void subghz_txrx_set_raw_file_encoder_worker_callback_end(
void subghz_txrx_set_debug_pin_state(SubGhzTxRx* instance, bool state);
bool subghz_txrx_get_debug_pin_state(SubGhzTxRx* instance);
void subghz_txrx_reset_dynamic_and_custom_btns(SubGhzTxRx* instance);
SubGhzReceiver* subghz_txrx_get_receiver(SubGhzTxRx* instance); // TODO use only in DecodeRaw
#ifdef __cplusplus

View File

@@ -1,7 +1,5 @@
#include "../subghz_i.h"
#include "../helpers/subghz_custom_event.h"
#include <lib/subghz/protocols/keeloq.h>
#include <lib/subghz/protocols/star_line.h>
#include <lib/subghz/blocks/custom_btn.h>
@@ -108,7 +106,6 @@ void subghz_scene_receiver_info_draw_widget(SubGhz* subghz) {
void subghz_scene_receiver_info_on_enter(void* context) {
SubGhz* subghz = context;
keeloq_reset_original_btn();
subghz_custom_btns_reset();
subghz_scene_receiver_info_draw_widget(subghz);
@@ -191,10 +188,5 @@ void subghz_scene_receiver_info_on_exit(void* context) {
SubGhz* subghz = context;
widget_reset(subghz->widget);
keeloq_reset_mfname();
keeloq_reset_kl_type();
keeloq_reset_original_btn();
subghz_custom_btns_reset();
star_line_reset_mfname();
star_line_reset_kl_type();
subghz_txrx_reset_dynamic_and_custom_btns(subghz->txrx);
}

View File

@@ -1,6 +1,4 @@
#include "../subghz_i.h"
#include <lib/subghz/protocols/keeloq.h>
#include <lib/subghz/protocols/star_line.h>
#include <lib/subghz/blocks/custom_btn.h>
@@ -109,10 +107,5 @@ void subghz_scene_rpc_on_exit(void* context) {
popup_set_text(popup, NULL, 0, 0, AlignCenter, AlignTop);
popup_set_icon(popup, 0, 0, NULL);
keeloq_reset_mfname();
keeloq_reset_kl_type();
keeloq_reset_original_btn();
subghz_custom_btns_reset();
star_line_reset_mfname();
star_line_reset_kl_type();
subghz_txrx_reset_dynamic_and_custom_btns(subghz->txrx);
}

View File

@@ -2,8 +2,6 @@
#include "../views/transmitter.h"
#include <dolphin/dolphin.h>
#include <xtreme.h>
#include <lib/subghz/protocols/keeloq.h>
#include <lib/subghz/protocols/star_line.h>
#include <lib/subghz/blocks/custom_btn.h>
@@ -53,7 +51,6 @@ void fav_timer_callback(void* context) {
void subghz_scene_transmitter_on_enter(void* context) {
SubGhz* subghz = context;
keeloq_reset_original_btn();
subghz_custom_btns_reset();
if(!subghz_scene_transmitter_update_data_show(subghz)) {
@@ -136,10 +133,6 @@ bool subghz_scene_transmitter_on_event(void* context, SceneManagerEvent event) {
void subghz_scene_transmitter_on_exit(void* context) {
SubGhz* subghz = context;
subghz->state_notifications = SubGhzNotificationStateIDLE;
keeloq_reset_mfname();
keeloq_reset_kl_type();
keeloq_reset_original_btn();
subghz_custom_btns_reset();
star_line_reset_mfname();
star_line_reset_kl_type();
subghz_txrx_reset_dynamic_and_custom_btns(subghz->txrx);
}

View File

@@ -43,11 +43,32 @@ static void desktop_lock_icon_draw_callback(Canvas* canvas, void* context) {
canvas_draw_icon(canvas, 0, 0, &I_Lock_7x8);
}
static void desktop_toggle_clock_view(Desktop* desktop, bool is_enabled) {
static void desktop_clock_upd_time(Desktop* desktop, bool forced) {
furi_assert(desktop);
// clock type upd after 1 minute
FuriHalRtcDateTime curr_dt;
furi_hal_rtc_get_datetime(&curr_dt);
if(forced) {
desktop->clock_type = (locale_get_time_format() == LocaleTimeFormat24h);
}
if(forced || (desktop->minute != curr_dt.minute)) {
if(desktop->clock_type) {
desktop->hour = curr_dt.hour;
} else {
desktop->hour = (curr_dt.hour > 12) ? curr_dt.hour - 12 :
((curr_dt.hour == 0) ? 12 : curr_dt.hour);
}
desktop->minute = curr_dt.minute;
view_port_update(desktop->clock_viewport);
}
}
static void desktop_clock_toggle_view(Desktop* desktop, bool is_enabled) {
furi_assert(desktop);
desktop_clock_upd_time(desktop, true);
if(is_enabled) { // && !furi_timer_is_running(desktop->update_clock_timer)) {
furi_timer_start(desktop->update_clock_timer, furi_ms_to_ticks(1000));
@@ -135,7 +156,7 @@ static bool desktop_custom_event_callback(void* context, uint32_t event) {
// locking and unlocking
DESKTOP_SETTINGS_LOAD(&desktop->settings);
desktop_toggle_clock_view(desktop, desktop->settings.display_clock);
desktop_clock_toggle_view(desktop, desktop->settings.display_clock);
desktop_auto_lock_arm(desktop);
return true;
@@ -202,24 +223,12 @@ static void desktop_auto_lock_inhibit(Desktop* desktop) {
}
}
static void desktop_update_clock_timer_callback(void* context) {
static void desktop_clock_timer_callback(void* context) {
furi_assert(context);
Desktop* desktop = context;
if(gui_get_count_of_enabled_view_port_in_layer(desktop->gui, GuiLayerStatusBarLeft) < 6) {
FuriHalRtcDateTime curr_dt;
furi_hal_rtc_get_datetime(&curr_dt);
if(desktop->minute != curr_dt.minute) {
if(desktop->clock_type) {
desktop->hour = curr_dt.hour;
} else {
desktop->hour = (curr_dt.hour > 12) ? curr_dt.hour - 12 :
((curr_dt.hour == 0) ? 12 : curr_dt.hour);
}
desktop->minute = curr_dt.minute;
view_port_update(desktop->clock_viewport);
}
desktop_clock_upd_time(desktop, false);
view_port_enabled_set(desktop->clock_viewport, true);
} else {
@@ -403,18 +412,12 @@ Desktop* desktop_alloc() {
desktop->status_pubsub = furi_pubsub_alloc();
desktop->update_clock_timer =
furi_timer_alloc(desktop_update_clock_timer_callback, FuriTimerTypePeriodic, desktop);
furi_timer_alloc(desktop_clock_timer_callback, FuriTimerTypePeriodic, desktop);
FuriHalRtcDateTime curr_dt;
furi_hal_rtc_get_datetime(&curr_dt);
if(desktop->clock_type) {
desktop->hour = curr_dt.hour;
} else {
desktop->hour = (curr_dt.hour > 12) ? curr_dt.hour - 12 :
((curr_dt.hour == 0) ? 12 : curr_dt.hour);
}
desktop->minute = curr_dt.minute;
desktop_clock_upd_time(desktop, true);
furi_record_create(RECORD_DESKTOP, desktop);
@@ -460,7 +463,7 @@ int32_t desktop_srv(void* p) {
DESKTOP_SETTINGS_SAVE(&desktop->settings);
}
desktop_toggle_clock_view(desktop, desktop->settings.display_clock);
desktop_clock_toggle_view(desktop, desktop->settings.display_clock);
scene_manager_next_scene(desktop->scene_manager, DesktopSceneMain);

View File

@@ -265,7 +265,7 @@ static void text_input_view_draw_callback(Canvas* canvas, void* _model) {
canvas_draw_str(canvas, 2, 8, model->header);
elements_slightly_rounded_frame(canvas, 1, 12, 126, 15);
char buf[model->text_buffer_size + 1];
char buf[text_length + 1];
if(model->text_buffer) {
strlcpy(buf, model->text_buffer, sizeof(buf));
}

View File

Before

Width:  |  Height:  |  Size: 4.9 KiB

After

Width:  |  Height:  |  Size: 4.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 8.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.7 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

680
assets/resources/infrared/assets/tv.ir Normal file → Executable file

File diff suppressed because it is too large Load Diff

View File

@@ -1,7 +1,9 @@
from pathlib import Path
import posixpath
# For more details on these options, run 'fbt -h'
FIRMWARE_ORIGIN = "Xtreme"
# Default hardware target
TARGET_HW = 7
@@ -91,3 +93,8 @@ FIRMWARE_APPS = {
}
FIRMWARE_APP_SET = "default"
custom_options_fn = "fbt_options_local.py"
if Path(custom_options_fn).exists():
exec(compile(Path(custom_options_fn).read_text(), custom_options_fn, "exec"))

View File

@@ -18,6 +18,7 @@ env = ENV.Clone(
"fbt_apps",
"pvsstudio",
"fbt_hwtarget",
"fbt_envhooks",
],
COMPILATIONDB_USE_ABSPATH=False,
BUILD_DIR=fw_build_meta["build_dir"],
@@ -72,6 +73,8 @@ env = ENV.Clone(
_APP_ICONS=None,
)
env.PreConfigureFwEnvionment()
if env["IS_BASE_FIRMWARE"]:
env.Append(
FIRMWARE_BUILD_CFG="firmware",
@@ -100,6 +103,13 @@ lib_targets = env.BuildModules(
],
)
# Configure firmware origin definitions
env.Append(
CPPDEFINES=[
env.subst("FW_ORIGIN_${FIRMWARE_ORIGIN}"),
]
)
# Now, env is fully set up with everything to build apps
fwenv = env.Clone(FW_ARTIFACTS=[])
@@ -271,5 +281,6 @@ if should_gen_cdb_and_link_dir(fwenv, BUILD_TARGETS):
Alias(fwenv["FIRMWARE_BUILD_CFG"] + "_all", fw_artifacts)
env.PostConfigureFwEnvionment()
Return("fwenv")

View File

@@ -1,5 +1,5 @@
entry,status,name,type,params
Version,+,27.1,,
Version,+,28.1,,
Header,+,applications/services/bt/bt_service/bt.h,,
Header,+,applications/services/cli/cli.h,,
Header,+,applications/services/cli/cli_vcp.h,,
@@ -40,8 +40,10 @@ Header,-,firmware/targets/f18/furi_hal/furi_hal_power_calibration.h,,
Header,+,firmware/targets/f18/furi_hal/furi_hal_resources.h,,
Header,+,firmware/targets/f18/furi_hal/furi_hal_spi_config.h,,
Header,+,firmware/targets/f18/furi_hal/furi_hal_target_hw.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_bus.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_clock.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_console.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_dma.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_flash.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_gpio.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_i2c_config.h,,
@@ -873,6 +875,12 @@ Function,+,furi_hal_bt_stop_tone_tx,void,
Function,+,furi_hal_bt_unlock_core2,void,
Function,+,furi_hal_bt_update_battery_level,void,uint8_t
Function,+,furi_hal_bt_update_power_state,void,
Function,+,furi_hal_bus_deinit_early,void,
Function,+,furi_hal_bus_disable,void,FuriHalBus
Function,+,furi_hal_bus_enable,void,FuriHalBus
Function,+,furi_hal_bus_init_early,void,
Function,+,furi_hal_bus_is_enabled,_Bool,FuriHalBus
Function,+,furi_hal_bus_reset,void,FuriHalBus
Function,+,furi_hal_cdc_get_ctrl_line_state,uint8_t,uint8_t
Function,+,furi_hal_cdc_get_port_settings,usb_cdc_line_coding*,uint8_t
Function,+,furi_hal_cdc_receive,int32_t,"uint8_t, uint8_t*, uint16_t"
@@ -915,6 +923,8 @@ Function,+,furi_hal_debug_disable,void,
Function,+,furi_hal_debug_enable,void,
Function,+,furi_hal_debug_is_gdb_session_active,_Bool,
Function,-,furi_hal_deinit_early,void,
Function,+,furi_hal_dma_deinit_early,void,
Function,+,furi_hal_dma_init_early,void,
Function,-,furi_hal_flash_erase,void,uint8_t
Function,-,furi_hal_flash_get_base,size_t,
Function,-,furi_hal_flash_get_cycles_count,size_t,
@@ -1033,6 +1043,7 @@ Function,+,furi_hal_pwm_start,void,"FuriHalPwmOutputId, uint32_t, uint8_t"
Function,+,furi_hal_pwm_stop,void,FuriHalPwmOutputId
Function,+,furi_hal_random_fill_buf,void,"uint8_t*, uint32_t"
Function,+,furi_hal_random_get,uint32_t,
Function,+,furi_hal_random_init,void,
Function,+,furi_hal_region_get,const FuriHalRegion*,
Function,+,furi_hal_region_get_band,const FuriHalRegionBand*,uint32_t
Function,+,furi_hal_region_get_name,const char*,
@@ -1993,6 +2004,8 @@ Function,-,vdprintf,int,"int, const char*, __gnuc_va_list"
Function,+,version_get,const Version*,
Function,+,version_get_builddate,const char*,const Version*
Function,+,version_get_dirty_flag,_Bool,const Version*
Function,+,version_get_firmware_origin,const char*,const Version*
Function,+,version_get_git_origin,const char*,const Version*
Function,+,version_get_gitbranch,const char*,const Version*
Function,+,version_get_gitbranchnum,const char*,const Version*
Function,+,version_get_githash,const char*,const Version*
1 entry status name type params
2 Version + 27.1 28.1
3 Header + applications/services/bt/bt_service/bt.h
4 Header + applications/services/cli/cli.h
5 Header + applications/services/cli/cli_vcp.h
40 Header + firmware/targets/f18/furi_hal/furi_hal_resources.h
41 Header + firmware/targets/f18/furi_hal/furi_hal_spi_config.h
42 Header + firmware/targets/f18/furi_hal/furi_hal_target_hw.h
43 Header + firmware/targets/f7/furi_hal/furi_hal_bus.h
44 Header + firmware/targets/f7/furi_hal/furi_hal_clock.h
45 Header + firmware/targets/f7/furi_hal/furi_hal_console.h
46 Header + firmware/targets/f7/furi_hal/furi_hal_dma.h
47 Header + firmware/targets/f7/furi_hal/furi_hal_flash.h
48 Header + firmware/targets/f7/furi_hal/furi_hal_gpio.h
49 Header + firmware/targets/f7/furi_hal/furi_hal_i2c_config.h
875 Function + furi_hal_bt_unlock_core2 void
876 Function + furi_hal_bt_update_battery_level void uint8_t
877 Function + furi_hal_bt_update_power_state void
878 Function + furi_hal_bus_deinit_early void
879 Function + furi_hal_bus_disable void FuriHalBus
880 Function + furi_hal_bus_enable void FuriHalBus
881 Function + furi_hal_bus_init_early void
882 Function + furi_hal_bus_is_enabled _Bool FuriHalBus
883 Function + furi_hal_bus_reset void FuriHalBus
884 Function + furi_hal_cdc_get_ctrl_line_state uint8_t uint8_t
885 Function + furi_hal_cdc_get_port_settings usb_cdc_line_coding* uint8_t
886 Function + furi_hal_cdc_receive int32_t uint8_t, uint8_t*, uint16_t
923 Function + furi_hal_debug_enable void
924 Function + furi_hal_debug_is_gdb_session_active _Bool
925 Function - furi_hal_deinit_early void
926 Function + furi_hal_dma_deinit_early void
927 Function + furi_hal_dma_init_early void
928 Function - furi_hal_flash_erase void uint8_t
929 Function - furi_hal_flash_get_base size_t
930 Function - furi_hal_flash_get_cycles_count size_t
1043 Function + furi_hal_pwm_stop void FuriHalPwmOutputId
1044 Function + furi_hal_random_fill_buf void uint8_t*, uint32_t
1045 Function + furi_hal_random_get uint32_t
1046 Function + furi_hal_random_init void
1047 Function + furi_hal_region_get const FuriHalRegion*
1048 Function + furi_hal_region_get_band const FuriHalRegionBand* uint32_t
1049 Function + furi_hal_region_get_name const char*
2004 Function + version_get const Version*
2005 Function + version_get_builddate const char* const Version*
2006 Function + version_get_dirty_flag _Bool const Version*
2007 Function + version_get_firmware_origin const char* const Version*
2008 Function + version_get_git_origin const char* const Version*
2009 Function + version_get_gitbranch const char* const Version*
2010 Function + version_get_gitbranchnum const char* const Version*
2011 Function + version_get_githash const char* const Version*

View File

@@ -19,6 +19,8 @@ bool furi_hal_is_normal_boot() {
void furi_hal_init_early() {
furi_hal_cortex_init_early();
furi_hal_clock_init_early();
furi_hal_bus_init_early();
furi_hal_dma_init_early();
furi_hal_resources_init_early();
furi_hal_os_init();
furi_hal_spi_config_init_early();
@@ -32,12 +34,15 @@ void furi_hal_deinit_early() {
furi_hal_i2c_deinit_early();
furi_hal_spi_config_deinit_early();
furi_hal_resources_deinit_early();
furi_hal_dma_deinit_early();
furi_hal_bus_deinit_early();
furi_hal_clock_deinit_early();
}
void furi_hal_init() {
furi_hal_mpu_init();
furi_hal_clock_init();
furi_hal_random_init();
furi_hal_console_init();
furi_hal_rtc_init();
furi_hal_interrupt_init();

View File

@@ -1,4 +1,5 @@
#include <furi_hal_resources.h>
#include <furi_hal_bus.h>
#include <furi.h>
#include <stm32wbxx_ll_rcc.h>
@@ -118,6 +119,13 @@ static void furi_hal_resources_init_input_pins(GpioMode mode) {
}
void furi_hal_resources_init_early() {
furi_hal_bus_enable(FuriHalBusGPIOA);
furi_hal_bus_enable(FuriHalBusGPIOB);
furi_hal_bus_enable(FuriHalBusGPIOC);
furi_hal_bus_enable(FuriHalBusGPIOD);
furi_hal_bus_enable(FuriHalBusGPIOE);
furi_hal_bus_enable(FuriHalBusGPIOH);
furi_hal_resources_init_input_pins(GpioModeInput);
// SD Card stepdown control
@@ -162,6 +170,12 @@ void furi_hal_resources_init_early() {
void furi_hal_resources_deinit_early() {
furi_hal_resources_init_input_pins(GpioModeAnalog);
furi_hal_bus_disable(FuriHalBusGPIOA);
furi_hal_bus_disable(FuriHalBusGPIOB);
furi_hal_bus_disable(FuriHalBusGPIOC);
furi_hal_bus_disable(FuriHalBusGPIOD);
furi_hal_bus_disable(FuriHalBusGPIOE);
furi_hal_bus_disable(FuriHalBusGPIOH);
}
void furi_hal_resources_init() {

View File

@@ -1,5 +1,6 @@
#include <furi_hal_spi_config.h>
#include <furi_hal_resources.h>
#include <furi_hal_bus.h>
#include <furi_hal_spi.h>
#include <furi.h>
@@ -96,28 +97,17 @@ void furi_hal_spi_config_init() {
static void furi_hal_spi_bus_r_event_callback(FuriHalSpiBus* bus, FuriHalSpiBusEvent event) {
if(event == FuriHalSpiBusEventInit) {
furi_hal_spi_bus_r_mutex = furi_mutex_alloc(FuriMutexTypeNormal);
FURI_CRITICAL_ENTER();
LL_APB2_GRP1_ForceReset(LL_APB2_GRP1_PERIPH_SPI1);
FURI_CRITICAL_EXIT();
bus->current_handle = NULL;
} else if(event == FuriHalSpiBusEventDeinit) {
furi_mutex_free(furi_hal_spi_bus_r_mutex);
FURI_CRITICAL_ENTER();
LL_APB2_GRP1_ForceReset(LL_APB2_GRP1_PERIPH_SPI1);
LL_APB2_GRP1_ReleaseReset(LL_APB2_GRP1_PERIPH_SPI1);
FURI_CRITICAL_EXIT();
} else if(event == FuriHalSpiBusEventLock) {
furi_check(furi_mutex_acquire(furi_hal_spi_bus_r_mutex, FuriWaitForever) == FuriStatusOk);
} else if(event == FuriHalSpiBusEventUnlock) {
furi_check(furi_mutex_release(furi_hal_spi_bus_r_mutex) == FuriStatusOk);
} else if(event == FuriHalSpiBusEventActivate) {
FURI_CRITICAL_ENTER();
LL_APB2_GRP1_ReleaseReset(LL_APB2_GRP1_PERIPH_SPI1);
FURI_CRITICAL_EXIT();
furi_hal_bus_enable(FuriHalBusSPI1);
} else if(event == FuriHalSpiBusEventDeactivate) {
FURI_CRITICAL_ENTER();
LL_APB2_GRP1_ForceReset(LL_APB2_GRP1_PERIPH_SPI1);
FURI_CRITICAL_EXIT();
furi_hal_bus_disable(FuriHalBusSPI1);
}
}
@@ -131,28 +121,17 @@ FuriMutex* furi_hal_spi_bus_d_mutex = NULL;
static void furi_hal_spi_bus_d_event_callback(FuriHalSpiBus* bus, FuriHalSpiBusEvent event) {
if(event == FuriHalSpiBusEventInit) {
furi_hal_spi_bus_d_mutex = furi_mutex_alloc(FuriMutexTypeNormal);
FURI_CRITICAL_ENTER();
LL_APB1_GRP1_ForceReset(LL_APB1_GRP1_PERIPH_SPI2);
FURI_CRITICAL_EXIT();
bus->current_handle = NULL;
} else if(event == FuriHalSpiBusEventDeinit) {
furi_mutex_free(furi_hal_spi_bus_d_mutex);
FURI_CRITICAL_ENTER();
LL_APB1_GRP1_ForceReset(LL_APB1_GRP1_PERIPH_SPI2);
LL_APB1_GRP1_ReleaseReset(LL_APB1_GRP1_PERIPH_SPI2);
FURI_CRITICAL_EXIT();
} else if(event == FuriHalSpiBusEventLock) {
furi_check(furi_mutex_acquire(furi_hal_spi_bus_d_mutex, FuriWaitForever) == FuriStatusOk);
} else if(event == FuriHalSpiBusEventUnlock) {
furi_check(furi_mutex_release(furi_hal_spi_bus_d_mutex) == FuriStatusOk);
} else if(event == FuriHalSpiBusEventActivate) {
FURI_CRITICAL_ENTER();
LL_APB1_GRP1_ReleaseReset(LL_APB1_GRP1_PERIPH_SPI2);
FURI_CRITICAL_EXIT();
furi_hal_bus_enable(FuriHalBusSPI2);
} else if(event == FuriHalSpiBusEventDeactivate) {
FURI_CRITICAL_ENTER();
LL_APB1_GRP1_ForceReset(LL_APB1_GRP1_PERIPH_SPI2);
FURI_CRITICAL_EXIT();
furi_hal_bus_disable(FuriHalBusSPI2);
}
}

View File

@@ -1,5 +1,5 @@
entry,status,name,type,params
Version,+,27.1,,
Version,+,28.1,,
Header,+,applications/main/archive/helpers/favorite_timeout.h,,
Header,+,applications/main/fap_loader/fap_loader_app.h,,
Header,+,applications/main/subghz/helpers/subghz_txrx.h,,
@@ -40,8 +40,10 @@ Header,+,applications/services/notification/notification_messages.h,,
Header,+,applications/services/power/power_service/power.h,,
Header,+,applications/services/rpc/rpc_app.h,,
Header,+,applications/services/storage/storage.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_bus.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_clock.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_console.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_dma.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_flash.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_gpio.h,,
Header,+,firmware/targets/f7/furi_hal/furi_hal_i2c_config.h,,
@@ -1137,6 +1139,12 @@ Function,+,furi_hal_bt_stop_tone_tx,void,
Function,+,furi_hal_bt_unlock_core2,void,
Function,+,furi_hal_bt_update_battery_level,void,uint8_t
Function,+,furi_hal_bt_update_power_state,void,
Function,+,furi_hal_bus_deinit_early,void,
Function,+,furi_hal_bus_disable,void,FuriHalBus
Function,+,furi_hal_bus_enable,void,FuriHalBus
Function,+,furi_hal_bus_init_early,void,
Function,+,furi_hal_bus_is_enabled,_Bool,FuriHalBus
Function,+,furi_hal_bus_reset,void,FuriHalBus
Function,+,furi_hal_cdc_get_ctrl_line_state,uint8_t,uint8_t
Function,+,furi_hal_cdc_get_port_settings,usb_cdc_line_coding*,uint8_t
Function,+,furi_hal_cdc_receive,int32_t,"uint8_t, uint8_t*, uint16_t"
@@ -1179,6 +1187,8 @@ Function,+,furi_hal_debug_disable,void,
Function,+,furi_hal_debug_enable,void,
Function,+,furi_hal_debug_is_gdb_session_active,_Bool,
Function,-,furi_hal_deinit_early,void,
Function,+,furi_hal_dma_deinit_early,void,
Function,+,furi_hal_dma_init_early,void,
Function,-,furi_hal_flash_erase,void,uint8_t
Function,-,furi_hal_flash_get_base,size_t,
Function,-,furi_hal_flash_get_cycles_count,size_t,
@@ -1348,6 +1358,7 @@ Function,+,furi_hal_pwm_start,void,"FuriHalPwmOutputId, uint32_t, uint8_t"
Function,+,furi_hal_pwm_stop,void,FuriHalPwmOutputId
Function,+,furi_hal_random_fill_buf,void,"uint8_t*, uint32_t"
Function,+,furi_hal_random_get,uint32_t,
Function,+,furi_hal_random_init,void,
Function,+,furi_hal_region_get,const FuriHalRegion*,
Function,+,furi_hal_region_get_band,const FuriHalRegionBand*,uint32_t
Function,+,furi_hal_region_get_name,const char*,
@@ -1358,31 +1369,23 @@ Function,-,furi_hal_resources_deinit_early,void,
Function,+,furi_hal_resources_get_ext_pin_number,int32_t,const GpioPin*
Function,-,furi_hal_resources_init,void,
Function,-,furi_hal_resources_init_early,void,
Function,+,furi_hal_rfid_change_read_config,void,"float, float"
Function,+,furi_hal_rfid_comp_set_callback,void,"FuriHalRfidCompCallback, void*"
Function,+,furi_hal_rfid_comp_start,void,
Function,+,furi_hal_rfid_comp_stop,void,
Function,-,furi_hal_rfid_init,void,
Function,+,furi_hal_rfid_pin_pull_pulldown,void,
Function,+,furi_hal_rfid_pin_pull_release,void,
Function,+,furi_hal_rfid_pins_emulate,void,
Function,+,furi_hal_rfid_pins_read,void,
Function,+,furi_hal_rfid_pins_reset,void,
Function,+,furi_hal_rfid_set_emulate_period,void,uint32_t
Function,+,furi_hal_rfid_set_emulate_pulse,void,uint32_t
Function,+,furi_hal_rfid_set_read_period,void,uint32_t
Function,+,furi_hal_rfid_set_read_pulse,void,uint32_t
Function,+,furi_hal_rfid_tim_emulate,void,float
Function,+,furi_hal_rfid_tim_emulate_dma_start,void,"uint32_t*, uint32_t*, size_t, FuriHalRfidDMACallback, void*"
Function,+,furi_hal_rfid_tim_emulate_dma_stop,void,
Function,+,furi_hal_rfid_tim_emulate_start,void,"FuriHalRfidEmulateCallback, void*"
Function,+,furi_hal_rfid_tim_emulate_stop,void,
Function,+,furi_hal_rfid_tim_read,void,"float, float"
Function,+,furi_hal_rfid_tim_read_capture_start,void,"FuriHalRfidReadCaptureCallback, void*"
Function,+,furi_hal_rfid_tim_read_capture_stop,void,
Function,+,furi_hal_rfid_tim_read_start,void,
Function,+,furi_hal_rfid_tim_read_continue,void,
Function,+,furi_hal_rfid_tim_read_pause,void,
Function,+,furi_hal_rfid_tim_read_start,void,"float, float"
Function,+,furi_hal_rfid_tim_read_stop,void,
Function,+,furi_hal_rfid_tim_reset,void,
Function,+,furi_hal_rtc_datetime_to_timestamp,uint32_t,FuriHalRtcDateTime*
Function,-,furi_hal_rtc_deinit_early,void,
Function,+,furi_hal_rtc_get_boot_mode,FuriHalRtcBootMode,
@@ -1864,9 +1867,6 @@ Function,-,j1f,float,float
Function,-,jn,double,"int, double"
Function,-,jnf,float,"int, float"
Function,-,jrand48,long,unsigned short[3]
Function,+,keeloq_reset_kl_type,void,
Function,+,keeloq_reset_mfname,void,
Function,+,keeloq_reset_original_btn,void,
Function,-,l64a,char*,long
Function,-,labs,long,long
Function,-,lcong48,void,unsigned short[7]
@@ -2619,8 +2619,6 @@ Function,+,srand,void,unsigned
Function,-,srand48,void,long
Function,-,srandom,void,unsigned
Function,+,sscanf,int,"const char*, const char*, ..."
Function,+,star_line_reset_kl_type,void,
Function,+,star_line_reset_mfname,void,
Function,+,storage_common_copy,FS_Error,"Storage*, const char*, const char*"
Function,+,storage_common_exists,_Bool,"Storage*, const char*"
Function,+,storage_common_fs_info,FS_Error,"Storage*, const char*, uint64_t*, uint64_t*"
@@ -2768,13 +2766,6 @@ Function,+,subghz_block_generic_deserialize,SubGhzProtocolStatus,"SubGhzBlockGen
Function,+,subghz_block_generic_deserialize_check_count_bit,SubGhzProtocolStatus,"SubGhzBlockGeneric*, FlipperFormat*, uint16_t"
Function,+,subghz_block_generic_get_preset_name,void,"const char*, FuriString*"
Function,+,subghz_block_generic_serialize,SubGhzProtocolStatus,"SubGhzBlockGeneric*, FlipperFormat*, SubGhzRadioPreset*"
Function,-,subghz_custom_btn_get,uint8_t,
Function,-,subghz_custom_btn_get_original,uint8_t,
Function,-,subghz_custom_btn_is_allowed,_Bool,
Function,+,subghz_custom_btn_set,_Bool,uint8_t
Function,-,subghz_custom_btn_set_max,void,uint8_t
Function,-,subghz_custom_btn_set_original,void,uint8_t
Function,+,subghz_custom_btns_reset,void,
Function,+,subghz_environment_alloc,SubGhzEnvironment*,
Function,+,subghz_environment_free,void,SubGhzEnvironment*
Function,+,subghz_environment_get_alutech_at_4n_rainbow_table_file_name,const char*,SubGhzEnvironment*
@@ -2784,6 +2775,7 @@ Function,+,subghz_environment_get_nice_flor_s_rainbow_table_file_name,const char
Function,+,subghz_environment_get_protocol_name_registry,const char*,"SubGhzEnvironment*, size_t"
Function,+,subghz_environment_get_protocol_registry,void*,SubGhzEnvironment*
Function,+,subghz_environment_load_keystore,_Bool,"SubGhzEnvironment*, const char*"
Function,+,subghz_environment_reset_keeloq,void,SubGhzEnvironment*
Function,+,subghz_environment_set_alutech_at_4n_rainbow_table_file_name,void,"SubGhzEnvironment*, const char*"
Function,+,subghz_environment_set_came_atomo_rainbow_table_file_name,void,"SubGhzEnvironment*, const char*"
Function,+,subghz_environment_set_nice_flor_s_rainbow_table_file_name,void,"SubGhzEnvironment*, const char*"
@@ -2794,6 +2786,7 @@ Function,-,subghz_keystore_get_data,SubGhzKeyArray_t*,SubGhzKeystore*
Function,-,subghz_keystore_load,_Bool,"SubGhzKeystore*, const char*"
Function,-,subghz_keystore_raw_encrypted_save,_Bool,"const char*, const char*, uint8_t*"
Function,-,subghz_keystore_raw_get_data,_Bool,"const char*, size_t, uint8_t*, size_t"
Function,-,subghz_keystore_reset_kl,void,SubGhzKeystore*
Function,-,subghz_keystore_save,_Bool,"SubGhzKeystore*, const char*, uint8_t*"
Function,-,subghz_protocol_alutech_at_4n_create_data,_Bool,"void*, FlipperFormat*, uint32_t, uint8_t, uint16_t, SubGhzRadioPreset*"
Function,+,subghz_protocol_blocks_add_bit,void,"SubGhzBlockDecoder*, uint8_t"
@@ -3467,6 +3460,7 @@ Function,+,submenu_set_header,void,"Submenu*, const char*"
Function,+,submenu_set_selected_item,void,"Submenu*, uint32_t"
Function,-,system,int,const char*
Function,+,t5577_write,void,LFRFIDT5577*
Function,-,t5577_write_with_pass,void,"LFRFIDT5577*, uint32_t"
Function,-,tan,double,double
Function,-,tanf,float,float
Function,-,tanh,double,double
@@ -3640,6 +3634,8 @@ Function,+,version_get,const Version*,
Function,+,version_get_builddate,const char*,const Version*
Function,+,version_get_custom_name,const char*,const Version*
Function,+,version_get_dirty_flag,_Bool,const Version*
Function,+,version_get_firmware_origin,const char*,const Version*
Function,+,version_get_git_origin,const char*,const Version*
Function,+,version_get_gitbranch,const char*,const Version*
Function,+,version_get_gitbranchnum,const char*,const Version*
Function,+,version_get_githash,const char*,const Version*
1 entry status name type params
2 Version + 27.1 28.1
3 Header + applications/main/archive/helpers/favorite_timeout.h
4 Header + applications/main/fap_loader/fap_loader_app.h
5 Header + applications/main/subghz/helpers/subghz_txrx.h
40 Header + applications/services/power/power_service/power.h
41 Header + applications/services/rpc/rpc_app.h
42 Header + applications/services/storage/storage.h
43 Header + firmware/targets/f7/furi_hal/furi_hal_bus.h
44 Header + firmware/targets/f7/furi_hal/furi_hal_clock.h
45 Header + firmware/targets/f7/furi_hal/furi_hal_console.h
46 Header + firmware/targets/f7/furi_hal/furi_hal_dma.h
47 Header + firmware/targets/f7/furi_hal/furi_hal_flash.h
48 Header + firmware/targets/f7/furi_hal/furi_hal_gpio.h
49 Header + firmware/targets/f7/furi_hal/furi_hal_i2c_config.h
1139 Function + furi_hal_bt_unlock_core2 void
1140 Function + furi_hal_bt_update_battery_level void uint8_t
1141 Function + furi_hal_bt_update_power_state void
1142 Function + furi_hal_bus_deinit_early void
1143 Function + furi_hal_bus_disable void FuriHalBus
1144 Function + furi_hal_bus_enable void FuriHalBus
1145 Function + furi_hal_bus_init_early void
1146 Function + furi_hal_bus_is_enabled _Bool FuriHalBus
1147 Function + furi_hal_bus_reset void FuriHalBus
1148 Function + furi_hal_cdc_get_ctrl_line_state uint8_t uint8_t
1149 Function + furi_hal_cdc_get_port_settings usb_cdc_line_coding* uint8_t
1150 Function + furi_hal_cdc_receive int32_t uint8_t, uint8_t*, uint16_t
1187 Function + furi_hal_debug_enable void
1188 Function + furi_hal_debug_is_gdb_session_active _Bool
1189 Function - furi_hal_deinit_early void
1190 Function + furi_hal_dma_deinit_early void
1191 Function + furi_hal_dma_init_early void
1192 Function - furi_hal_flash_erase void uint8_t
1193 Function - furi_hal_flash_get_base size_t
1194 Function - furi_hal_flash_get_cycles_count size_t
1358 Function + furi_hal_pwm_stop void FuriHalPwmOutputId
1359 Function + furi_hal_random_fill_buf void uint8_t*, uint32_t
1360 Function + furi_hal_random_get uint32_t
1361 Function + furi_hal_random_init void
1362 Function + furi_hal_region_get const FuriHalRegion*
1363 Function + furi_hal_region_get_band const FuriHalRegionBand* uint32_t
1364 Function + furi_hal_region_get_name const char*
1369 Function + furi_hal_resources_get_ext_pin_number int32_t const GpioPin*
1370 Function - furi_hal_resources_init void
1371 Function - furi_hal_resources_init_early void
Function + furi_hal_rfid_change_read_config void float, float
1372 Function + furi_hal_rfid_comp_set_callback void FuriHalRfidCompCallback, void*
1373 Function + furi_hal_rfid_comp_start void
1374 Function + furi_hal_rfid_comp_stop void
1375 Function - furi_hal_rfid_init void
1376 Function + furi_hal_rfid_pin_pull_pulldown void
1377 Function + furi_hal_rfid_pin_pull_release void
Function + furi_hal_rfid_pins_emulate void
Function + furi_hal_rfid_pins_read void
1378 Function + furi_hal_rfid_pins_reset void
Function + furi_hal_rfid_set_emulate_period void uint32_t
Function + furi_hal_rfid_set_emulate_pulse void uint32_t
1379 Function + furi_hal_rfid_set_read_period void uint32_t
1380 Function + furi_hal_rfid_set_read_pulse void uint32_t
Function + furi_hal_rfid_tim_emulate void float
1381 Function + furi_hal_rfid_tim_emulate_dma_start void uint32_t*, uint32_t*, size_t, FuriHalRfidDMACallback, void*
1382 Function + furi_hal_rfid_tim_emulate_dma_stop void
Function + furi_hal_rfid_tim_emulate_start void FuriHalRfidEmulateCallback, void*
Function + furi_hal_rfid_tim_emulate_stop void
Function + furi_hal_rfid_tim_read void float, float
1383 Function + furi_hal_rfid_tim_read_capture_start void FuriHalRfidReadCaptureCallback, void*
1384 Function + furi_hal_rfid_tim_read_capture_stop void
1385 Function + furi_hal_rfid_tim_read_start furi_hal_rfid_tim_read_continue void
1386 Function + furi_hal_rfid_tim_read_pause void
1387 Function + furi_hal_rfid_tim_read_start void float, float
1388 Function + furi_hal_rfid_tim_read_stop void
Function + furi_hal_rfid_tim_reset void
1389 Function + furi_hal_rtc_datetime_to_timestamp uint32_t FuriHalRtcDateTime*
1390 Function - furi_hal_rtc_deinit_early void
1391 Function + furi_hal_rtc_get_boot_mode FuriHalRtcBootMode
1867 Function - jn double int, double
1868 Function - jnf float int, float
1869 Function - jrand48 long unsigned short[3]
Function + keeloq_reset_kl_type void
Function + keeloq_reset_mfname void
Function + keeloq_reset_original_btn void
1870 Function - l64a char* long
1871 Function - labs long long
1872 Function - lcong48 void unsigned short[7]
2619 Function - srand48 void long
2620 Function - srandom void unsigned
2621 Function + sscanf int const char*, const char*, ...
Function + star_line_reset_kl_type void
Function + star_line_reset_mfname void
2622 Function + storage_common_copy FS_Error Storage*, const char*, const char*
2623 Function + storage_common_exists _Bool Storage*, const char*
2624 Function + storage_common_fs_info FS_Error Storage*, const char*, uint64_t*, uint64_t*
2766 Function + subghz_block_generic_deserialize_check_count_bit SubGhzProtocolStatus SubGhzBlockGeneric*, FlipperFormat*, uint16_t
2767 Function + subghz_block_generic_get_preset_name void const char*, FuriString*
2768 Function + subghz_block_generic_serialize SubGhzProtocolStatus SubGhzBlockGeneric*, FlipperFormat*, SubGhzRadioPreset*
Function - subghz_custom_btn_get uint8_t
Function - subghz_custom_btn_get_original uint8_t
Function - subghz_custom_btn_is_allowed _Bool
Function + subghz_custom_btn_set _Bool uint8_t
Function - subghz_custom_btn_set_max void uint8_t
Function - subghz_custom_btn_set_original void uint8_t
Function + subghz_custom_btns_reset void
2769 Function + subghz_environment_alloc SubGhzEnvironment*
2770 Function + subghz_environment_free void SubGhzEnvironment*
2771 Function + subghz_environment_get_alutech_at_4n_rainbow_table_file_name const char* SubGhzEnvironment*
2775 Function + subghz_environment_get_protocol_name_registry const char* SubGhzEnvironment*, size_t
2776 Function + subghz_environment_get_protocol_registry void* SubGhzEnvironment*
2777 Function + subghz_environment_load_keystore _Bool SubGhzEnvironment*, const char*
2778 Function + subghz_environment_reset_keeloq void SubGhzEnvironment*
2779 Function + subghz_environment_set_alutech_at_4n_rainbow_table_file_name void SubGhzEnvironment*, const char*
2780 Function + subghz_environment_set_came_atomo_rainbow_table_file_name void SubGhzEnvironment*, const char*
2781 Function + subghz_environment_set_nice_flor_s_rainbow_table_file_name void SubGhzEnvironment*, const char*
2786 Function - subghz_keystore_load _Bool SubGhzKeystore*, const char*
2787 Function - subghz_keystore_raw_encrypted_save _Bool const char*, const char*, uint8_t*
2788 Function - subghz_keystore_raw_get_data _Bool const char*, size_t, uint8_t*, size_t
2789 Function - subghz_keystore_reset_kl void SubGhzKeystore*
2790 Function - subghz_keystore_save _Bool SubGhzKeystore*, const char*, uint8_t*
2791 Function - subghz_protocol_alutech_at_4n_create_data _Bool void*, FlipperFormat*, uint32_t, uint8_t, uint16_t, SubGhzRadioPreset*
2792 Function + subghz_protocol_blocks_add_bit void SubGhzBlockDecoder*, uint8_t
3460 Function + submenu_set_selected_item void Submenu*, uint32_t
3461 Function - system int const char*
3462 Function + t5577_write void LFRFIDT5577*
3463 Function - t5577_write_with_pass void LFRFIDT5577*, uint32_t
3464 Function - tan double double
3465 Function - tanf float float
3466 Function - tanh double double
3634 Function + version_get_builddate const char* const Version*
3635 Function + version_get_custom_name const char* const Version*
3636 Function + version_get_dirty_flag _Bool const Version*
3637 Function + version_get_firmware_origin const char* const Version*
3638 Function + version_get_git_origin const char* const Version*
3639 Function + version_get_gitbranch const char* const Version*
3640 Function + version_get_gitbranchnum const char* const Version*
3641 Function + version_get_githash const char* const Version*

View File

@@ -19,6 +19,8 @@ bool furi_hal_is_normal_boot() {
void furi_hal_init_early() {
furi_hal_cortex_init_early();
furi_hal_clock_init_early();
furi_hal_bus_init_early();
furi_hal_dma_init_early();
furi_hal_resources_init_early();
furi_hal_os_init();
furi_hal_spi_config_init_early();
@@ -32,12 +34,15 @@ void furi_hal_deinit_early() {
furi_hal_i2c_deinit_early();
furi_hal_spi_config_deinit_early();
furi_hal_resources_deinit_early();
furi_hal_dma_deinit_early();
furi_hal_bus_deinit_early();
furi_hal_clock_deinit_early();
}
void furi_hal_init() {
furi_hal_mpu_init();
furi_hal_clock_init();
furi_hal_random_init();
furi_hal_console_init();
furi_hal_rtc_init();
furi_hal_interrupt_init();

View File

@@ -7,6 +7,7 @@
#include <furi_hal_version.h>
#include <furi_hal_bt_hid.h>
#include <furi_hal_bt_serial.h>
#include <furi_hal_bus.c>
#include "battery_service.h"
#include <furi.h>
@@ -80,6 +81,11 @@ FuriHalBtProfileConfig profile_config[FuriHalBtProfileNumber] = {
FuriHalBtProfileConfig* current_profile = NULL;
void furi_hal_bt_init() {
furi_hal_bus_enable(FuriHalBusHSEM);
furi_hal_bus_enable(FuriHalBusIPCC);
furi_hal_bus_enable(FuriHalBusAES2);
furi_hal_bus_enable(FuriHalBusPKA);
if(!furi_hal_bt_core2_mtx) {
furi_hal_bt_core2_mtx = furi_mutex_alloc(FuriMutexTypeNormal);
furi_assert(furi_hal_bt_core2_mtx);
@@ -269,6 +275,11 @@ void furi_hal_bt_reinit() {
furi_delay_ms(100);
ble_glue_thread_stop();
furi_hal_bus_disable(FuriHalBusHSEM);
furi_hal_bus_disable(FuriHalBusIPCC);
furi_hal_bus_disable(FuriHalBusAES2);
furi_hal_bus_disable(FuriHalBusPKA);
FURI_LOG_I(TAG, "Start BT initialization");
furi_hal_bt_init();

View File

@@ -0,0 +1,302 @@
#include <furi_hal_bus.h>
#include <furi.h>
#include <stm32wbxx_ll_bus.h>
/* Bus bitmask definitions */
#define FURI_HAL_BUS_IGNORE (0x0U)
#define FURI_HAL_BUS_AHB1_GRP1 \
(LL_AHB1_GRP1_PERIPH_DMA1 | LL_AHB1_GRP1_PERIPH_DMA2 | LL_AHB1_GRP1_PERIPH_DMAMUX1 | \
LL_AHB1_GRP1_PERIPH_CRC | LL_AHB1_GRP1_PERIPH_TSC)
#if defined(ADC_SUPPORT_5_MSPS)
#define FURI_HAL_BUS_AHB2_GRP1 \
(LL_AHB2_GRP1_PERIPH_GPIOA | LL_AHB2_GRP1_PERIPH_GPIOB | LL_AHB2_GRP1_PERIPH_GPIOC | \
LL_AHB2_GRP1_PERIPH_GPIOD | LL_AHB2_GRP1_PERIPH_GPIOE | LL_AHB2_GRP1_PERIPH_GPIOH | \
LL_AHB2_GRP1_PERIPH_ADC | LL_AHB2_GRP1_PERIPH_AES1)
#define FURI_HAL_BUS_APB2_GRP1 \
(LL_APB2_GRP1_PERIPH_TIM1 | LL_APB2_GRP1_PERIPH_SPI1 | LL_APB2_GRP1_PERIPH_USART1 | \
LL_APB2_GRP1_PERIPH_TIM16 | LL_APB2_GRP1_PERIPH_TIM17 | LL_APB2_GRP1_PERIPH_SAI1)
#else
#define FURI_HAL_BUS_AHB2_GRP1 \
(LL_AHB2_GRP1_PERIPH_GPIOA | LL_AHB2_GRP1_PERIPH_GPIOB | LL_AHB2_GRP1_PERIPH_GPIOC | \
LL_AHB2_GRP1_PERIPH_GPIOD | LL_AHB2_GRP1_PERIPH_GPIOE | LL_AHB2_GRP1_PERIPH_GPIOH | \
LL_AHB2_GRP1_PERIPH_AES1)
#define FURI_HAL_BUS_APB2_GRP1 \
(LL_APB2_GRP1_PERIPH_ADC | LL_APB2_GRP1_PERIPH_TIM1 | LL_APB2_GRP1_PERIPH_SPI1 | \
LL_APB2_GRP1_PERIPH_USART1 | LL_APB2_GRP1_PERIPH_TIM16 | LL_APB2_GRP1_PERIPH_TIM17 | \
LL_APB2_GRP1_PERIPH_SAI1)
#endif
#define FURI_HAL_BUS_AHB3_GRP1 \
(LL_AHB3_GRP1_PERIPH_QUADSPI | LL_AHB3_GRP1_PERIPH_PKA | LL_AHB3_GRP1_PERIPH_AES2 | \
LL_AHB3_GRP1_PERIPH_RNG | LL_AHB3_GRP1_PERIPH_HSEM | LL_AHB3_GRP1_PERIPH_IPCC)
// LL_AHB3_GRP1_PERIPH_FLASH enabled by default
#define FURI_HAL_BUS_APB1_GRP1 \
(LL_APB1_GRP1_PERIPH_TIM2 | LL_APB1_GRP1_PERIPH_LCD | LL_APB1_GRP1_PERIPH_RTCAPB | \
LL_APB1_GRP1_PERIPH_SPI2 | LL_APB1_GRP1_PERIPH_I2C1 | LL_APB1_GRP1_PERIPH_I2C3 | \
LL_APB1_GRP1_PERIPH_CRS | LL_APB1_GRP1_PERIPH_USB | LL_APB1_GRP1_PERIPH_LPTIM1)
#define FURI_HAL_BUS_APB1_GRP2 (LL_APB1_GRP2_PERIPH_LPUART1 | LL_APB1_GRP2_PERIPH_LPTIM2)
#define FURI_HAL_BUS_APB3_GRP1 (LL_APB3_GRP1_PERIPH_RF)
/* Test macro definitions */
#define FURI_HAL_BUS_IS_ALL_CLEAR(reg, value) (READ_BIT((reg), (value)) == 0UL)
#define FURI_HAL_BUS_IS_ALL_SET(reg, value) (READ_BIT((reg), (value)) == (value))
#define FURI_HAL_BUS_IS_CLOCK_ENABLED(bus, value, ...) \
(FURI_HAL_BUS_IS_ALL_SET(RCC->bus##ENR##__VA_ARGS__, (value)))
#define FURI_HAL_BUS_IS_CLOCK_DISABLED(bus, value, ...) \
(FURI_HAL_BUS_IS_ALL_CLEAR(RCC->bus##ENR##__VA_ARGS__, (value)))
#define FURI_HAL_BUS_IS_RESET_ASSERTED(bus, value, ...) \
(FURI_HAL_BUS_IS_ALL_SET(RCC->bus##RSTR##__VA_ARGS__, (value)))
#define FURI_HAL_BUS_IS_RESET_DEASSERTED(bus, value, ...) \
(FURI_HAL_BUS_IS_ALL_CLEAR(RCC->bus##RSTR##__VA_ARGS__, (value)))
#define FURI_HAL_BUS_IS_PERIPH_ENABLED(bus, value, ...) \
(FURI_HAL_BUS_IS_RESET_DEASSERTED(bus, (value), __VA_ARGS__) && \
FURI_HAL_BUS_IS_CLOCK_ENABLED(bus, (value), __VA_ARGS__))
#define FURI_HAL_BUS_IS_PERIPH_DISABLED(bus, value, ...) \
(FURI_HAL_BUS_IS_CLOCK_DISABLED(bus, (value), __VA_ARGS__) && \
FURI_HAL_BUS_IS_RESET_ASSERTED(bus, (value), __VA_ARGS__))
/* Control macro definitions */
#define FURI_HAL_BUS_RESET_ASSERT(bus, value, grp) LL_##bus##_GRP##grp##_ForceReset(value)
#define FURI_HAL_BUS_RESET_DEASSERT(bus, value, grp) LL_##bus##_GRP##grp##_ReleaseReset(value)
#define FURI_HAL_BUS_CLOCK_ENABLE(bus, value, grp) LL_##bus##_GRP##grp##_EnableClock(value)
#define FURI_HAL_BUS_CLOCK_DISABLE(bus, value, grp) LL_##bus##_GRP##grp##_DisableClock(value)
#define FURI_HAL_BUS_PERIPH_ENABLE(bus, value, grp) \
FURI_HAL_BUS_CLOCK_ENABLE(bus, value, grp); \
FURI_HAL_BUS_RESET_DEASSERT(bus, value, grp)
#define FURI_HAL_BUS_PERIPH_DISABLE(bus, value, grp) \
FURI_HAL_BUS_RESET_ASSERT(bus, value, grp); \
FURI_HAL_BUS_CLOCK_DISABLE(bus, value, grp)
#define FURI_HAL_BUS_PERIPH_RESET(bus, value, grp) \
FURI_HAL_BUS_RESET_ASSERT(bus, value, grp); \
FURI_HAL_BUS_RESET_DEASSERT(bus, value, grp)
static const uint32_t furi_hal_bus[] = {
[FuriHalBusAHB1_GRP1] = FURI_HAL_BUS_AHB1_GRP1,
[FuriHalBusDMA1] = LL_AHB1_GRP1_PERIPH_DMA1,
[FuriHalBusDMA2] = LL_AHB1_GRP1_PERIPH_DMA2,
[FuriHalBusDMAMUX1] = LL_AHB1_GRP1_PERIPH_DMAMUX1,
[FuriHalBusCRC] = LL_AHB1_GRP1_PERIPH_CRC,
[FuriHalBusTSC] = LL_AHB1_GRP1_PERIPH_TSC,
[FuriHalBusAHB2_GRP1] = FURI_HAL_BUS_AHB2_GRP1,
[FuriHalBusGPIOA] = LL_AHB2_GRP1_PERIPH_GPIOA,
[FuriHalBusGPIOB] = LL_AHB2_GRP1_PERIPH_GPIOB,
[FuriHalBusGPIOC] = LL_AHB2_GRP1_PERIPH_GPIOC,
[FuriHalBusGPIOD] = LL_AHB2_GRP1_PERIPH_GPIOD,
[FuriHalBusGPIOE] = LL_AHB2_GRP1_PERIPH_GPIOE,
[FuriHalBusGPIOH] = LL_AHB2_GRP1_PERIPH_GPIOH,
#if defined(ADC_SUPPORT_5_MSPS)
[FuriHalBusADC] = LL_AHB2_GRP1_PERIPH_ADC,
#endif
[FuriHalBusAES1] = LL_AHB2_GRP1_PERIPH_AES1,
[FuriHalBusAHB3_GRP1] = FURI_HAL_BUS_AHB3_GRP1,
[FuriHalBusQUADSPI] = LL_AHB3_GRP1_PERIPH_QUADSPI,
[FuriHalBusPKA] = LL_AHB3_GRP1_PERIPH_PKA,
[FuriHalBusAES2] = LL_AHB3_GRP1_PERIPH_AES2,
[FuriHalBusRNG] = LL_AHB3_GRP1_PERIPH_RNG,
[FuriHalBusHSEM] = LL_AHB3_GRP1_PERIPH_HSEM,
[FuriHalBusIPCC] = LL_AHB3_GRP1_PERIPH_IPCC,
[FuriHalBusFLASH] = LL_AHB3_GRP1_PERIPH_FLASH,
[FuriHalBusAPB1_GRP1] = FURI_HAL_BUS_APB1_GRP1,
[FuriHalBusTIM2] = LL_APB1_GRP1_PERIPH_TIM2,
[FuriHalBusLCD] = LL_APB1_GRP1_PERIPH_LCD,
[FuriHalBusSPI2] = LL_APB1_GRP1_PERIPH_SPI2,
[FuriHalBusI2C1] = LL_APB1_GRP1_PERIPH_I2C1,
[FuriHalBusI2C3] = LL_APB1_GRP1_PERIPH_I2C3,
[FuriHalBusCRS] = LL_APB1_GRP1_PERIPH_CRS,
[FuriHalBusUSB] = LL_APB1_GRP1_PERIPH_USB,
[FuriHalBusLPTIM1] = LL_APB1_GRP1_PERIPH_LPTIM1,
[FuriHalBusAPB1_GRP2] = FURI_HAL_BUS_APB1_GRP2,
[FuriHalBusLPUART1] = LL_APB1_GRP2_PERIPH_LPUART1,
[FuriHalBusLPTIM2] = LL_APB1_GRP2_PERIPH_LPTIM2,
[FuriHalBusAPB2_GRP1] = FURI_HAL_BUS_APB2_GRP1,
#if defined(ADC_SUPPORT_2_5_MSPS)
[FuriHalBusADC] = LL_APB2_GRP1_PERIPH_ADC,
#endif
[FuriHalBusTIM1] = LL_APB2_GRP1_PERIPH_TIM1,
[FuriHalBusSPI1] = LL_APB2_GRP1_PERIPH_SPI1,
[FuriHalBusUSART1] = LL_APB2_GRP1_PERIPH_USART1,
[FuriHalBusTIM16] = LL_APB2_GRP1_PERIPH_TIM16,
[FuriHalBusTIM17] = LL_APB2_GRP1_PERIPH_TIM17,
[FuriHalBusSAI1] = LL_APB2_GRP1_PERIPH_SAI1,
[FuriHalBusAPB3_GRP1] = FURI_HAL_BUS_IGNORE, // APB3_GRP1 clocking cannot be changed
[FuriHalBusRF] = LL_APB3_GRP1_PERIPH_RF,
};
void furi_hal_bus_init_early() {
FURI_CRITICAL_ENTER();
FURI_HAL_BUS_PERIPH_DISABLE(AHB1, FURI_HAL_BUS_AHB1_GRP1, 1);
FURI_HAL_BUS_PERIPH_DISABLE(AHB2, FURI_HAL_BUS_AHB2_GRP1, 1);
FURI_HAL_BUS_PERIPH_DISABLE(AHB3, FURI_HAL_BUS_AHB3_GRP1, 1);
FURI_HAL_BUS_PERIPH_DISABLE(APB1, FURI_HAL_BUS_APB1_GRP1, 1);
FURI_HAL_BUS_PERIPH_DISABLE(APB1, FURI_HAL_BUS_APB1_GRP2, 2);
FURI_HAL_BUS_PERIPH_DISABLE(APB2, FURI_HAL_BUS_APB2_GRP1, 1);
FURI_HAL_BUS_RESET_ASSERT(APB3, FURI_HAL_BUS_APB3_GRP1, 1);
FURI_CRITICAL_EXIT();
}
void furi_hal_bus_deinit_early() {
FURI_CRITICAL_ENTER();
FURI_HAL_BUS_PERIPH_ENABLE(AHB1, FURI_HAL_BUS_AHB1_GRP1, 1);
FURI_HAL_BUS_PERIPH_ENABLE(AHB2, FURI_HAL_BUS_AHB2_GRP1, 1);
FURI_HAL_BUS_PERIPH_ENABLE(AHB3, FURI_HAL_BUS_AHB3_GRP1, 1);
FURI_HAL_BUS_PERIPH_ENABLE(APB1, FURI_HAL_BUS_APB1_GRP1, 1);
FURI_HAL_BUS_PERIPH_ENABLE(APB1, FURI_HAL_BUS_APB1_GRP2, 2);
FURI_HAL_BUS_PERIPH_ENABLE(APB2, FURI_HAL_BUS_APB2_GRP1, 1);
FURI_HAL_BUS_RESET_DEASSERT(APB3, FURI_HAL_BUS_APB3_GRP1, 1);
FURI_CRITICAL_EXIT();
}
void furi_hal_bus_enable(FuriHalBus bus) {
furi_check(bus < FuriHalBusMAX);
const uint32_t value = furi_hal_bus[bus];
if(!value) {
return;
}
FURI_CRITICAL_ENTER();
if(bus < FuriHalBusAHB2_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_DISABLED(AHB1, value));
FURI_HAL_BUS_PERIPH_ENABLE(AHB1, value, 1);
} else if(bus < FuriHalBusAHB3_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_DISABLED(AHB2, value));
FURI_HAL_BUS_PERIPH_ENABLE(AHB2, value, 1);
} else if(bus < FuriHalBusAPB1_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_DISABLED(AHB3, value));
FURI_HAL_BUS_PERIPH_ENABLE(AHB3, value, 1);
} else if(bus < FuriHalBusAPB1_GRP2) {
furi_check(FURI_HAL_BUS_IS_PERIPH_DISABLED(APB1, value, 1));
FURI_HAL_BUS_PERIPH_ENABLE(APB1, value, 1);
} else if(bus < FuriHalBusAPB2_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_DISABLED(APB1, value, 2));
FURI_HAL_BUS_PERIPH_ENABLE(APB1, value, 2);
} else if(bus < FuriHalBusAPB3_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_DISABLED(APB2, value));
FURI_HAL_BUS_PERIPH_ENABLE(APB2, value, 1);
} else {
furi_check(FURI_HAL_BUS_IS_RESET_ASSERTED(APB3, value));
FURI_HAL_BUS_RESET_DEASSERT(APB3, FURI_HAL_BUS_APB3_GRP1, 1);
}
FURI_CRITICAL_EXIT();
}
void furi_hal_bus_reset(FuriHalBus bus) {
furi_check(bus < FuriHalBusMAX);
const uint32_t value = furi_hal_bus[bus];
if(!value) {
return;
}
FURI_CRITICAL_ENTER();
if(bus < FuriHalBusAHB2_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_ENABLED(AHB1, value));
FURI_HAL_BUS_PERIPH_RESET(AHB1, value, 1);
} else if(bus < FuriHalBusAHB3_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_ENABLED(AHB2, value));
FURI_HAL_BUS_PERIPH_RESET(AHB2, value, 1);
} else if(bus < FuriHalBusAPB1_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_ENABLED(AHB3, value));
FURI_HAL_BUS_PERIPH_RESET(AHB3, value, 1);
} else if(bus < FuriHalBusAPB1_GRP2) {
furi_check(FURI_HAL_BUS_IS_PERIPH_ENABLED(APB1, value, 1));
FURI_HAL_BUS_PERIPH_RESET(APB1, value, 1);
} else if(bus < FuriHalBusAPB2_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_ENABLED(APB1, value, 2));
FURI_HAL_BUS_PERIPH_RESET(APB1, value, 2);
} else if(bus < FuriHalBusAPB3_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_ENABLED(APB2, value));
FURI_HAL_BUS_PERIPH_RESET(APB2, value, 1);
} else {
furi_check(FURI_HAL_BUS_IS_RESET_DEASSERTED(APB3, value));
FURI_HAL_BUS_PERIPH_RESET(APB3, value, 1);
}
FURI_CRITICAL_EXIT();
}
void furi_hal_bus_disable(FuriHalBus bus) {
furi_check(bus < FuriHalBusMAX);
const uint32_t value = furi_hal_bus[bus];
if(!value) {
return;
}
FURI_CRITICAL_ENTER();
if(bus < FuriHalBusAHB2_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_ENABLED(AHB1, value));
FURI_HAL_BUS_PERIPH_DISABLE(AHB1, value, 1);
} else if(bus < FuriHalBusAHB3_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_ENABLED(AHB2, value));
FURI_HAL_BUS_PERIPH_DISABLE(AHB2, value, 1);
} else if(bus < FuriHalBusAPB1_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_ENABLED(AHB3, value));
FURI_HAL_BUS_PERIPH_DISABLE(AHB3, value, 1);
} else if(bus < FuriHalBusAPB1_GRP2) {
furi_check(FURI_HAL_BUS_IS_PERIPH_ENABLED(APB1, value, 1));
FURI_HAL_BUS_PERIPH_DISABLE(APB1, value, 1);
} else if(bus < FuriHalBusAPB2_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_ENABLED(APB1, value, 2));
FURI_HAL_BUS_PERIPH_DISABLE(APB1, value, 2);
} else if(bus < FuriHalBusAPB3_GRP1) {
furi_check(FURI_HAL_BUS_IS_PERIPH_ENABLED(APB2, value));
FURI_HAL_BUS_PERIPH_DISABLE(APB2, value, 1);
} else {
furi_check(FURI_HAL_BUS_IS_RESET_DEASSERTED(APB3, value));
FURI_HAL_BUS_RESET_ASSERT(APB3, FURI_HAL_BUS_APB3_GRP1, 1);
}
FURI_CRITICAL_EXIT();
}
bool furi_hal_bus_is_enabled(FuriHalBus bus) {
furi_check(bus < FuriHalBusMAX);
const uint32_t value = furi_hal_bus[bus];
if(value == FURI_HAL_BUS_IGNORE) {
return true;
}
bool ret = false;
FURI_CRITICAL_ENTER();
if(bus < FuriHalBusAHB2_GRP1) {
ret = FURI_HAL_BUS_IS_PERIPH_ENABLED(AHB1, value);
} else if(bus < FuriHalBusAHB3_GRP1) {
ret = FURI_HAL_BUS_IS_PERIPH_ENABLED(AHB2, value);
} else if(bus < FuriHalBusAPB1_GRP1) {
ret = FURI_HAL_BUS_IS_PERIPH_ENABLED(AHB3, value);
} else if(bus < FuriHalBusAPB1_GRP2) {
ret = FURI_HAL_BUS_IS_PERIPH_ENABLED(APB1, value, 1);
} else if(bus < FuriHalBusAPB2_GRP1) {
ret = FURI_HAL_BUS_IS_PERIPH_ENABLED(APB1, value, 2);
} else if(bus < FuriHalBusAPB3_GRP1) {
ret = FURI_HAL_BUS_IS_PERIPH_ENABLED(APB2, value);
} else {
ret = FURI_HAL_BUS_IS_RESET_DEASSERTED(APB3, value);
}
FURI_CRITICAL_EXIT();
return ret;
}

View File

@@ -0,0 +1,112 @@
#pragma once
#ifdef __cplusplus
extern "C" {
#endif
#include "stm32wbxx.h"
#include "stdbool.h"
typedef enum {
FuriHalBusAHB1_GRP1,
FuriHalBusDMA1,
FuriHalBusDMA2,
FuriHalBusDMAMUX1,
FuriHalBusCRC,
FuriHalBusTSC,
FuriHalBusAHB2_GRP1,
FuriHalBusGPIOA,
FuriHalBusGPIOB,
FuriHalBusGPIOC,
FuriHalBusGPIOD,
FuriHalBusGPIOE,
FuriHalBusGPIOH,
#if defined(ADC_SUPPORT_5_MSPS)
FuriHalBusADC,
#endif
FuriHalBusAES1,
FuriHalBusAHB3_GRP1,
FuriHalBusQUADSPI,
FuriHalBusPKA,
FuriHalBusAES2,
FuriHalBusRNG,
FuriHalBusHSEM,
FuriHalBusIPCC,
FuriHalBusFLASH,
FuriHalBusAPB1_GRP1,
FuriHalBusTIM2,
FuriHalBusLCD,
FuriHalBusSPI2,
FuriHalBusI2C1,
FuriHalBusI2C3,
FuriHalBusCRS,
FuriHalBusUSB,
FuriHalBusLPTIM1,
FuriHalBusAPB1_GRP2,
FuriHalBusLPUART1,
FuriHalBusLPTIM2,
FuriHalBusAPB2_GRP1,
#if defined(ADC_SUPPORT_2_5_MSPS)
FuriHalBusADC,
#endif
FuriHalBusTIM1,
FuriHalBusSPI1,
FuriHalBusUSART1,
FuriHalBusTIM16,
FuriHalBusTIM17,
FuriHalBusSAI1,
FuriHalBusAPB3_GRP1,
FuriHalBusRF,
FuriHalBusMAX,
} FuriHalBus;
/** Early initialization */
void furi_hal_bus_init_early();
/** Early de-initialization */
void furi_hal_bus_deinit_early();
/**
* Enable a peripheral by turning the clocking on and deasserting the reset.
* @param [in] bus Peripheral to be enabled.
* @warning Peripheral must be in disabled state in order to be enabled.
*/
void furi_hal_bus_enable(FuriHalBus bus);
/**
* Reset a peripheral by sequentially asserting and deasserting the reset.
* @param [in] bus Peripheral to be reset.
* @warning Peripheral must be in enabled state in order to be reset.
*/
void furi_hal_bus_reset(FuriHalBus bus);
/**
* Disable a peripheral by turning the clocking off and asserting the reset.
* @param [in] bus Peripheral to be disabled.
* @warning Peripheral must be in enabled state in order to be disabled.
*/
void furi_hal_bus_disable(FuriHalBus bus);
/** Check if peripheral is enabled
*
* @warning FuriHalBusAPB3_GRP1 is a special group of shared peripherals, for
* core1 its clock is always on and the only status we can report is
* peripheral reset status. Check code and Reference Manual for
* details.
*
* @param[in] bus The peripheral to check
*
* @return true if enabled or always enabled, false otherwise
*/
bool furi_hal_bus_is_enabled(FuriHalBus bus);
#ifdef __cplusplus
}
#endif

Some files were not shown because too many files have changed in this diff Show More