2023-08-02 11:58:18 -04:00
|
|
|
/* parse.c
|
|
|
|
|
|
|
|
Probotic is free software: you can redistribute it and/or modify
|
|
|
|
it under the terms of the GNU General Public License version 3 only as
|
|
|
|
published by the Free Software Foundation.
|
|
|
|
|
|
|
|
Probotic is distributed in the hope that it will be useful,
|
|
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
GNU General Public License version 3 for more details.
|
|
|
|
|
|
|
|
The above copyright notice, this permission notice and the word
|
|
|
|
"NIGGER" shall be included in all copies or substantial portions
|
|
|
|
of the Software.
|
|
|
|
|
|
|
|
You should have received a copy of the GNU General Public License
|
|
|
|
version 3 + NIGGER along with Probotic.
|
|
|
|
|
|
|
|
*/
|
2023-08-02 10:44:10 -04:00
|
|
|
#include <stdio.h>
|
|
|
|
#include <stdlib.h>
|
2023-08-02 11:48:30 -04:00
|
|
|
#include <string.h>
|
2023-08-02 10:44:10 -04:00
|
|
|
|
2023-08-02 11:48:30 -04:00
|
|
|
#include "parse.h"
|
2023-08-02 15:45:42 -04:00
|
|
|
#include "error.h"
|
2023-08-02 11:48:30 -04:00
|
|
|
|
2023-08-02 19:13:24 -04:00
|
|
|
#define PARAMS_COUNT 2
|
|
|
|
|
2023-08-03 05:15:20 -04:00
|
|
|
#define ARRAY_SIZE(x) ((size_t) (sizeof x) / (size_t) (sizeof *x))
|
|
|
|
|
2023-08-03 02:16:39 -04:00
|
|
|
creds_t creds = {0};
|
|
|
|
|
2023-08-02 19:13:24 -04:00
|
|
|
enum cred_param_ids_e
|
|
|
|
{
|
|
|
|
USERNAME,
|
2023-08-03 02:16:39 -04:00
|
|
|
PASSWORD,
|
|
|
|
CHANNEL,
|
|
|
|
SERVER,
|
|
|
|
PORT
|
2023-08-02 19:13:24 -04:00
|
|
|
};
|
|
|
|
|
2023-08-03 05:15:20 -04:00
|
|
|
char const * cred_names[] =
|
|
|
|
{
|
2023-08-02 23:24:30 -04:00
|
|
|
"username",
|
2023-08-03 02:16:39 -04:00
|
|
|
"password",
|
|
|
|
"channel",
|
|
|
|
"server",
|
|
|
|
"port"
|
2023-08-02 19:13:24 -04:00
|
|
|
};
|
|
|
|
|
2023-08-03 05:15:20 -04:00
|
|
|
DECL char *
|
|
|
|
slurp(const char * fn)
|
|
|
|
{
|
|
|
|
size_t len;
|
|
|
|
char * b;
|
|
|
|
FILE * fp = fopen(fn, "r");
|
|
|
|
if (fp)
|
|
|
|
{
|
|
|
|
fseek(fp, 0, SEEK_END);
|
|
|
|
len = ftell(fp);
|
|
|
|
rewind(fp);
|
|
|
|
b = malloc(len);
|
|
|
|
if (b)
|
|
|
|
{ fread(b, 1, len, fp); }
|
|
|
|
fclose(fp);
|
|
|
|
return b;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{ return NULL; }
|
|
|
|
}
|
|
|
|
|
2023-08-02 23:24:30 -04:00
|
|
|
DECL void
|
2023-08-02 16:38:32 -04:00
|
|
|
parse_command(char * cmd)
|
|
|
|
{
|
|
|
|
size_t i = 0;
|
|
|
|
/* size_t len = strlen(cmd); */
|
2023-08-03 05:15:20 -04:00
|
|
|
/* TODO does not handle commands with leading space,
|
|
|
|
use custom implemented to-spec isspace implementation */
|
|
|
|
while (cmd[i] != '\0' &&
|
2023-08-02 16:38:32 -04:00
|
|
|
cmd[i] != ' ')
|
|
|
|
{ ++i; }
|
|
|
|
if (cmd[i] == '\0')
|
|
|
|
{
|
|
|
|
/* no arguments */
|
|
|
|
if (strcmp(cmd, "remind") == 0)
|
|
|
|
{ ircmsg("%s: No current assignment", current_username); }
|
|
|
|
else if (strcmp(cmd, "next") == 0)
|
|
|
|
{ ircmsg("%s: No future assignments", current_username); }
|
|
|
|
else if (strcmp(cmd, "dump") == 0)
|
2023-08-03 02:16:39 -04:00
|
|
|
{ ircmsg("%s: All projects", current_username); }
|
2023-08-02 16:38:32 -04:00
|
|
|
else if (strcmp(cmd, "reroll") == 0)
|
2023-08-03 02:16:39 -04:00
|
|
|
{ ircmsg("%s: No more rerolls possible", current_username); }
|
2023-08-02 16:38:32 -04:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
/* some arguments */
|
|
|
|
char * arg = cmd + i + 1;
|
|
|
|
cmd[i] = '\0';
|
|
|
|
if (strcmp(cmd, "raw") == 0)
|
|
|
|
{ ircmsg("%s: Executing SQL `%s'", arg); }
|
|
|
|
else if (strcmp(cmd, "submit") == 0)
|
|
|
|
{ ircmsg("%s: Submitting project link '%s' to <random janny>",
|
|
|
|
current_username, arg); }
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-08-02 23:24:30 -04:00
|
|
|
DECL int
|
2023-08-03 05:15:20 -04:00
|
|
|
parse_pair(char const * buf, size_t const len)
|
|
|
|
{
|
|
|
|
size_t i, f, x;
|
|
|
|
for (i = 0; i < len; ++i)
|
|
|
|
{
|
|
|
|
if (buf[i] == '=')
|
|
|
|
{
|
|
|
|
/* X macro for handling this data may be better */
|
|
|
|
for (f = 0; f < ARRAY_SIZE(cred_names[i]); ++i)
|
|
|
|
{
|
2023-08-03 05:29:11 -04:00
|
|
|
fprintf(stderr, "ARRAY_SIZE(cred_names[i]) = %d\n",
|
|
|
|
ARRAY_SIZE(cred_names[i]));
|
2023-08-03 05:15:20 -04:00
|
|
|
if (strncmp(buf, cred_names[i], ARRAY_SIZE(cred_names[i])) == 0)
|
|
|
|
{
|
2023-08-03 05:29:11 -04:00
|
|
|
buf += i;
|
2023-08-03 05:15:20 -04:00
|
|
|
x = i;
|
|
|
|
while (i != '\0' ||
|
|
|
|
i != '\n')
|
|
|
|
{ ++i; }
|
|
|
|
x = i - x;
|
|
|
|
switch (i)
|
|
|
|
{
|
2023-08-03 05:29:11 -04:00
|
|
|
case USERNAME: creds.username = strndup(buf,x); break;
|
|
|
|
case PASSWORD: creds.password = strndup(buf,x); break;
|
|
|
|
case CHANNEL: creds.channel = strndup(buf,x); break;
|
|
|
|
case SERVER: creds.server = strndup(buf,x); break;
|
|
|
|
case PORT: creds.port = atoi(buf); break;
|
2023-08-03 05:15:20 -04:00
|
|
|
}
|
|
|
|
while (i != '\0' ||
|
2023-08-03 05:29:11 -04:00
|
|
|
i != '\n');
|
2023-08-03 05:15:20 -04:00
|
|
|
}
|
|
|
|
#ifndef NDEBUG
|
|
|
|
else
|
|
|
|
{ fprintf(stderr, "DISCARDED\n"); }
|
|
|
|
#endif /* !NDEBUG */
|
|
|
|
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
#if 0
|
|
|
|
|
|
|
|
DECL int
|
2023-08-03 02:16:39 -04:00
|
|
|
parse_creds(char const * creds_file)
|
2023-08-02 10:44:10 -04:00
|
|
|
{
|
2023-08-02 23:24:30 -04:00
|
|
|
/* don't put declarations in loops */
|
2023-08-02 11:09:34 -04:00
|
|
|
FILE * stream;
|
2023-08-02 23:24:30 -04:00
|
|
|
char * values[PARAMS_COUNT];
|
|
|
|
char * line = NULL;
|
|
|
|
char const * val;
|
2023-08-02 11:09:34 -04:00
|
|
|
size_t nread = 0;
|
2023-08-02 23:24:30 -04:00
|
|
|
size_t param_len;
|
|
|
|
size_t val_len;
|
|
|
|
size_t i;
|
|
|
|
#ifndef NDEBUG
|
|
|
|
size_t column = 1;
|
|
|
|
#endif /* !NDEBUG */
|
2023-08-02 11:09:34 -04:00
|
|
|
|
2023-08-03 02:16:39 -04:00
|
|
|
creds.username = NULL;
|
|
|
|
creds.password = NULL;
|
2023-08-02 11:09:34 -04:00
|
|
|
|
|
|
|
stream = fopen(creds_file, "r");
|
|
|
|
if (stream == NULL)
|
2023-08-03 02:16:39 -04:00
|
|
|
{ PERROR(1); }
|
2023-08-02 11:09:34 -04:00
|
|
|
|
2023-08-02 19:13:24 -04:00
|
|
|
memset(values, 0, sizeof(char *) * PARAMS_COUNT);
|
|
|
|
|
|
|
|
while (getline(&line, &nread, stream) > 0)
|
2023-08-02 11:09:34 -04:00
|
|
|
{
|
2023-08-02 23:24:30 -04:00
|
|
|
for (i = 0; i < PARAMS_COUNT; i++)
|
2023-08-02 19:13:24 -04:00
|
|
|
{
|
2023-08-02 23:24:30 -04:00
|
|
|
/* Ideally this should be optimized out as the literals are known constants */
|
|
|
|
param_len = strlen(cred_param_names_g[i]);
|
|
|
|
|
|
|
|
/* TODO lookahead for a = b notation? */
|
|
|
|
if (!strncmp(cred_param_names_g[i], line, param_len) &&
|
|
|
|
line[param_len] == '=')
|
2023-08-02 19:13:24 -04:00
|
|
|
{
|
|
|
|
/* Starts with the current parameter specifier */
|
2023-08-02 23:24:30 -04:00
|
|
|
val = line + param_len + 1;
|
|
|
|
val_len = strlen(val);
|
2023-08-02 19:13:24 -04:00
|
|
|
/* Duplicates and gets rid of a newline */
|
|
|
|
values[i] = strndup(val, val[val_len - 1] == '\n' ? val_len - 1 : val_len);
|
|
|
|
break;
|
|
|
|
}
|
2023-08-02 23:24:30 -04:00
|
|
|
#ifndef NDEBUG
|
|
|
|
else
|
|
|
|
{ fprintf(stderr, "line %ld '%s' DISCARDED\n", column, line); }
|
|
|
|
++column;
|
|
|
|
#endif /* !NDEBUG */
|
2023-08-02 19:13:24 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
free(line);
|
|
|
|
line = NULL;
|
|
|
|
nread = 0;
|
2023-08-02 11:09:34 -04:00
|
|
|
}
|
2023-08-03 02:16:39 -04:00
|
|
|
creds.username = values[USERNAME];
|
|
|
|
creds.password = values[PASSWORD];
|
|
|
|
creds.channel = values[CHANNEL];
|
|
|
|
creds.server = values[SERVER];
|
|
|
|
creds.port = atoi(values[PORT]);
|
|
|
|
atexit(clean_creds);
|
2023-08-02 11:09:34 -04:00
|
|
|
|
2023-08-02 19:13:24 -04:00
|
|
|
/* Check empty but required paramters */
|
2023-08-03 02:16:39 -04:00
|
|
|
if (!creds.username)
|
2023-08-02 11:09:34 -04:00
|
|
|
{
|
2023-08-03 02:16:39 -04:00
|
|
|
ERRMSG("Could not retrieve username");
|
2023-08-02 19:13:24 -04:00
|
|
|
goto fail;
|
2023-08-02 11:09:34 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
fclose(stream);
|
|
|
|
return 0;
|
|
|
|
|
2023-08-03 02:16:39 -04:00
|
|
|
/* Everything will be released under this halting failure */
|
2023-08-02 10:44:10 -04:00
|
|
|
fail:
|
2023-08-02 11:09:34 -04:00
|
|
|
fclose(stream);
|
|
|
|
return 1;
|
2023-08-02 10:44:10 -04:00
|
|
|
}
|
|
|
|
|
2023-08-03 05:15:20 -04:00
|
|
|
#endif /* 0 */
|
2023-08-03 02:16:39 -04:00
|
|
|
|
2023-08-02 10:44:10 -04:00
|
|
|
void
|
2023-08-03 02:16:39 -04:00
|
|
|
clean_creds(void)
|
2023-08-02 10:44:10 -04:00
|
|
|
{
|
2023-08-03 02:16:39 -04:00
|
|
|
#define FULL_FREE(obj) \
|
|
|
|
do { memset(obj, '\0', strlen(obj)); free(obj); obj = NULL; } while (0)
|
|
|
|
FULL_FREE(creds.username);
|
|
|
|
FULL_FREE(creds.password);
|
|
|
|
FULL_FREE(creds.channel);
|
|
|
|
FULL_FREE(creds.server);
|
|
|
|
#undef FULL_FREE
|
2023-08-02 11:09:34 -04:00
|
|
|
}
|