aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/supplemental/util/CMakeLists.txt8
-rw-r--r--src/supplemental/util/options.c124
-rw-r--r--src/supplemental/util/options.h48
-rw-r--r--src/supplemental/util/platform.h6
4 files changed, 179 insertions, 7 deletions
diff --git a/src/supplemental/util/CMakeLists.txt b/src/supplemental/util/CMakeLists.txt
index 443473d6..f94e2b45 100644
--- a/src/supplemental/util/CMakeLists.txt
+++ b/src/supplemental/util/CMakeLists.txt
@@ -8,8 +8,8 @@
# found online at https://opensource.org/licenses/MIT.
#
-set(SUPP_PLATFORM_SOURCES supplemental/util/platform.c)
-set(SUPP_PLATFORM_HEADERS supplemental/util/platform.h)
+set(SUPP_UTIL_SOURCES supplemental/util/options.c supplemental/util/platform.c)
+set(SUPP_UTIL_HEADERS supplemental/util/options.h supplemental/util/platform.h)
-set(NNG_SOURCES ${NNG_SOURCES} ${SUPP_PLATFORM_SOURCES} PARENT_SCOPE)
-set(NNG_HEADERS ${NNG_HEADERS} ${SUPP_PLATFORM_HEADERS} PARENT_SCOPE)
+set(NNG_SOURCES ${NNG_SOURCES} ${SUPP_UTIL_SOURCES} PARENT_SCOPE)
+set(NNG_HEADERS ${NNG_HEADERS} ${SUPP_UTIL_HEADERS} PARENT_SCOPE)
diff --git a/src/supplemental/util/options.c b/src/supplemental/util/options.c
new file mode 100644
index 00000000..d8f78deb
--- /dev/null
+++ b/src/supplemental/util/options.c
@@ -0,0 +1,124 @@
+//
+// Copyright 2018 Staysail Systems, Inc. <info@staysail.tech>
+// Copyright 2018 Capitar IT Group BV <info@capitar.com>
+//
+// This software is supplied under the terms of the MIT License, a
+// copy of which should be located in the distribution where this
+// file was obtained (LICENSE.txt). A copy of the license may also be
+// found online at https://opensource.org/licenses/MIT.
+//
+
+#include <stdlib.h>
+#include <string.h>
+
+#include "core/nng_impl.h"
+#include "supplemental/util/options.h"
+
+// Call with optidx set to 1 to start parsing.
+int
+nng_opts_parse(int argc, const char **argv, const nng_optspec *opts, int *val,
+ const char **optarg, int *optidx)
+{
+ const nng_optspec *opt;
+ int matches;
+ bool shortopt;
+ size_t l;
+ const char * arg = argv[*optidx];
+ int i;
+
+ if ((i = *optidx) >= argc) {
+ return (-1);
+ }
+
+ if (arg[0] != '-') {
+ return (-1);
+ }
+ if (arg[1] == '\0') {
+ *optidx = i + 1;
+ return (-1);
+ }
+
+ if ((arg[0] == '-') && (arg[1] == '-')) {
+ arg += 2;
+ shortopt = false;
+ for (l = 0; arg[l] != '\0'; l++) {
+ if ((arg[l] == '=') || (arg[l] == ':')) {
+ break;
+ }
+ }
+ } else {
+ arg++;
+ shortopt = true;
+ l = 1;
+ }
+
+ matches = 0;
+ opt = NULL;
+
+ for (int x = 0; opts[x].o_val != 0; x++) {
+
+ if (shortopt) {
+ if (arg[0] == opts[x].o_short) {
+ matches = 1;
+ opt = &opts[x];
+ break;
+ }
+ continue;
+ }
+
+ if ((opts[x].o_name == NULL) ||
+ (strncmp(arg, opts[x].o_name, l) != 0)) {
+ continue;
+ }
+ matches++;
+ opt = &opts[x];
+
+ if (strlen(opts[x].o_name) == l) {
+ // Perfect match.
+ matches = 1;
+ break;
+ }
+ }
+
+ switch (matches) {
+ case 1:
+ // Exact match
+ break;
+ case 0:
+ // No such option
+ return (NNG_EINVAL);
+ break;
+ default:
+ // Ambiguous (not match)
+ return (NNG_EINVAL);
+ break;
+ }
+
+ if (!opt->o_arg) {
+ // No option clustering for short options yet.
+ if (arg[l] != '\0') {
+ return (NNG_EINVAL);
+ }
+ *val = opt->o_val;
+ *optidx = i + 1;
+ return (0);
+ }
+
+ if (arg[l] != '\0') {
+ if (shortopt) {
+ *optarg = arg + l;
+ } else {
+ *optarg = arg + l + 1;
+ }
+ } else {
+ i++;
+ if (i >= argc) {
+ return (NNG_EINVAL);
+ }
+ *optarg = argv[i];
+ }
+ *optidx = ++i;
+ *val = opt->o_val;
+
+ return (0);
+}
diff --git a/src/supplemental/util/options.h b/src/supplemental/util/options.h
new file mode 100644
index 00000000..02b3a9d4
--- /dev/null
+++ b/src/supplemental/util/options.h
@@ -0,0 +1,48 @@
+//
+// Copyright 2018 Staysail Systems, Inc. <info@staysail.tech>
+// Copyright 2018 Capitar IT Group BV <info@capitar.com>
+//
+// This software is supplied under the terms of the MIT License, a
+// copy of which should be located in the distribution where this
+// file was obtained (LICENSE.txt). A copy of the license may also be
+// found online at https://opensource.org/licenses/MIT.
+//
+
+#ifndef NNG_SUPPLEMENTAL_UTIL_OPTIONS_H
+#define NNG_SUPPLEMENTAL_UTIL_OPTIONS_H
+
+#include <stdbool.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+// This is a relatively simple "options parsing" library, used to
+// parse command line options. We would use getopt(3), but there are
+// two problems with getopt(3). First, it isn't available on all
+// platforms (especially Win32), and second, it doesn't support long
+// options. We *exclusively* support long options. POSIX style
+// short option clustering is *NOT* supported.
+
+struct nng_optspec {
+ const char *o_name; // Long style name (may be NULL for short only)
+ int o_short; // Short option (no clustering!)
+ int o_val; // Value stored on a good parse (>0)
+ bool o_arg; // Option takes an argument if true
+};
+
+typedef struct nng_optspec nng_optspec;
+
+// Call with *optidx set to 1 to start parsing for a standard program.
+// The val will store the value of the matched "o_val", optarg will be
+// set to match the option string, and optidx will be increment appropriately.
+// Returns -1 when the end of options is reached, 0 on success, or
+// NNG_EINVAL if the option parse is invalid for any reason.
+NNG_DECL int nng_opts_parse(int argc, const char **argv,
+ const nng_optspec *opts, int *val, const char **optarg, int *optidx);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif // NNG_SUPPLEMENTAL_UTIL_OPTIONS_H \ No newline at end of file
diff --git a/src/supplemental/util/platform.h b/src/supplemental/util/platform.h
index 1383fe15..fd287713 100644
--- a/src/supplemental/util/platform.h
+++ b/src/supplemental/util/platform.h
@@ -20,13 +20,13 @@
// APIs or Windows APIs, then by all means please feel free to simply
// ignore this.
+#include <stddef.h>
+#include <stdint.h>
+
#ifdef __cplusplus
extern "C" {
#endif
-#include <stddef.h>
-#include <stdint.h>
-
// nng_time represents an absolute time since some arbitrary point in the
// past, measured in milliseconds. The values are always positive.
typedef uint64_t nng_time;