aboutsummaryrefslogtreecommitdiff
path: root/src/options.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/options.c')
-rw-r--r--src/options.c40
1 files changed, 26 insertions, 14 deletions
diff --git a/src/options.c b/src/options.c
index 8d2248a..b9cd4f1 100644
--- a/src/options.c
+++ b/src/options.c
@@ -39,6 +39,7 @@ struct opt {
static struct opt options[OPT_MAX+1] = {
OPT_STR("./potd.log", 0, "log", "short help", "help"),
OPT_STR(NULL, 0, "log-level", "short help", "help"),
+ OPT_NOARG("daemon", "short help", "help"),
OPT(OT_INVALID, .ll = 0, 0, NULL, NULL, NULL)
};
@@ -50,8 +51,11 @@ static int setopt(struct opt *o, const char *optarg)
{
char *endptr = NULL;
+ assert(o && o->type != OT_INVALID);
if (o->used && !o->is_list)
return 1;
+ if (!optarg || o->type == OT_NOARG)
+ goto noarg;
switch (o->type) {
case OT_L:
@@ -71,37 +75,44 @@ static int setopt(struct opt *o, const char *optarg)
if (endptr && *endptr != 0)
return 1;
+noarg:
+ o->used = 1;
+
return 0;
}
int options_cmdline(int argc, char **argv)
{
- int i, option, option_index;
+ int rc, i, option, option_index;
struct option *o = (struct option *) calloc(OPT_MAX+1, sizeof *o);
assert(o);
for (i = 0; i < OPT_MAX; ++i) {
o[i].name = options[i].arg_name;
- o[i].has_arg =
- (options[i].type == OT_NOARG ? no_argument : optional_argument);
+ if (options[i].def_value.ll)
+ o[i].has_arg = optional_argument;
+ else
+ o[i].has_arg =
+ (options[i].type == OT_NOARG ? no_argument : required_argument);
}
+ rc = 0;
while (1) {
option_index = -1;
option = getopt_long_only(argc, argv, "", o, &option_index);
- if (option == -1 || option_index == -1)
+
+ if (option_index == -1 && option != -1) {
+ rc = 1;
+ continue;
+ }
+ if (option == -1)
break;
if (!option) {
- options[option_index].used = 1;
-
- if (optarg && options[option_index].type != OT_INVALID &&
- options[option_index].type != OT_NOARG)
- {
- if (setopt(&options[option_index], optarg)) {
- goto error;
- }
- } else goto error;
+ if (setopt(&options[option_index], optarg)) {
+ rc = 1;
+ goto error;
+ }
} else {
fprintf(stderr, "%s: unknown option '%c' [0x%X]\n",
argv[0], option, option);
@@ -111,7 +122,7 @@ int options_cmdline(int argc, char **argv)
error:
free(o);
- return 0;
+ return rc;
}
int getopt_used(opt_name on)
@@ -129,6 +140,7 @@ getopt_str(opt_name on)
str = options[on].value.str_dup;
if (!str)
str = options[on].def_value.str_dup;
+ assert(str);
return str;
}