YAZ options: special -- ends options
authorAdam Dickmeiss <adam@indexdata.dk>
Wed, 21 Sep 2011 12:34:28 +0000 (14:34 +0200)
committerAdam Dickmeiss <adam@indexdata.dk>
Wed, 21 Sep 2011 12:34:28 +0000 (14:34 +0200)
Add test of YAZ options

include/yaz/options.h
src/options.c
test/Makefile.am
test/test_options.c [new file with mode: 0644]

index a822b47..b9d0231 100644 (file)
@@ -55,6 +55,9 @@ YAZ_BEGIN_CDECL
     The first char is what is returned when met (single char option char).
     The second is zero ore more long option values (synonum for single char)
     If colon is appended, it means the option takes an argument.
     The first char is what is returned when met (single char option char).
     The second is zero ore more long option values (synonum for single char)
     If colon is appended, it means the option takes an argument.
+    If argv includes empty long option (--) that means "end of options" :
+    all argv data following that is considered non-options .. (0 returned
+    for each).
 */
 YAZ_EXPORT int options(const char *desc, char **argv, int argc, char **arg);
 
 */
 YAZ_EXPORT int options(const char *desc, char **argv, int argc, char **arg);
 
index d0811a9..4cb53d1 100644 (file)
@@ -16,6 +16,7 @@
 
 static int arg_no = 1;
 static size_t arg_off = 0;
 
 static int arg_no = 1;
 static size_t arg_off = 0;
+static int eof_options = 0;
 
 int options(const char *desc, char **argv, int argc, char **arg)
 {
 
 int options(const char *desc, char **argv, int argc, char **arg)
 {
@@ -33,15 +34,26 @@ int options(const char *desc, char **argv, int argc, char **arg)
             if (arg_no >= argc)
                 return YAZ_OPTIONS_EOF;
         }
             if (arg_no >= argc)
                 return YAZ_OPTIONS_EOF;
         }
-        if (argv[arg_no][0] != '-' || argv[arg_no][1] == '\0')
+        if (argv[arg_no][0] != '-' || argv[arg_no][1] == '\0' || eof_options)
         {
             *arg = argv[arg_no++];
             return 0;
         }
         arg_off++; /* skip - */
     }
         {
             *arg = argv[arg_no++];
             return 0;
         }
         arg_off++; /* skip - */
     }
+    /* we're in option mode */
     if (argv[arg_no][1] == '-')
     {   /* long opt */
     if (argv[arg_no][1] == '-')
     {   /* long opt */
+        if (argv[arg_no][2] == '\0') /* -- : end of options */
+        {
+            eof_options = 1;
+            arg_off = 0;
+            ++arg_no;
+            if (arg_no >= argc)
+                return YAZ_OPTIONS_EOF;
+            *arg = argv[arg_no++];
+            return 0;
+        }
         opt_buf = argv[arg_no]+2;
         arg_off = strlen(argv[arg_no]);
     }
         opt_buf = argv[arg_no]+2;
         arg_off = strlen(argv[arg_no]);
     }
index cc857ef..bfae410 100644 (file)
@@ -6,7 +6,7 @@ check_PROGRAMS = test_ccl test_comstack test_cql2ccl \
  test_iconv test_icu test_json \
  test_libstemmer test_log test_log_thread \
  test_match_glob test_matchstr test_mutex \
  test_iconv test_icu test_json \
  test_libstemmer test_log test_log_thread \
  test_match_glob test_matchstr test_mutex \
- test_nmem test_odr test_odrstack test_oid  \
+ test_nmem test_odr test_odrstack test_oid test_options \
  test_pquery test_query_charset \
  test_record_conv test_rpn2cql test_rpn2solr test_retrieval \
  test_shared_ptr test_soap1 test_soap2 test_solr test_sortspec \
  test_pquery test_query_charset \
  test_record_conv test_rpn2cql test_rpn2solr test_retrieval \
  test_shared_ptr test_soap1 test_soap2 test_solr test_sortspec \
@@ -77,6 +77,7 @@ test_solr_SOURCES = test_solr.c
 test_sortspec_SOURCES = test_sortspec.c
 test_log_thread_SOURCES = test_log_thread.c
 test_xmlquery_SOURCES = test_xmlquery.c
 test_sortspec_SOURCES = test_sortspec.c
 test_log_thread_SOURCES = test_log_thread.c
 test_xmlquery_SOURCES = test_xmlquery.c
+test_options_SOURCES = test_options.c
 test_pquery_SOURCES = test_pquery.c
 test_comstack_SOURCES = test_comstack.c
 test_filepath_SOURCES = test_filepath.c
 test_pquery_SOURCES = test_pquery.c
 test_comstack_SOURCES = test_comstack.c
 test_filepath_SOURCES = test_filepath.c
diff --git a/test/test_options.c b/test/test_options.c
new file mode 100644 (file)
index 0000000..0b00224
--- /dev/null
@@ -0,0 +1,74 @@
+/* This file is part of the YAZ toolkit.
+ * Copyright (C) 1995-2011 Index Data
+ * See the file LICENSE for details.
+ */
+#if HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#include <string.h>
+#include <yaz/options.h>
+#include <yaz/log.h>
+#include <yaz/test.h>
+
+static void tst(void)
+{
+    char *argv[16] = {
+        "program",
+        "-a",
+        "-b",
+        "-",
+        "-cd",
+        "--longa",
+        "-n11",
+        "-n", "12",
+        "--marmelade", "13",
+        "file",
+        "--",
+        "-a",
+        "--b",
+        "other"};
+    int argc = sizeof(argv) / sizeof(*argv);
+    char *arg = 0;
+    const char *desc = "a{longa}b{longb}cdn:m{marmelade}:";
+    
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 'a');
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 'b');
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 0);
+    YAZ_CHECK(arg && !strcmp(arg, "-"));
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 'c');
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 'd');
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 'a');
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 'n');
+    YAZ_CHECK(arg && !strcmp(arg, "11"));
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 'n');
+    YAZ_CHECK(arg && !strcmp(arg, "12"));
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 'm');
+    YAZ_CHECK(arg && !strcmp(arg, "13"));
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 0);
+    YAZ_CHECK(arg && !strcmp(arg, "file"));
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 0);
+    YAZ_CHECK(arg && !strcmp(arg, "-a"));
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 0);
+    YAZ_CHECK(arg && !strcmp(arg, "--b"));
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), 0);
+    YAZ_CHECK(arg && !strcmp(arg, "other"));
+    YAZ_CHECK_EQ(options(desc, argv, argc, &arg), YAZ_OPTIONS_EOF);
+}
+
+int main(int argc, char **argv)
+{
+    YAZ_CHECK_INIT(argc, argv);
+    YAZ_CHECK_LOG();
+    tst();
+    YAZ_CHECK_TERM;
+}
+/*
+ * Local variables:
+ * c-basic-offset: 4
+ * c-file-style: "Stroustrup"
+ * indent-tabs-mode: nil
+ * End:
+ * vim: shiftwidth=4 tabstop=8 expandtab
+ */
+