forked from flipperdevices/flipperzero-firmware
-
-
Notifications
You must be signed in to change notification settings - Fork 551
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
* Initial implementation of #11
- Loading branch information
Showing
18 changed files
with
394 additions
and
20 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,79 @@ | ||
// Original idea: https://github.com/br0ziliy | ||
|
||
#include "cli.h" | ||
#include <lib/toolbox/args.h> | ||
#include "commands/list/list.h" | ||
#include "commands/add/add.h" | ||
#include "commands/delete/delete.h" | ||
|
||
#define TOTP_CLI_COMMAND_NAME "totp" | ||
|
||
static void totp_cli_print_unknown_command(FuriString* unknown_command) { | ||
printf("Command \"%s\" is unknown. Use \"help\" command to get list of available commands.", furi_string_get_cstr(unknown_command)); | ||
} | ||
|
||
static void totp_cli_print_help() { | ||
printf("Usage:\r\n"); | ||
printf("totp <command> <arguments>\r\n"); | ||
printf("Command list:\r\n"); | ||
printf("\thelp - print command usage help\r\n"); | ||
printf("\tlist - list all tokens\r\n"); | ||
printf("\tdelete <INDEX> [-f] - delete token\r\n"); | ||
printf("\t\t<INDEX> - token index in the list\r\n"); | ||
printf("\t\t-f - [OPTIONAL] force command to do not ask user for interactive confirmation\r\n"); | ||
printf("\tadd <NAME> <SECRET> [-a <ALGO>] [-d <DIGITS>] - add new token\r\n"); | ||
printf("\t\t<NAME> - token name\r\n"); | ||
printf("\t\t<SECRET> - Base32 token secret\r\n"); | ||
printf("\t\t<ALGO> - [OPTIONAL] token hashing algorithm, could be one of: sha1, sha256, sha512; default: sha1\r\n"); | ||
printf("\t\t<DIGITS> - [OPTIONAL] number of digits to generate, one of: 6, 8; default: 6\r\n\r\n"); | ||
} | ||
|
||
static void totp_cli_print_unauthenticated() { | ||
printf("Pleases enter PIN on your flipper device\r\n"); | ||
} | ||
|
||
static void totp_cli_handler(Cli* cli, FuriString* args, void* context) { | ||
PluginState* plugin_state = (PluginState* )context; | ||
|
||
if (plugin_state->current_scene == TotpSceneAuthentication) { | ||
totp_cli_print_unauthenticated(); | ||
|
||
while (plugin_state->current_scene == TotpSceneAuthentication && !cli_cmd_interrupt_received(cli)) { | ||
furi_delay_tick(0); | ||
} | ||
|
||
if (plugin_state->current_scene == TotpSceneAuthentication) { | ||
return; | ||
} | ||
} | ||
|
||
FuriString* cmd = furi_string_alloc(); | ||
|
||
args_read_string_and_trim(args, cmd); | ||
|
||
if(furi_string_cmp_str(cmd, "help") == 0 || furi_string_empty(cmd)) { | ||
totp_cli_print_help(); | ||
} else if(furi_string_cmp_str(cmd, "add") == 0) { | ||
totp_cli_handle_add_command(plugin_state, args); | ||
} else if(furi_string_cmp_str(cmd, "list") == 0) { | ||
totp_cli_handle_list_command(plugin_state); | ||
} else if(furi_string_cmp_str(cmd, "delete") == 0) { | ||
totp_cli_handle_delete_command(plugin_state, args, cli); | ||
} else { | ||
totp_cli_print_unknown_command(cmd); | ||
} | ||
|
||
furi_string_free(cmd); | ||
} | ||
|
||
void totp_cli_register_command_handler(PluginState* plugin_state) { | ||
Cli* cli = furi_record_open(RECORD_CLI); | ||
cli_add_command(cli, TOTP_CLI_COMMAND_NAME, CliCommandFlagParallelSafe, totp_cli_handler, plugin_state); | ||
furi_record_close(RECORD_CLI); | ||
} | ||
|
||
void totp_cli_unregister_command_handler() { | ||
Cli* cli = furi_record_open(RECORD_CLI); | ||
cli_delete_command(cli, TOTP_CLI_COMMAND_NAME); | ||
furi_record_close(RECORD_CLI); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
#pragma once | ||
|
||
#include <cli/cli.h> | ||
#include "../../types/plugin_state.h" | ||
|
||
void totp_cli_register_command_handler(PluginState* plugin_state); | ||
void totp_cli_unregister_command_handler(); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
#include "cli_common_helpers.h" | ||
#include <cli/cli.h> | ||
|
||
void totp_cli_print_invalid_arguments() { | ||
printf("Invalid command arguments. use \"help\" command to get list of available commands"); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
#pragma once | ||
|
||
void totp_cli_print_invalid_arguments(); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,125 @@ | ||
#include "add.h" | ||
#include <stdlib.h> | ||
#include <lib/toolbox/args.h> | ||
#include "../../../list/list.h" | ||
#include "../../../../types/token_info.h" | ||
#include "../../../config/config.h" | ||
#include "../../cli_common_helpers.h" | ||
#include "../../../../scenes/scene_director.h" | ||
|
||
static bool token_info_set_digits_from_str(TokenInfo* token_info, FuriString* str) { | ||
switch(furi_string_get_char(str, 0)) { | ||
case '6': | ||
token_info->digits = TOTP_6_DIGITS; | ||
return true; | ||
case '8': | ||
token_info->digits = TOTP_8_DIGITS; | ||
return true; | ||
} | ||
|
||
return false; | ||
} | ||
|
||
static bool token_info_set_algo_from_str(TokenInfo* token_info, FuriString* str) { | ||
if(furi_string_cmpi_str(str, TOTP_CONFIG_TOKEN_ALGO_SHA1_NAME) == 0) { | ||
token_info->algo = SHA1; | ||
return true; | ||
} | ||
|
||
if(furi_string_cmpi_str(str, TOTP_CONFIG_TOKEN_ALGO_SHA256_NAME) == 0) { | ||
token_info->algo = SHA256; | ||
return true; | ||
} | ||
|
||
if(furi_string_cmpi_str(str, TOTP_CONFIG_TOKEN_ALGO_SHA512_NAME) == 0) { | ||
token_info->algo = SHA512; | ||
return true; | ||
} | ||
|
||
return false; | ||
} | ||
|
||
void totp_cli_handle_add_command(PluginState* plugin_state, FuriString* args) { | ||
FuriString* temp_str = furi_string_alloc(); | ||
const char* temp_cstr; | ||
|
||
TokenInfo* token_info = token_info_alloc(); | ||
|
||
// Reading token name | ||
if (!args_read_probably_quoted_string_and_trim(args, temp_str)) { | ||
totp_cli_print_invalid_arguments(); | ||
furi_string_free(temp_str); | ||
token_info_free(token_info); | ||
return; | ||
} | ||
|
||
temp_cstr = furi_string_get_cstr(temp_str); | ||
token_info->name = malloc(strlen(temp_cstr) + 1); | ||
strcpy(token_info->name, temp_cstr); | ||
|
||
// Reading token secret | ||
if (!args_read_probably_quoted_string_and_trim(args, temp_str)) { | ||
totp_cli_print_invalid_arguments(); | ||
furi_string_free(temp_str); | ||
token_info_free(token_info); | ||
return; | ||
} | ||
|
||
temp_cstr = furi_string_get_cstr(temp_str); | ||
if (!token_info_set_secret(token_info, temp_cstr, strlen(temp_cstr), plugin_state->iv)) { | ||
printf("Token secret seems to be invalid and can not be parsed\r\n"); | ||
furi_string_free(temp_str); | ||
token_info_free(token_info); | ||
return; | ||
} | ||
|
||
// Read optional arguments | ||
while (args_read_string_and_trim(args, temp_str)) { | ||
bool parsed = false; | ||
if (furi_string_cmpi_str(temp_str, "-a") == 0) { | ||
if (!args_read_string_and_trim(args, temp_str)) { | ||
printf("Missed value for argument \"-a\"\r\n"); | ||
} else if (!token_info_set_algo_from_str(token_info, temp_str)) { | ||
printf("\"%s\" is incorrect value for argument \"-a\"\r\n", furi_string_get_cstr(temp_str)); | ||
} else { | ||
parsed = true; | ||
} | ||
} else if (furi_string_cmpi_str(temp_str, "-d") == 0) { | ||
if (!args_read_string_and_trim(args, temp_str)) { | ||
printf("Missed value for argument \"-d\"\r\n"); | ||
} else if (!token_info_set_digits_from_str(token_info, temp_str)) { | ||
printf("\"%s\" is incorrect value for argument \"-d\"\r\n", furi_string_get_cstr(temp_str)); | ||
} else { | ||
parsed = true; | ||
} | ||
} | ||
if (!parsed) { | ||
totp_cli_print_invalid_arguments(); | ||
furi_string_free(temp_str); | ||
token_info_free(token_info); | ||
return; | ||
} | ||
} | ||
|
||
bool load_generate_token_scene = false; | ||
if (plugin_state->current_scene == TotpSceneGenerateToken) { | ||
totp_scene_director_activate_scene(plugin_state, TotpSceneNone, NULL); | ||
load_generate_token_scene = true; | ||
} | ||
|
||
if(plugin_state->tokens_list == NULL) { | ||
plugin_state->tokens_list = list_init_head(token_info); | ||
} else { | ||
list_add(plugin_state->tokens_list, token_info); | ||
} | ||
plugin_state->tokens_count++; | ||
totp_config_file_save_new_token(token_info); | ||
|
||
if (load_generate_token_scene) { | ||
totp_scene_director_activate_scene(plugin_state, TotpSceneGenerateToken, NULL); | ||
} | ||
|
||
furi_string_free(temp_str); | ||
|
||
printf("Token \"%s\" has been successfully added\r\n", token_info->name); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
#pragma once | ||
|
||
#include <cli/cli.h> | ||
#include "../../../../types/plugin_state.h" | ||
|
||
void totp_cli_handle_add_command(PluginState* plugin_state, FuriString* args); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,71 @@ | ||
#include "delete.h" | ||
|
||
#include <stdlib.h> | ||
#include <ctype.h> | ||
#include <lib/toolbox/args.h> | ||
#include "../../../list/list.h" | ||
#include "../../../config/config.h" | ||
#include "../../cli_common_helpers.h" | ||
#include "../../../../scenes/scene_director.h" | ||
|
||
void totp_cli_handle_delete_command(PluginState* plugin_state, FuriString* args, Cli* cli) { | ||
int token_number; | ||
if (!args_read_int_and_trim(args, &token_number) || token_number <= 0 || token_number > plugin_state->tokens_count) { | ||
totp_cli_print_invalid_arguments(); | ||
return; | ||
} | ||
|
||
FuriString* temp_str = furi_string_alloc(); | ||
bool confirm_needed = true; | ||
if (args_read_string_and_trim(args, temp_str)) { | ||
if (furi_string_cmpi_str(temp_str, "-f") == 0) { | ||
confirm_needed = false; | ||
} else { | ||
printf("Unknown argument \"%s\"\r\n", furi_string_get_cstr(temp_str)); | ||
totp_cli_print_invalid_arguments(); | ||
furi_string_free(temp_str); | ||
return; | ||
} | ||
} | ||
furi_string_free(temp_str); | ||
|
||
ListNode* list_node = list_element_at(plugin_state->tokens_list, token_number - 1); | ||
|
||
TokenInfo* token_info = list_node->data; | ||
|
||
bool confirmed = !confirm_needed; | ||
if (confirm_needed) { | ||
printf("WARNING!\r\n"); | ||
printf("Token \"%s\" will be permanently deleted without ability to recover it.\r\n", token_info->name); | ||
printf("Confirm? [y/n]\r\n"); | ||
fflush(stdout); | ||
char user_pick; | ||
do { | ||
user_pick = tolower(cli_getc(cli)); | ||
} while (user_pick != 'y' && user_pick != 'n' && user_pick != 0x0d); | ||
|
||
confirmed = user_pick == 'y' || user_pick == 0x0d; | ||
} | ||
|
||
if (confirmed) { | ||
bool activate_generate_token_scene = false; | ||
if (plugin_state->current_scene == TotpSceneGenerateToken) { | ||
totp_scene_director_activate_scene(plugin_state, TotpSceneNone, NULL); | ||
activate_generate_token_scene = true; | ||
} | ||
|
||
plugin_state->tokens_list = list_remove(plugin_state->tokens_list, list_node); | ||
plugin_state->tokens_count--; | ||
|
||
totp_full_save_config_file(plugin_state); | ||
|
||
if (activate_generate_token_scene) { | ||
totp_scene_director_activate_scene(plugin_state, TotpSceneGenerateToken, NULL); | ||
} | ||
|
||
printf("Token \"%s\" has been successfully deleted\r\n", token_info->name); | ||
token_info_free(token_info); | ||
} else { | ||
printf("User not confirmed\r\n"); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
#pragma once | ||
|
||
#include <cli/cli.h> | ||
#include "../../../../types/plugin_state.h" | ||
|
||
void totp_cli_handle_delete_command(PluginState* plugin_state, FuriString* args, Cli* cli); |
Oops, something went wrong.