Initial getopt in the project

This commit is contained in:
2019-01-06 01:42:05 +02:00
parent 0382ead79b
commit 31a9156add
3 changed files with 119 additions and 78 deletions

View File

@@ -25,12 +25,13 @@
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include <unistd.h> #include <unistd.h>
#include <libgen.h>
#include "log.h" #include "log.h"
#include "confparser.h" #include "confparser.h"
#include "enum_functions.h" #include "enum_functions.h"
static int test_conf_perms(void); static int test_conf_perms(char *config);
static int test_conf_syntax(void); static int test_conf_syntax(char *config);
struct conf_table conf = { struct conf_table conf = {
0, /* isvalid initial state */ 0, /* isvalid initial state */
@@ -155,11 +156,44 @@ static int fopen_and_mkdir(const char *dir)
} }
static int test_conf_perms(void) static int test_conf_perms(char *config)
{ {
struct stat s; struct stat s;
char confresult[128]; char confresult[128];
int err = stat("/etc/rmps", &s); char *config_copy = strdup(config);
int err = stat(config, &s);
if (err == -1) {
if (errno == ENOENT) {
enumtostr(confresult, CONF_MISSING);
log(ERROR, confresult);
return 1;
}
} else {
if (!S_ISREG(s.st_mode)) {
enumtostr(confresult, CONF_NOTFILE);
log(ERROR, confresult);
return 1;
}
if (!(0400 & s.st_mode)) {
enumtostr(confresult, CONF_PERM);
log(ERROR, confresult);
return 1;
}
if (s.st_uid != 0) {
enumtostr(confresult, CONF_FILE_UID_INSECURE);
log(WARNING, confresult);
} else if (s.st_gid != 0) {
enumtostr(confresult, CONF_FILE_GID_INSECURE);
log(WARNING, confresult);
} else if ((0004 & s.st_mode) ||
(0002 & s.st_mode)) {
enumtostr(confresult, CONF_FILE_PERM_INSECURE);
log(WARNING, confresult);
}
}
err = stat(dirname(config_copy), &s);
if (err == -1) { if (err == -1) {
if (errno == ENOENT) { if (errno == ENOENT) {
@@ -192,48 +226,17 @@ static int test_conf_perms(void)
} }
} }
err = stat("/etc/rmps/rmps.conf", &s);
if (err == -1) {
if (errno == ENOENT) {
enumtostr(confresult, CONF_MISSING);
log(ERROR, confresult);
return 1;
}
} else {
if (!S_ISREG(s.st_mode)) {
enumtostr(confresult, CONF_NOTFILE);
log(ERROR, confresult);
return 1;
}
if (!(0400 & s.st_mode)) {
enumtostr(confresult, CONF_PERM);
log(ERROR, confresult);
return 1;
}
if (s.st_uid != 0) {
enumtostr(confresult, CONF_FILE_UID_INSECURE);
log(WARNING, confresult);
} else if (s.st_gid != 0) {
enumtostr(confresult, CONF_FILE_GID_INSECURE);
log(WARNING, confresult);
} else if ((0004 & s.st_mode) ||
(0002 & s.st_mode)) {
enumtostr(confresult, CONF_FILE_PERM_INSECURE);
log(WARNING, confresult);
}
}
return 0; /* conf is readable */ return 0; /* conf is readable */
} }
static int test_conf_syntax(void) static int test_conf_syntax(char *config)
{ {
int i, j = 0, ok = 1, failed = 0; int i, j = 0, ok = 1, failed = 0;
char buf[CFGLINESIZE], *tmp; char buf[CFGLINESIZE], *tmp;
FILE *fp = fopen("/etc/rmps/rmps.conf", "r"); FILE *fp = fopen(config, "r");
if (fp == NULL) { if (fp == NULL) {
log(ERROR, "Failed to read /etc/rmps/rmps.conf"); log(ERROR, "Failed to read %s", config);
return 1; return 1;
} }
@@ -252,8 +255,7 @@ static int test_conf_syntax(void)
*tmp = '\0'; *tmp = '\0';
else { else {
log(ERROR, log(ERROR,
"Bad entry in /etc/rmps/rmps.conf, line %d: %s", "Bad entry in %s, line %d: %s", config, j, buf);
j, buf);
ok = 0; ok = 0;
failed = 1; failed = 1;
continue; continue;
@@ -438,15 +440,15 @@ static int test_conf_syntax(void)
return 0; return 0;
} }
int confparse(void) int confparse(char *config)
{ {
int result; int result;
result = test_conf_perms(); result = test_conf_perms(config);
if (result) if (result)
return 1; /* Bad conf perms */ return 1; /* Bad conf perms */
result = test_conf_syntax(); result = test_conf_syntax(config);
if (result != 0) if (result != 0)
return 1; /* Bad conf syntax */ return 1; /* Bad conf syntax */
return 0; /* seems legit */ return 0; /* seems legit */

View File

@@ -66,10 +66,9 @@ struct conf_table {
}; };
extern struct conf_table conf; extern struct conf_table conf;
extern int confparse(void); extern int confparse(char *);
extern void confexport(void); extern void confexport(void);
extern const char *conf_db_pass(void); extern const char *conf_db_pass(void);
extern const char *conf_db_hostname(void); extern const char *conf_db_hostname(void);
#endif /* CONFPARSER_H */ #endif /* CONFPARSER_H */

View File

@@ -25,61 +25,101 @@
#include <errno.h> #include <errno.h>
#include <signal.h> #include <signal.h>
#include <unistd.h> #include <unistd.h>
#include <getopt.h>
#include "confparser.h" #include "confparser.h"
#include "log.h" #include "log.h"
#include "rmps.h" #include "rmps.h"
static void usage(char *argv) static void usage(char *argv)
{ {
log(ERROR, fprintf(stderr, "Usage:\n%s TASK [-c CONFIG] [-d]\n\n"
"Usage:\n%s start|stop|restart [--daemonize=yes|no]", argv); "Tasks:\n"
"\t--start\t\tStart the RMPS server.\n"
"\t--stop\t\tStop the RMPS server.\n"
"\t--restart\tRestart the RMPS server.\n\n"
"Options:\n"
"\t-c, --config\n"
"\t\tSpecify the configuration file path. Default is set "
"to /etc/rmps/rmps.conf\n"
"\t-d, --daemonize\n"
"\t\tSetting this will make the parent fork in the "
"backgroud. Default is not to fork.\n"
"\t-h, --help\n"
"\t\tShow this message.\n", argv);
} }
int main(int argc, char *argv[]) int main(int argc, char *argv[])
{ {
int fork_flag = 1, task; enum tasks {
START = 1,
STOP,
RESTART
};
static int task;
const char opts_short[] = "dc:h";
static struct option opts_long[] =
{
{"start", no_argument, &task, START},
{"stop", no_argument, &task, STOP},
{"restart", no_argument, &task, RESTART},
{"daemonize", no_argument, 0, 'd'},
{"config", required_argument, 0, 'c'},
{"help", no_argument, 0, 'h'},
{NULL, 0, NULL, 0}
};
int opt = 0, opt_index = 0, fork_flag = 0;
char *config = NULL;
if (argc < 2 || argc > 3) { while ((opt = getopt_long(argc, argv, opts_short, opts_long, &opt_index)) != -1) {
usage(argv[0]); switch (opt) {
exit(EXIT_FAILURE); case 0:
} if (opts_long[opt_index].flag != 0)
break;
if (!strcmp(argv[1], "start")) log(INFO, "option %s", opts_long[opt_index].name);
task = 1; if (optarg)
else if (!strcmp(argv[1], "stop")) log(INFO, "with arg %s\n", optarg);
task = 2; break;
else if (!strcmp(argv[1], "restart")) case 'd':
task = 3;
else {
usage(argv[0]);
exit(EXIT_FAILURE);
}
if (argc == 3) {
if (!strcmp("--daemonize=yes", argv[2]))
fork_flag = 1; fork_flag = 1;
else if (!strcmp("--daemonize=no", argv[2])) break;
fork_flag = 0; case 'c':
else { config = optarg;
break;
case 'h':
usage(argv[0]);
exit(EXIT_SUCCESS);
default:
usage(argv[0]); usage(argv[0]);
exit(EXIT_FAILURE); exit(EXIT_FAILURE);
} }
} }
if (confparse() != 0) {
if (!config) {
char path[] = "/etc/rmps/rmps.conf";
int path_size = strlen(path) + 1;
config = calloc(sizeof(char), path_size);
if (config == NULL) {
log(ERROR, "malloc() failed for config");
exit(EXIT_FAILURE);
}
memcpy(config, path, path_size);
}
if (confparse(config) != 0) {
log(ERROR, "Failed to parse the conf!"); log(ERROR, "Failed to parse the conf!");
exit(EXIT_FAILURE); exit(EXIT_FAILURE);
} }
log(VERBOSE, "Conf parser finished successfully"); log(VERBOSE, "Conf parser finished successfully");
//confexport(); //confexport();
if (task == 2 || task == 3) { if (task == STOP|| task == RESTART) {
char buf[10]; char buf[10];
int pid; int pid;
FILE *fp; FILE *fp;
if (task == 2) if (task == STOP)
log(VERBOSE, "We got a stop signal!"); log(VERBOSE, "We got a stop signal!");
else if (task == 3) else if (task == RESTART)
log(VERBOSE, "We got a restart signal!"); log(VERBOSE, "We got a restart signal!");
fp = fopen(conf.rmps.pidfile, "r"); fp = fopen(conf.rmps.pidfile, "r");
@@ -99,7 +139,7 @@ int main(int argc, char *argv[])
log(ERROR, "Permission denied to read PID. Exiting!"); log(ERROR, "Permission denied to read PID. Exiting!");
exit(EXIT_FAILURE); exit(EXIT_FAILURE);
case ENOENT: case ENOENT:
if (task == 2) if (task == STOP)
exit(EXIT_FAILURE); exit(EXIT_FAILURE);
break; break;
default: default:
@@ -109,7 +149,7 @@ int main(int argc, char *argv[])
exit(EXIT_FAILURE); exit(EXIT_FAILURE);
} }
} }
if (task == 1 || task == 3) if (task == START || task == RESTART)
launch_rmps(&conf, fork_flag); launch_rmps(&conf, fork_flag);
return 0; return 0;