From 7880fd95fb6bd9a938e86c3fb6743d5c9fd9aecb Mon Sep 17 00:00:00 2001 From: fall-leaf Date: Thu, 3 Aug 2023 02:13:24 +0300 Subject: [PATCH] Improved credentials parsing scalability --- credentials.txt | 2 +- include/parse.h | 4 ++-- src/parse.c | 54 +++++++++++++++++++++++++++++++++++++++++++----------- 3 files changed, 46 insertions(+), 14 deletions(-) diff --git a/credentials.txt b/credentials.txt index 575c4db..6efad6d 100644 --- a/credentials.txt +++ b/credentials.txt @@ -1 +1 @@ -probotic \ No newline at end of file +username=probotic \ No newline at end of file diff --git a/include/parse.h b/include/parse.h index 65d6521..67997ea 100644 --- a/include/parse.h +++ b/include/parse.h @@ -2,8 +2,8 @@ typedef struct { - char * username; - char * password; + char * username; + char * password; } creds_t; DELC void parse_command(char * cmd); diff --git a/src/parse.c b/src/parse.c index 2cf8dee..94d921a 100644 --- a/src/parse.c +++ b/src/parse.c @@ -24,6 +24,20 @@ #include "parse.h" #include "error.h" +#define PARAMS_COUNT 2 + +enum cred_param_ids_e +{ + USERNAME, + PASSWORD +}; + +/* TODO: move = to the handler */ +char const * cred_param_names_g[] = { + "username=", + "password=" +}; + DELC void parse_command(char * cmd) { @@ -71,21 +85,39 @@ parse_creds(creds_t * creds, if (stream == NULL) { PERROR(PROGN); } - if (getline(&(creds->username), &nread, stream) < 1) + char * values[PARAMS_COUNT]; + memset(values, 0, sizeof(char *) * PARAMS_COUNT); + + char * line = NULL; + while (getline(&line, &nread, stream) > 0) { - ERRMSG("Cannot get username"); - goto fail; + for (size_t i = 0; i < PARAMS_COUNT; i++) + { + size_t param_len = strlen(cred_param_names_g[i]); + + if (!strncmp(cred_param_names_g[i], line, param_len)) + { + /* Starts with the current parameter specifier */ + char const * val = line + param_len; + size_t val_len = strlen(val); + /* Duplicates and gets rid of a newline */ + values[i] = strndup(val, val[val_len - 1] == '\n' ? val_len - 1 : val_len); + break; + } + } + + free(line); + line = NULL; + nread = 0; } + creds->username = values[USERNAME]; + creds->password = values[PASSWORD]; - if (getline(&(creds->password), &nread, stream) < 1) + /* Check empty but required paramters */ + if (!creds->username) { - /* Bot credentials file with an empty password is a valid case. - * Considering irc_connect api the pointer to the password should be NULL in that case. - */ - - /* Theoretically it can be allocated with an empty string */ - free(creds->password); - creds->password = NULL; + ERRMSG("Could not parse bot login"); + goto fail; } fclose(stream);