OSDN Git Service

Don't require environment variable to start with "pass:" prefix + some code clean-up.
authorLoRd_MuldeR <mulder2@gmx.de>
Fri, 26 Mar 2021 00:21:29 +0000 (01:21 +0100)
committerLoRd_MuldeR <mulder2@gmx.de>
Fri, 26 Mar 2021 00:48:30 +0000 (01:48 +0100)
frontend/src/main.c

index 0783f6b..0981bce 100644 (file)
 #include <signal.h>
 #include <assert.h>
 
-/* Const */
+// ==========================================================================
+// Constants
+// ==========================================================================
+
 #define BUFFER_SIZE 4096U
 
-/* Op-mode */
-#define SLUNK_MODE_HELP 0
-#define SLUNK_MODE_VERS 1
-#define SLUNK_MODE_ENCR 2
-#define SLUNK_MODE_DECR 3
-#define SLUNK_MODE_PASS 4
-#define SLUNK_MODE_TEST 5
+#define MODE_HELP 0
+#define MODE_VERS 1
+#define MODE_ENCR 2
+#define MODE_DECR 3
+#define MODE_PASS 4
+#define MODE_TEST 5
 
+#define PW_FROM_ENV (!(argc > 4))
+
+static const CHR* const ENV_PASSWRD = T("SLUNK_PASSPHRASE");
 static const CHR* const PREFIX_PASS = T("pass:");
 static const CHR* const PREFIX_FILE = T("file:");
 
-static const CHR* const ENV_PASSWD_NAME = T("SLUNK_PASSPHRASE");
-
 static const char PASSWD_SYMBOLS[] =
 {
        '!', '#', '$', '%', '&', '(', ')', '*', '+', ',', '-', '.', '/', '0', '1',
@@ -51,42 +54,44 @@ static const char PASSWD_SYMBOLS[] =
        'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', '{', '|', '}', '~'
 };
 
+static const size_t RCMD_PWDLEN_LENGTH = 12U;
+static const size_t DFLT_PWDLEN_LENGTH = 20U;
+
 static const uint64_t MAGIC_NUMBER = 0x243F6A8885A308D3ull;
 
 // ==========================================================================
 // Auxiliary functions
 // ==========================================================================
 
-static int parse_mode(const CHR* const command)
+static int parse_slunk_mode(const CHR* const command)
 {
        if ((!STRICMP(command, T("-h"))) || (!STRICMP(command, T("/?"))) || (!STRICMP(command, T("--help"))))
        {
-               return SLUNK_MODE_HELP;
+               return MODE_HELP;
        }
        else if ((!STRICMP(command, T("-v"))) || (!STRICMP(command, T("--version"))))
        {
-               return SLUNK_MODE_VERS;
+               return MODE_VERS;
        }
        else if ((!STRICMP(command, T("-e"))) || (!STRICMP(command, T("--encrypt"))))
        {
-               return SLUNK_MODE_ENCR;
+               return MODE_ENCR;
        }
        else if ((!STRICMP(command, T("-d"))) || (!STRICMP(command, T("--decrypt"))))
        {
-               return SLUNK_MODE_DECR;
+               return MODE_DECR;
        }
        else if ((!STRICMP(command, T("-p"))) || (!STRICMP(command, T("--make-pw"))))
        {
-               return SLUNK_MODE_PASS;
+               return MODE_PASS;
        }
        else if ((!STRICMP(command, T("-t"))) || (!STRICMP(command, T("--self-test"))))
        {
-               return SLUNK_MODE_TEST;
+               return MODE_TEST;
        }
        else
        {
-               FPRINTF(stderr, T("Error: The specified command \"%") T(PRISTR) T("\" is unknown!\n\n"), command);
-               exit(EXIT_FAILURE);
+               return -1; /*invalid command*/
        }
 }
 
@@ -100,22 +105,29 @@ static void print_manpage(const CHR *const program)
        FPRINTF(stderr, T("  %") T(PRISTR) T(" --encrypt [pass:<pass>|file:<file>] <input.txt> <output.enc>\n"), program);
        FPRINTF(stderr, T("  %") T(PRISTR) T(" --decrypt [pass:<pass>|file:<file>] <input.enc> <output.txt>\n"), program);
        FPRINTF(stderr, T("  %") T(PRISTR) T(" --make-pw [<length>]\n\n"), program);
-       FPRINTF(stderr, T("Optionally, reads passphrase from the %") T(PRISTR) T(" environment variable.\n\n"), ENV_PASSWD_NAME);
+       FPRINTF(stderr, T("Optionally, reads passphrase from the %") T(PRISTR) T(" environment variable.\n\n"), ENV_PASSWRD);
 }
 
-static char *duplicate_string(const CHR *const passphrase)
+static char *copy_passphrase(const CHR *const passphrase)
 {
+       if ((!passphrase) || (!passphrase[0U]))
+       {
+               FPUTS(T("Error: The passphrase input string must not be empty!\n\n"), stderr);
+               return NULL;
+       }
+
        char *const buffer = CHR_to_utf8(passphrase);
        if (!buffer)
        {
                FPUTS(T("Error: Failed to allocate the string buffer!\n\n"), stderr);
        }
+
        return buffer;
 }
 
-static char *read_passphrase(const CHRconst file_name)
+static char *read_passphrase(const CHR *const file_name)
 {
-       if (file_name && (!file_name[0U]))
+       if ((!file_name) || (!file_name[0U]))
        {
                FPUTS(T("Error: The passphrase input file name must not be empty!\n\n"), stderr);
                return NULL;
@@ -133,7 +145,7 @@ static char *read_passphrase(const CHR* const file_name)
        FILE *const file_in = use_stdin ? stdin : FOPEN(file_name, T("rb"));
        if (!file_in)
        {
-               FPRINTF(stderr, T("Error: Failed to open file \"%") T(PRISTR) T("\" for reading!\n\n"), file_name);
+               FPRINTF(stderr, T("Error: Failed to open input file \"%") T(PRISTR) T("\" for reading!\n\n"), file_name);
                free(buffer);
                return NULL;
        }
@@ -225,20 +237,20 @@ clean_up:
        return result;
 }
 
-static int open_files(FILE **const file_in, FILE **const file_out, const CHR* const input_path, const CHR* const output_path)
+static int open_files(FILE **const file_in, FILE **const file_out, const CHR *const input_path, const CHR *const output_path)
 {
-       *file_in = FOPEN(input_path, T("rb"));
-       if (!(*file_in))
+       if (!(*file_in = FOPEN(input_path, T("rb"))))
        {
-               FPRINTF(stderr, T("Error: Failed to open file \"%") T(PRISTR) T("\" for reading!\n\n"), input_path);
+               FPRINTF(stderr, T("Error: Failed to open input file \"%") T(PRISTR) T("\" for reading!\n\n"), input_path);
+               *file_out = NULL;
                return EXIT_FAILURE;
        }
 
-       *file_out = FOPEN(output_path, T("wb"));
-       if (!(*file_out))
+       if (!(*file_out = FOPEN(output_path, T("wb"))))
        {
-               FPRINTF(stderr, T("Error: Failed to open file \"%") T(PRISTR) T("\" for writing!\n\n"), output_path);
+               FPRINTF(stderr, T("Error: Failed to open output file \"%") T(PRISTR) T("\" for writing!\n\n"), output_path);
                fclose(*file_in);
+               *file_in = NULL;
                return EXIT_FAILURE;
        }
 
@@ -763,20 +775,26 @@ int MAIN(const int argc, CHR *const argv[])
                goto clean_up;
        }
 
-       const int mode = parse_mode(argv[1U]);
-       switch (mode)
+       const int slunk_mode = parse_slunk_mode(argv[1U]);
+       switch (slunk_mode)
        {
-       case SLUNK_MODE_HELP:
+       case MODE_HELP:
                print_manpage(get_file_name(argv[0U]));
-       case SLUNK_MODE_VERS:
+       case MODE_VERS:
                result = EXIT_SUCCESS;
                goto clean_up;
-       case SLUNK_MODE_PASS:
-               result = generate_passphrase((argc > 2) ? STRTOUL(argv[2U]) : 24U);
+       case MODE_ENCR:
+       case MODE_DECR:
+               break; /*fallthrough*/
+       case MODE_PASS:
+               result = generate_passphrase((argc > 2) ? STRTOUL(argv[2U]) : DFLT_PWDLEN_LENGTH);
                goto clean_up;
-       case SLUNK_MODE_TEST:
+       case MODE_TEST:
                result = run_self_test();
                goto clean_up;
+       default:
+               FPRINTF(stderr, T("Error: The specified command \"%") T(PRISTR) T("\" is unknown!\n\n"), argv[1U]);
+               goto clean_up;
        }
 
        if (argc < 4)
@@ -785,8 +803,8 @@ int MAIN(const int argc, CHR *const argv[])
                goto clean_up;
        }
 
-       const CHR *const passphrase = (argc > 4) ? argv[2U] : GETENV(ENV_PASSWD_NAME);
-       const CHR *const input_file = argv[(argc > 4) ? 3U : 2U], *const output_file = argv[(argc > 4) ? 4U : 3U];
+       const CHR *const passphrase = PW_FROM_ENV ? GETENV(ENV_PASSWRD) : argv[2U];
+       const CHR *const input_file = argv[PW_FROM_ENV ? 2U : 3U], *const output_file = argv[PW_FROM_ENV ? 3U : 4U];
 
        if ((!passphrase) || (!passphrase[0U]))
        {
@@ -794,10 +812,13 @@ int MAIN(const int argc, CHR *const argv[])
                goto clean_up;
        }
 
-       if (STRICMP(passphrase, T("-")) && (!STARTS_WITH(passphrase, PREFIX_PASS)) && (!STARTS_WITH(passphrase, PREFIX_FILE)))
+       if ((!PW_FROM_ENV) && STRICMP(passphrase, T("-")))
        {
-               FPRINTF(stderr, T("Error: The passphrase must start with a '%") T(PRISTR) T("' or '%") T(PRISTR) T("' prefix!\n\n"), PREFIX_PASS, PREFIX_FILE);
-               goto clean_up;
+               if ((!STARTS_WITH(passphrase, PREFIX_PASS)) && (!STARTS_WITH(passphrase, PREFIX_FILE)))
+               {
+                       FPRINTF(stderr, T("Error: The passphrase must start with a '%") T(PRISTR) T("' or '%") T(PRISTR) T("' prefix!\n\n"), PREFIX_PASS, PREFIX_FILE);
+                       goto clean_up;
+               }
        }
 
        if ((!input_file[0U]) || (!output_file[0U]))
@@ -810,9 +831,9 @@ int MAIN(const int argc, CHR *const argv[])
        /* Initialize passphrase                                 */
        /* ----------------------------------------------------- */
 
-       passphrase_buffer = STARTS_WITH(passphrase, PREFIX_PASS) ? duplicate_string(passphrase + STRLEN(PREFIX_PASS)) :
-                       (STARTS_WITH(passphrase, PREFIX_FILE) ? read_passphrase(passphrase + STRLEN(PREFIX_FILE)) : read_passphrase(NULL));
-       if (!passphrase_buffer)
+       if (!(passphrase_buffer = PW_FROM_ENV ? copy_passphrase(passphrase) :
+                       (STARTS_WITH(passphrase, PREFIX_PASS) ? copy_passphrase(passphrase + STRLEN(PREFIX_PASS)) :
+                       (STARTS_WITH(passphrase, PREFIX_FILE) ? read_passphrase(passphrase + STRLEN(PREFIX_FILE)) : read_passphrase(T("-"))))))
        {
                goto clean_up;
        }
@@ -822,18 +843,18 @@ int MAIN(const int argc, CHR *const argv[])
        const size_t passphrase_len = strlen(passphrase_buffer);
        if (passphrase_len < SLUNKCRYPT_PWDLEN_MIN)
        {
-               FPRINTF(stderr, T("Error: Passphrase must be at least %") T(PRIu64) T(" characters in length!\n\n"), (uint64_t)SLUNKCRYPT_PWDLEN_MIN);
+               FPRINTF(stderr, T("Error: Passphrase must be at least %u characters in length!\n\n"), (unsigned)SLUNKCRYPT_PWDLEN_MIN);
                goto clean_up;
        }
        else if (passphrase_len > SLUNKCRYPT_PWDLEN_MAX)
        {
-               FPRINTF(stderr, T("Error: Passphrase must be at most %") T(PRIu64) T(" characters in length!\n\n"), (uint64_t)SLUNKCRYPT_PWDLEN_MAX);
+               FPRINTF(stderr, T("Error: Passphrase must be at most %u characters in length!\n\n"),  (unsigned)SLUNKCRYPT_PWDLEN_MAX);
                goto clean_up;
        }
 
-       if (passphrase_len < 12U)
+       if (passphrase_len < RCMD_PWDLEN_LENGTH)
        {
-               FPUTS(T("Warning: Using a *short* passphrase; a length of 12 characters or more is recommended!\n\n"), stderr);
+               FPRINTF(stderr, T("Warning: Using a *short* passphrase; a length of %u characters or more is recommended!\n\n"), (unsigned)RCMD_PWDLEN_LENGTH);
        }
        else if (weak_passphrase(passphrase_buffer))
        {
@@ -846,12 +867,12 @@ int MAIN(const int argc, CHR *const argv[])
 
        const clock_t clk_start = clock();
 
-       switch (mode)
+       switch (slunk_mode)
        {
-       case SLUNK_MODE_ENCR:
+       case MODE_ENCR:
                result = encrypt(passphrase_buffer, input_file, output_file);
                break;
-       case SLUNK_MODE_DECR:
+       case MODE_DECR:
                result = decrypt(passphrase_buffer, input_file, output_file);
                break;
        default: