Merge remote-tracking branch 'UFW/dev' into archive

This commit is contained in:
gid9798
2023-07-18 23:49:03 +03:00
39 changed files with 845 additions and 349 deletions

View File

@@ -4,5 +4,6 @@ App(
targets=["f7"],
entry_point="subghz_device_cc1101_ext_ep",
requires=["subghz"],
sdk_headers=["cc1101_ext/cc1101_ext_interconnect.h"],
fap_libs=["hwdrivers"],
)

View File

@@ -18,7 +18,7 @@ Before launching the application, connect the sensor to Flipper's external GPIO
In order to launch this demo, follow the steps below:
1. Make sure your Flipper has an SD card installed.
2. Connect your Flipper to the computer via a USB cable.
3. Run `./fbt launch_app APPSRC=example_thermo` in your terminal emulator of choice.
3. Run `./fbt launch APPSRC=example_thermo` in your terminal emulator of choice.
## Changing the data pin
It is possible to use other GPIO pin as a 1-Wire data pin. In order to change it, set the `THERMO_GPIO_PIN` macro to any of the options listed below:

View File

@@ -517,4 +517,14 @@ uint8_t nrf24_find_channel(
}
return ch;
}
bool nrf24_check_connected(FuriHalSpiBusHandle* handle) {
uint8_t status = nrf24_status(handle);
if(status != 0x00) {
return true;
} else {
return false;
}
}

View File

@@ -361,6 +361,13 @@ void int32_to_bytes(uint32_t val, uint8_t* out, bool bigendian);
*/
uint32_t bytes_to_int32(uint8_t* bytes, bool bigendian);
/** Check if the nrf24 is connected
* @param handle - pointer to FuriHalSpiHandle
*
* @return true if connected, otherwise false
*/
bool nrf24_check_connected(FuriHalSpiBusHandle* handle);
#ifdef __cplusplus
}
#endif

View File

@@ -9,15 +9,14 @@
#include <furi_hal_interrupt.h>
#include <furi_hal_resources.h>
#include <nrf24.h>
#include <notification/notification_messages.h>
#include "mousejacker_ducky.h"
#include <nrf24_mouse_jacker_icons.h>
#define TAG "mousejacker"
#define LOGITECH_MAX_CHANNEL 85
#define NRFSNIFF_APP_PATH_FOLDER "/ext/nrfsniff"
#define NRFSNIFF_APP_PATH_EXTENSION ".txt"
#define NRFSNIFF_APP_FILENAME "addresses.txt"
#define MOUSEJACKER_APP_PATH_FOLDER "/ext/mousejacker"
#define NRFSNIFF_APP_PATH_FOLDER_ADDRESSES EXT_PATH("apps_data/nrf24sniff/addresses.txt")
#define LOCAL_BADUSB_FOLDER EXT_PATH("badusb")
#define MOUSEJACKER_APP_PATH_EXTENSION ".txt"
#define MAX_ADDRS 100
@@ -32,12 +31,13 @@ typedef struct {
} PluginEvent;
uint8_t addrs_count = 0;
uint8_t addr_idx = 0;
int8_t addr_idx = 0;
uint8_t loaded_addrs[MAX_ADDRS][6]; // first byte is rate, the rest are the address
char target_fmt_text[] = "Target addr: %s";
char target_address_str[12] = "None";
char target_text[30];
char index_text[30];
static void render_callback(Canvas* const canvas, void* ctx) {
furi_assert(ctx);
@@ -53,8 +53,15 @@ static void render_callback(Canvas* const canvas, void* ctx) {
snprintf(target_text, sizeof(target_text), target_fmt_text, target_address_str);
canvas_draw_str_aligned(canvas, 7, 10, AlignLeft, AlignBottom, target_text);
canvas_draw_str_aligned(canvas, 22, 20, AlignLeft, AlignBottom, "<- select address ->");
canvas_draw_str_aligned(canvas, 10, 30, AlignLeft, AlignBottom, "Press Ok button to ");
canvas_draw_str_aligned(canvas, 10, 40, AlignLeft, AlignBottom, "browse for ducky script");
snprintf(
index_text, sizeof(index_text), "Address index: %d/%d", addr_idx + 1, addrs_count);
canvas_draw_str_aligned(canvas, 10, 30, AlignLeft, AlignBottom, index_text);
canvas_draw_str_aligned(canvas, 10, 40, AlignLeft, AlignBottom, "Press Ok button to ");
canvas_draw_str_aligned(canvas, 10, 50, AlignLeft, AlignBottom, "browse for ducky script");
if(!plugin_state->is_nrf24_connected) {
canvas_draw_str_aligned(
canvas, 10, 60, AlignLeft, AlignBottom, "Connect NRF24 to GPIO!");
}
} else if(plugin_state->addr_err) {
canvas_draw_str_aligned(
canvas, 10, 10, AlignLeft, AlignBottom, "Error: No nrfsniff folder");
@@ -94,6 +101,7 @@ static void input_callback(InputEvent* input_event, FuriMessageQueue* event_queu
static void mousejacker_state_init(PluginState* const plugin_state) {
plugin_state->is_thread_running = false;
plugin_state->is_nrf24_connected = true;
}
static void hexlify(uint8_t* in, uint8_t size, char* out) {
@@ -107,7 +115,7 @@ static bool open_ducky_script(Stream* stream, PluginState* plugin_state) {
bool result = false;
FuriString* path;
path = furi_string_alloc();
furi_string_set(path, MOUSEJACKER_APP_PATH_FOLDER);
furi_string_set(path, LOCAL_BADUSB_FOLDER);
DialogsFileBrowserOptions browser_options;
dialog_file_browser_set_basic_options(
@@ -132,27 +140,17 @@ static bool open_ducky_script(Stream* stream, PluginState* plugin_state) {
}
static bool open_addrs_file(Stream* stream) {
DialogsApp* dialogs = furi_record_open("dialogs");
bool result = false;
FuriString* path;
path = furi_string_alloc();
furi_string_set(path, NRFSNIFF_APP_PATH_FOLDER);
furi_string_set(path, NRFSNIFF_APP_PATH_FOLDER_ADDRESSES);
DialogsFileBrowserOptions browser_options;
dialog_file_browser_set_basic_options(
&browser_options, NRFSNIFF_APP_PATH_EXTENSION, &I_sub1_10px);
browser_options.hide_ext = false;
bool ret = dialog_file_browser_show(dialogs, path, path, &browser_options);
furi_record_close("dialogs");
if(ret) {
if(!file_stream_open(stream, furi_string_get_cstr(path), FSAM_READ, FSOM_OPEN_EXISTING)) {
FURI_LOG_D(TAG, "Cannot open file \"%s\"", furi_string_get_cstr(path));
} else {
result = true;
}
if(!file_stream_open(stream, furi_string_get_cstr(path), FSAM_READ, FSOM_OPEN_EXISTING)) {
FURI_LOG_D(TAG, "Cannot open file \"%s\"", furi_string_get_cstr(path));
} else {
result = true;
}
furi_string_free(path);
return result;
}
@@ -277,12 +275,6 @@ static int32_t mj_worker_thread(void* ctx) {
return 0;
}
void start_mjthread(PluginState* plugin_state) {
if(!plugin_state->is_thread_running) {
furi_thread_start(plugin_state->mjthread);
}
}
int32_t mousejacker_app(void* p) {
UNUSED(p);
FuriMessageQueue* event_queue = furi_message_queue_alloc(8, sizeof(PluginEvent));
@@ -297,6 +289,8 @@ int32_t mousejacker_app(void* p) {
return 255;
}
NotificationApp* notification = furi_record_open(RECORD_NOTIFICATION);
// Set system callbacks
ViewPort* view_port = view_port_alloc();
view_port_draw_callback_set(view_port, render_callback, plugin_state);
@@ -307,7 +301,6 @@ int32_t mousejacker_app(void* p) {
gui_add_view_port(gui, view_port, GuiLayerFullscreen);
plugin_state->storage = furi_record_open(RECORD_STORAGE);
storage_common_mkdir(plugin_state->storage, MOUSEJACKER_APP_PATH_FOLDER);
plugin_state->file_stream = file_stream_alloc(plugin_state->storage);
plugin_state->mjthread = furi_thread_alloc();
@@ -344,21 +337,25 @@ int32_t mousejacker_app(void* p) {
case InputKeyRight:
if(!plugin_state->addr_err) {
addr_idx++;
if(addr_idx > addrs_count) addr_idx = 0;
if(addr_idx >= addrs_count) addr_idx = 0;
hexlify(loaded_addrs[addr_idx] + 1, 5, target_address_str);
}
break;
case InputKeyLeft:
if(!plugin_state->addr_err) {
addr_idx--;
if(addr_idx == 0) addr_idx = addrs_count - 1;
if(addr_idx < 0) addr_idx = addrs_count - 1;
hexlify(loaded_addrs[addr_idx] + 1, 5, target_address_str);
}
break;
case InputKeyOk:
if(!plugin_state->addr_err) {
if(!plugin_state->is_thread_running) {
start_mjthread(plugin_state);
if(!nrf24_check_connected(nrf24_HANDLE)) {
plugin_state->is_nrf24_connected = false;
view_port_update(view_port);
notification_message(notification, &sequence_error);
} else if(!plugin_state->is_thread_running) {
furi_thread_start(plugin_state->mjthread);
view_port_update(view_port);
}
}
@@ -388,6 +385,7 @@ int32_t mousejacker_app(void* p) {
view_port_enabled_set(view_port, false);
gui_remove_view_port(gui, view_port);
furi_record_close(RECORD_GUI);
furi_record_close(RECORD_NOTIFICATION);
furi_record_close(RECORD_STORAGE);
view_port_free(view_port);
furi_message_queue_free(event_queue);
@@ -395,4 +393,4 @@ int32_t mousejacker_app(void* p) {
free(plugin_state);
return 0;
}
}

View File

@@ -26,6 +26,7 @@ typedef struct {
bool addr_err;
bool is_thread_running;
bool is_ducky_running;
bool is_nrf24_connected;
bool close_thread_please;
Storage* storage;
FuriThread* mjthread;

View File

@@ -517,4 +517,14 @@ uint8_t nrf24_find_channel(
}
return ch;
}
bool nrf24_check_connected(FuriHalSpiBusHandle* handle) {
uint8_t status = nrf24_status(handle);
if(status != 0x00) {
return true;
} else {
return false;
}
}

View File

@@ -361,6 +361,13 @@ void int32_to_bytes(uint32_t val, uint8_t* out, bool bigendian);
*/
uint32_t bytes_to_int32(uint8_t* bytes, bool bigendian);
/** Check if the nrf24 is connected
* @param handle - pointer to FuriHalSpiHandle
*
* @return true if connected, otherwise false
*/
bool nrf24_check_connected(FuriHalSpiBusHandle* handle);
#ifdef __cplusplus
}
#endif

View File

@@ -10,11 +10,11 @@
#define LOGITECH_MAX_CHANNEL 85
#define COUNT_THRESHOLD 2
#define DEFAULT_SAMPLE_TIME 8000
#define DEFAULT_SAMPLE_TIME 4000
#define MAX_ADDRS 100
#define MAX_CONFIRMED 32
#define NRFSNIFF_APP_PATH_FOLDER "/ext/nrfsniff"
#define NRFSNIFF_APP_PATH_FOLDER STORAGE_APP_DATA_PATH_PREFIX
#define NRFSNIFF_APP_FILENAME "addresses.txt"
#define TAG "nrfsniff"
@@ -341,6 +341,7 @@ int32_t nrfsniff_app(void* p) {
NotificationApp* notification = furi_record_open(RECORD_NOTIFICATION);
Storage* storage = furi_record_open(RECORD_STORAGE);
storage_common_migrate(storage, EXT_PATH("nrfsniff"), NRFSNIFF_APP_PATH_FOLDER);
storage_common_mkdir(storage, NRFSNIFF_APP_PATH_FOLDER);
PluginEvent event;
@@ -387,13 +388,19 @@ int32_t nrfsniff_app(void* p) {
break;
case InputKeyOk:
// toggle sniffing
sniffing_state = !sniffing_state;
if(sniffing_state) {
clear_cache();
start_sniffing();
start = furi_get_tick();
} else
wrap_up(storage, notification);
if(nrf24_check_connected(nrf24_HANDLE)) {
sniffing_state = !sniffing_state;
if(sniffing_state) {
clear_cache();
start_sniffing();
start = furi_get_tick();
} else {
wrap_up(storage, notification);
}
} else {
notification_message(notification, &sequence_error);
}
break;
case InputKeyBack:
if(event.input.type == InputTypeLong) processing = false;

View File

@@ -12,15 +12,15 @@ void ibutton_scene_delete_confirm_on_enter(void* context) {
widget_add_button_element(
widget, GuiButtonTypeRight, "Delete", ibutton_widget_callback, context);
furi_string_printf(tmp, "Delete %s?", ibutton->key_name);
widget_add_string_element(
widget, 128 / 2, 0, AlignCenter, AlignTop, FontPrimary, furi_string_get_cstr(tmp));
furi_string_printf(tmp, "\e#Delete %s?\e#", ibutton->key_name);
widget_add_text_box_element(
widget, 0, 0, 128, 23, AlignCenter, AlignCenter, furi_string_get_cstr(tmp), false);
furi_string_reset(tmp);
ibutton_protocols_render_brief_data(ibutton->protocols, key, tmp);
widget_add_string_multiline_element(
widget, 128 / 2, 16, AlignCenter, AlignTop, FontSecondary, furi_string_get_cstr(tmp));
widget, 128 / 2, 24, AlignCenter, AlignTop, FontSecondary, furi_string_get_cstr(tmp));
view_dispatcher_switch_to_view(ibutton->view_dispatcher, iButtonViewWidget);
furi_string_free(tmp);

View File

@@ -1,8 +1,9 @@
App(
appid="subghz",
name="Sub-GHz",
apptype=FlipperAppType.MENUEXTERNAL,
apptype=FlipperAppType.APP,
targets=["f7"],
cdefines=["APP_SUBGHZ"],
entry_point="subghz_app",
requires=[
"gui",
@@ -15,7 +16,7 @@ App(
],
icon="A_Sub1ghz_14",
stack_size=3 * 1024,
order=10,
order=1,
fap_libs=["assets", "hwdrivers"],
fap_icon="icon.png",
fap_category="Sub-GHz",
@@ -26,6 +27,7 @@ App(
targets=["f7"],
apptype=FlipperAppType.STARTUP,
entry_point="subghz_on_system_start",
requires=["subghz"],
order=40,
)

View File

@@ -94,7 +94,25 @@ static uint32_t loader_menu_exit(void* context) {
}
static void loader_menu_build_menu(LoaderMenuApp* app, LoaderMenu* menu) {
size_t i;
size_t i = 0;
menu_add_item(
app->primary_menu,
LOADER_APPLICATIONS_NAME,
&A_Plugins_14,
i++,
loader_menu_applications_callback,
(void*)menu);
for(i = 0; i < FLIPPER_APPS_COUNT; i++) {
menu_add_item(
app->primary_menu,
FLIPPER_APPS[i].name,
FLIPPER_APPS[i].icon,
i,
loader_menu_apps_callback,
(void*)menu);
}
for(i = 0; i < FLIPPER_EXTERNAL_APPS_COUNT; i++) {
menu_add_item(
@@ -106,24 +124,8 @@ static void loader_menu_build_menu(LoaderMenuApp* app, LoaderMenu* menu) {
(void*)menu);
}
for(i = 0; i < FLIPPER_APPS_COUNT; i++) {
menu_add_item(
app->primary_menu,
FLIPPER_APPS[i].name,
FLIPPER_APPS[i].icon,
i,
loader_menu_apps_callback,
(void*)menu);
}
menu_add_item(
app->primary_menu, "Settings", &A_Settings_14, i++, loader_menu_switch_to_settings, app);
menu_add_item(
app->primary_menu,
LOADER_APPLICATIONS_NAME,
&A_Plugins_14,
i++,
loader_menu_applications_callback,
(void*)menu);
};
static void loader_menu_build_submenu(LoaderMenuApp* app, LoaderMenu* loader_menu) {

View File

@@ -300,6 +300,7 @@ static bool power_update_info(Power* power) {
info.is_charging = furi_hal_power_is_charging();
info.gauge_is_ok = furi_hal_power_gauge_is_ok();
info.is_shutdown_requested = furi_hal_power_is_shutdown_requested();
info.charge = furi_hal_power_get_pct();
info.health = furi_hal_power_get_bat_health_pct();
info.capacity_remaining = furi_hal_power_get_battery_remaining_capacity();
@@ -328,7 +329,7 @@ static void power_check_low_battery(Power* power) {
}
// Check battery charge and vbus voltage
if((power->info.charge == 0) && (power->info.voltage_vbus < 4.0f) &&
if((power->info.is_shutdown_requested) && (power->info.voltage_vbus < 4.0f) &&
power->show_low_bat_level_message) {
if(!power->battery_low) {
view_dispatcher_send_to_front(power->view_dispatcher);

View File

@@ -37,6 +37,7 @@ typedef struct {
typedef struct {
bool gauge_is_ok;
bool is_charging;
bool is_shutdown_requested;
float current_charger;
float current_gauge;

View File

@@ -54,8 +54,7 @@ static void draw_battery(Canvas* canvas, BatteryInfoModel* data, int x, int y) {
(uint32_t)(data->vbus_voltage * 10) % 10,
current);
} else if(current < -5) {
// Often gauge reports anything in the range 1~5ma as 5ma
// That brings confusion, so we'll treat it as Napping
// 0-5ma deadband
snprintf(
emote,
sizeof(emote),