diff options
author | Aaron Ball <nullspoon@oper.io> | 2019-02-03 22:57:47 -0700 |
---|---|---|
committer | Aaron Ball <nullspoon@oper.io> | 2019-02-04 22:49:55 -0700 |
commit | 6878a1fc964d4ef0ddba15461801caf972f91185 (patch) | |
tree | a6957c56e3cb36669cc2df5a196c0eff3717e7c5 /src | |
parent | f64ca2f8c12b15d33722b036db8447dc96cc10de (diff) | |
download | upwgen-6878a1fc964d4ef0ddba15461801caf972f91185.tar.gz upwgen-6878a1fc964d4ef0ddba15461801caf972f91185.tar.xz |
Initial support for user-specified charsets
Added runtime switch parsing. This adds the -c,--capitalize;
-y,--symbols; -l,--lower; -i,--i18n; -n,--numerals; and -h,--help
switches. These allow the end user to customer the output.
Set default password length to 32 long. User can still specify with old
syntax. Also added some better error checking on the input string to
ensure the user specifies an int.
Added helptext (usage function). Updated README.
Diffstat (limited to 'src')
-rw-r--r-- | src/main.c | 74 |
1 files changed, 60 insertions, 14 deletions
@@ -15,6 +15,7 @@ // along with this program. If not, see <http://www.gnu.org/licenses/>. #include <stdlib.h> #include <stdio.h> +#include <string.h> #include <time.h> #include <locale.h> @@ -74,7 +75,6 @@ int intrcat(unsigned int* arr, unsigned int rstart, unsigned int rend) { // // @return Size of the array contents int populate_intl_arr(unsigned int* out) { - out[0] = '\0'; int count = 0; // Populate the array @@ -106,34 +106,80 @@ void print_intl_arr(unsigned int* arr) { } +void usage() { + printf( + "Upwgen is a password generator with international support. If no length\n" + "is specified, defaults to 32 characters output length\n\n" + "Usage:\n upwgen [options] [length]\n\n" + "Options:\n" + " -c,--capitalize Include at least one capital letter in output\n" + " -l,--lower Include at least one lower case letter in output\n" + " -n,--numerals Include at least one numeral in output\n" + " -y,--symbols Include at least one symbol in output\n" + " -i,--i18n Include at least one international letter in output\n" + "\n" + " -h,--help Print this help text\n" + ); +} + + int main(int argc, char* argv[]) { - char* passlen; // Argv 1, user specified length of the password - int count; // Number of international chars to choose from struct timespec ts; // Timespec for seeding rng + int count; // Number of chars to choose from int len; // Password length + int i; // Arg index unsigned long seed; // Seed for the RNG (current seconds * nanoseconds) unsigned int chars[1024]; // Uint array to hold international chars + // Initialize + count = 0; + len = 32; + i = 1; + chars[0] = '\0'; setlocale(LC_ALL, "en_US.UTF-8"); - if(argc == 1) { - printf("Password length required\n"); - return 1; + while(i < argc) { + if(strcmp(argv[i], "-c") == 0 || strcmp(argv[i], "--capitals") == 0) { + count += intrcat(chars, 65, 90); // English uppercase + } else if(strcmp(argv[i], "-l") == 0 || strcmp(argv[i], "--lower") == 0) { + count += intrcat(chars, 97, 122); // English lower case + } else if(strcmp(argv[i], "-n") == 0 || strcmp(argv[i], "--numerals") == 0) { + count += intrcat(chars, 48, 57); // English numerals + } else if(strcmp(argv[i], "-y") == 0 || strcmp(argv[i], "--symbols") == 0) { + count += intrcat(chars, 33, 47); // English symbols ! - / + count += intrcat(chars, 58, 64); // English symbols : - @ + count += intrcat(chars, 91, 96); // English symbols [ - ` + count += intrcat(chars, 123, 126); // English symbols { - ~ + } else if(strcmp(argv[i], "-i") == 0 || strcmp(argv[i], "--i18n") == 0) { + count += populate_intl_arr(chars); + } else if(strcmp(argv[i], "-h") == 0 || strcmp(argv[i], "--help") == 0) { + usage(); + return 0; + } else { + // If we reach this block, the user specified a custom length (or + // fatfingered something). Test for ability to convert from str to int + // and set length if possible. + if(atoi(argv[i]) == 0) { + printf("Invalid length \"%s\"\n", argv[i]); + return 1; + } else { + len = atoi(argv[i]); + } + } + i++; } - passlen = argv[1]; - - // Store supported chars here! - count = populate_intl_arr(chars); - //printf("%d international chars for use\n", count); - //print_intl_arr(chars); - //return 0; + // Ensure at least one character set was specified + if(chars[0] == '\0') { + printf("Must specify at least one character set\n"); + return 0; + } + // Get the random data seed clock_gettime(CLOCK_REALTIME, &ts); seed = ts.tv_sec + ts.tv_nsec; srand((unsigned)seed); - len = atoi(passlen); while(len > 0) { int r = rand() % count; printf("%lc", chars[r]); |