Skip to content

Commit

Permalink
BadUSB: BLE, media keys, Fn/Globe key commands (flipperdevices#3403)
Browse files Browse the repository at this point in the history
* BadUSB: media keys, GLOBE command
* f18 api table fix
* BadUSB over BLE
* Made PVS happy

Co-authored-by: Aleksandr Kutuzov <alleteam@gmail.com>
  • Loading branch information
nminaylov and skotopes authored Mar 25, 2024
1 parent f633f47 commit 6de2934
Show file tree
Hide file tree
Showing 22 changed files with 636 additions and 170 deletions.
2 changes: 1 addition & 1 deletion applications/main/bad_usb/application.fam
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ App(
icon="A_BadUsb_14",
order=70,
resources="resources",
fap_libs=["assets"],
fap_libs=["assets", "ble_profile"],
fap_icon="icon.png",
fap_category="USB",
)
102 changes: 64 additions & 38 deletions applications/main/bad_usb/bad_usb_app.c
Original file line number Diff line number Diff line change
@@ -1,11 +1,14 @@
#include "bad_usb_app_i.h"
#include "bad_usb_settings_filename.h"
#include <furi.h>
#include <furi_hal.h>
#include <storage/storage.h>
#include <lib/toolbox/path.h>
#include <flipper_format/flipper_format.h>

#define BAD_USB_SETTINGS_PATH BAD_USB_APP_BASE_FOLDER "/" BAD_USB_SETTINGS_FILE_NAME
#define BAD_USB_SETTINGS_PATH BAD_USB_APP_BASE_FOLDER "/.badusb.settings"
#define BAD_USB_SETTINGS_FILE_TYPE "Flipper BadUSB Settings File"
#define BAD_USB_SETTINGS_VERSION 1
#define BAD_USB_SETTINGS_DEFAULT_LAYOUT BAD_USB_APP_PATH_LAYOUT_FOLDER "/en-US.kl"

static bool bad_usb_app_custom_event_callback(void* context, uint32_t event) {
furi_assert(context);
Expand All @@ -26,46 +29,69 @@ static void bad_usb_app_tick_event_callback(void* context) {
}

static void bad_usb_load_settings(BadUsbApp* app) {
File* settings_file = storage_file_alloc(furi_record_open(RECORD_STORAGE));
if(storage_file_open(settings_file, BAD_USB_SETTINGS_PATH, FSAM_READ, FSOM_OPEN_EXISTING)) {
char chr;
while((storage_file_read(settings_file, &chr, 1) == 1) &&
!storage_file_eof(settings_file) && !isspace(chr)) {
furi_string_push_back(app->keyboard_layout, chr);
}
} else {
furi_string_reset(app->keyboard_layout);
Storage* storage = furi_record_open(RECORD_STORAGE);
FlipperFormat* fff = flipper_format_file_alloc(storage);
bool state = false;

FuriString* temp_str = furi_string_alloc();
uint32_t version = 0;
uint32_t interface = 0;

if(flipper_format_file_open_existing(fff, BAD_USB_SETTINGS_PATH)) {
do {
if(!flipper_format_read_header(fff, temp_str, &version)) break;
if((strcmp(furi_string_get_cstr(temp_str), BAD_USB_SETTINGS_FILE_TYPE) != 0) ||
(version != BAD_USB_SETTINGS_VERSION))
break;

if(!flipper_format_read_string(fff, "layout", temp_str)) break;
if(!flipper_format_read_uint32(fff, "interface", &interface, 1)) break;
if(interface > BadUsbHidInterfaceBle) break;

state = true;
} while(0);
}
storage_file_close(settings_file);
storage_file_free(settings_file);
flipper_format_free(fff);
furi_record_close(RECORD_STORAGE);

if(state) {
furi_string_set(app->keyboard_layout, temp_str);
app->interface = interface;

if(!furi_string_empty(app->keyboard_layout)) {
Storage* fs_api = furi_record_open(RECORD_STORAGE);
FileInfo layout_file_info;
FS_Error file_check_err = storage_common_stat(
fs_api, furi_string_get_cstr(app->keyboard_layout), &layout_file_info);
furi_record_close(RECORD_STORAGE);
if(file_check_err != FSE_OK) {
furi_string_reset(app->keyboard_layout);
return;
}
if(layout_file_info.size != 256) {
furi_string_reset(app->keyboard_layout);
if((file_check_err != FSE_OK) || (layout_file_info.size != 256)) {
furi_string_set(app->keyboard_layout, BAD_USB_SETTINGS_DEFAULT_LAYOUT);
}
} else {
furi_string_set(app->keyboard_layout, BAD_USB_SETTINGS_DEFAULT_LAYOUT);
app->interface = BadUsbHidInterfaceUsb;
}

furi_string_free(temp_str);
}

static void bad_usb_save_settings(BadUsbApp* app) {
File* settings_file = storage_file_alloc(furi_record_open(RECORD_STORAGE));
if(storage_file_open(settings_file, BAD_USB_SETTINGS_PATH, FSAM_WRITE, FSOM_OPEN_ALWAYS)) {
storage_file_write(
settings_file,
furi_string_get_cstr(app->keyboard_layout),
furi_string_size(app->keyboard_layout));
storage_file_write(settings_file, "\n", 1);
Storage* storage = furi_record_open(RECORD_STORAGE);
FlipperFormat* fff = flipper_format_file_alloc(storage);

if(flipper_format_file_open_always(fff, BAD_USB_SETTINGS_PATH)) {
do {
if(!flipper_format_write_header_cstr(
fff, BAD_USB_SETTINGS_FILE_TYPE, BAD_USB_SETTINGS_VERSION))
break;
if(!flipper_format_write_string(fff, "layout", app->keyboard_layout)) break;
uint32_t interface_id = app->interface;
if(!flipper_format_write_uint32(fff, "interface", (const uint32_t*)&interface_id, 1))
break;
} while(0);
}
storage_file_close(settings_file);
storage_file_free(settings_file);

flipper_format_free(fff);
furi_record_close(RECORD_STORAGE);
}

BadUsbApp* bad_usb_app_alloc(char* arg) {
Expand Down Expand Up @@ -103,13 +129,15 @@ BadUsbApp* bad_usb_app_alloc(char* arg) {
view_dispatcher_add_view(
app->view_dispatcher, BadUsbAppViewError, widget_get_view(app->widget));

app->submenu = submenu_alloc();
app->var_item_list = variable_item_list_alloc();
view_dispatcher_add_view(
app->view_dispatcher, BadUsbAppViewConfig, submenu_get_view(app->submenu));
app->view_dispatcher,
BadUsbAppViewConfig,
variable_item_list_get_view(app->var_item_list));

app->bad_usb_view = bad_usb_alloc();
app->bad_usb_view = bad_usb_view_alloc();
view_dispatcher_add_view(
app->view_dispatcher, BadUsbAppViewWork, bad_usb_get_view(app->bad_usb_view));
app->view_dispatcher, BadUsbAppViewWork, bad_usb_view_get_view(app->bad_usb_view));

view_dispatcher_attach_to_gui(app->view_dispatcher, app->gui, ViewDispatcherTypeFullscreen);

Expand All @@ -122,8 +150,6 @@ BadUsbApp* bad_usb_app_alloc(char* arg) {
furi_check(furi_hal_usb_set_config(NULL, NULL));

if(!furi_string_empty(app->file_path)) {
app->bad_usb_script = bad_usb_script_open(app->file_path);
bad_usb_script_set_keyboard_layout(app->bad_usb_script, app->keyboard_layout);
scene_manager_next_scene(app->scene_manager, BadUsbSceneWork);
} else {
furi_string_set(app->file_path, BAD_USB_APP_BASE_FOLDER);
Expand All @@ -144,15 +170,15 @@ void bad_usb_app_free(BadUsbApp* app) {

// Views
view_dispatcher_remove_view(app->view_dispatcher, BadUsbAppViewWork);
bad_usb_free(app->bad_usb_view);
bad_usb_view_free(app->bad_usb_view);

// Custom Widget
view_dispatcher_remove_view(app->view_dispatcher, BadUsbAppViewError);
widget_free(app->widget);

// Submenu
// Config menu
view_dispatcher_remove_view(app->view_dispatcher, BadUsbAppViewConfig);
submenu_free(app->submenu);
variable_item_list_free(app->var_item_list);

// View dispatcher
view_dispatcher_free(app->view_dispatcher);
Expand Down
5 changes: 3 additions & 2 deletions applications/main/bad_usb/bad_usb_app_i.h
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,12 @@
#include "bad_usb_app.h"
#include "scenes/bad_usb_scene.h"
#include "helpers/ducky_script.h"
#include "helpers/bad_usb_hid.h"

#include <gui/gui.h>
#include <assets_icons.h>
#include <gui/view_dispatcher.h>
#include <gui/scene_manager.h>
#include <gui/modules/submenu.h>
#include <dialogs/dialogs.h>
#include <notification/notification_messages.h>
#include <gui/modules/variable_item_list.h>
Expand All @@ -33,14 +33,15 @@ struct BadUsbApp {
NotificationApp* notifications;
DialogsApp* dialogs;
Widget* widget;
Submenu* submenu;
VariableItemList* var_item_list;

BadUsbAppError error;
FuriString* file_path;
FuriString* keyboard_layout;
BadUsb* bad_usb_view;
BadUsbScript* bad_usb_script;

BadUsbHidInterface interface;
FuriHalUsbInterface* usb_if_prev;
};

Expand Down
3 changes: 0 additions & 3 deletions applications/main/bad_usb/bad_usb_settings_filename.h

This file was deleted.

Loading

0 comments on commit 6de2934

Please sign in to comment.