LCOV - code coverage report
Current view: top level - tests - catch_arguments.cpp (source / functions) Hit Total Coverage
Test: coverage.info Lines: 3136 3168 99.0 %
Date: 2022-03-01 20:39:45 Functions: 16 16 100.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : // Copyright (c) 2006-2022  Made to Order Software Corp.  All Rights Reserved
       2             : //
       3             : // https://snapwebsites.org/project/advgetopt
       4             : // contact@m2osw.com
       5             : //
       6             : // This program is free software; you can redistribute it and/or modify
       7             : // it under the terms of the GNU General Public License as published by
       8             : // the Free Software Foundation; either version 2 of the License, or
       9             : // (at your option) any later version.
      10             : //
      11             : // This program is distributed in the hope that it will be useful,
      12             : // but WITHOUT ANY WARRANTY; without even the implied warranty of
      13             : // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      14             : // GNU General Public License for more details.
      15             : //
      16             : // You should have received a copy of the GNU General Public License along
      17             : // with this program; if not, write to the Free Software Foundation, Inc.,
      18             : // 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
      19             : 
      20             : // self
      21             : //
      22             : #include    "catch_main.h"
      23             : 
      24             : 
      25             : // advgetopt lib
      26             : //
      27             : #include    <advgetopt/exception.h>
      28             : 
      29             : 
      30             : // snapdev lib
      31             : //
      32             : #include    <snapdev/ostream_to_buf.h>
      33             : #include    <snapdev/safe_setenv.h>
      34             : 
      35             : 
      36             : // C++ lib
      37             : //
      38             : #include    <fstream>
      39             : #include    <sstream>
      40             : 
      41             : 
      42             : // last include
      43             : //
      44             : #include    <snapdev/poison.h>
      45             : 
      46             : 
      47             : 
      48             : 
      49             : 
      50             : 
      51             : 
      52             : 
      53             : 
      54             : 
      55             : 
      56             : 
      57          10 : CATCH_TEST_CASE("flag_argument", "[arguments][valid][getopt]")
      58             : {
      59          16 :     CATCH_START_SECTION("Verify a simple --verbose argument")
      60           2 :         advgetopt::option const options[] =
      61             :         {
      62             :             advgetopt::define_option(
      63             :                   advgetopt::Name("verbose")
      64             :                 , advgetopt::ShortName('v')
      65             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
      66             :                 , advgetopt::Help("print info as we work.")
      67             :             ),
      68             :             advgetopt::end_options()
      69             :         };
      70             : 
      71           2 :         advgetopt::options_environment environment_options;
      72           2 :         environment_options.f_project_name = "unittest";
      73           2 :         environment_options.f_options = options;
      74           2 :         environment_options.f_environment_flags = 0;
      75           2 :         environment_options.f_help_header = "Usage: test simple --verbose option";
      76           2 :         environment_options.f_environment_variable_name = "ADVGETOPT_UNDEFINED_VARIABLE_TO_TEST_THE_NULL";
      77             : 
      78           4 :         CATCH_WHEN("using long form")
      79             :         {
      80           1 :             char const * cargv[] =
      81             :             {
      82             :                 "/usr/bin/arguments",
      83             :                 "--verbose",
      84             :                 nullptr
      85             :             };
      86           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
      87           1 :             char ** argv = const_cast<char **>(cargv);
      88             : 
      89           2 :             advgetopt::getopt opt(environment_options, argc, argv);
      90             : 
      91             :             // check that the result is valid
      92             : 
      93             :             // an invalid parameter, MUST NOT EXIST
      94           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
      95           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
      96           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
      97           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
      98           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
      99             : 
     100             :             // no default
     101           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
     102           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
     103           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
     104           1 :             CATCH_REQUIRE(opt.size("--") == 0);
     105             : 
     106             :             // the valid parameter
     107           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
     108           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
     109           1 :             CATCH_REQUIRE(opt.is_defined("verbose"));
     110           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
     111           1 :             CATCH_REQUIRE(opt.size("verbose") == 1);
     112             : 
     113             :             // other parameters
     114           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     115           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     116             :         }
     117             : 
     118           4 :         CATCH_WHEN("using short form")
     119             :         {
     120           1 :             char const * cargv[] =
     121             :             {
     122             :                 "/usr/bin/arguments",
     123             :                 "-v",
     124             :                 nullptr
     125             :             };
     126           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     127           1 :             char ** argv = const_cast<char **>(cargv);
     128             : 
     129           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     130             : 
     131             :             // check that the result is valid
     132             : 
     133             :             // an invalid parameter, MUST NOT EXIST
     134           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     135           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     136           1 :             CATCH_REQUIRE(opt.get_option('Z', true) == nullptr);
     137           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     138           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     139           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     140             : 
     141             :             // no default
     142           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
     143           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
     144           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
     145           1 :             CATCH_REQUIRE(opt.size("--") == 0);
     146             : 
     147             :             // the valid parameter
     148           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
     149           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
     150           1 :             CATCH_REQUIRE(opt.get_option('v', true) == opt.get_option('v'));
     151           1 :             CATCH_REQUIRE(opt.is_defined("verbose"));
     152           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
     153           1 :             CATCH_REQUIRE(opt.size("verbose") == 1);
     154             : 
     155             :             // other parameters
     156           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     157           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     158             :         }
     159             :     CATCH_END_SECTION()
     160             : 
     161          16 :     CATCH_START_SECTION("Verify a simple --verbose argument in a variable")
     162           2 :         advgetopt::option const options[] =
     163             :         {
     164             :             advgetopt::define_option(
     165             :                   advgetopt::Name("verbose")
     166             :                 , advgetopt::ShortName('v')
     167             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_FLAG>())
     168             :                 , advgetopt::Help("print info as we work.")
     169             :             ),
     170             :             advgetopt::end_options()
     171             :         };
     172             : 
     173           2 :         advgetopt::options_environment environment_options;
     174           2 :         environment_options.f_project_name = "unittest";
     175           2 :         environment_options.f_options = options;
     176           2 :         environment_options.f_environment_flags = 0;
     177           2 :         environment_options.f_help_header = "Usage: test simple --verbose option";
     178           2 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
     179             : 
     180           4 :         CATCH_WHEN("using long form")
     181             :         {
     182           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--verbose");
     183             : 
     184           1 :             char const * cargv[] =
     185             :             {
     186             :                 "/usr/bin/arguments",
     187             :                 nullptr
     188             :             };
     189           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     190           1 :             char ** argv = const_cast<char **>(cargv);
     191             : 
     192           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     193             : 
     194             :             // check that the result is valid
     195             : 
     196             :             // an invalid parameter, MUST NOT EXIST
     197           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     198           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     199           1 :             CATCH_REQUIRE(opt.get_option('Z', true) == nullptr);
     200           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     201           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     202           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     203             : 
     204             :             // no default
     205           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
     206           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
     207           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
     208           1 :             CATCH_REQUIRE(opt.size("--") == 0);
     209             : 
     210             :             // the valid parameter
     211           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
     212           1 :             CATCH_REQUIRE(opt.get_option('v') == opt.get_option("verbose"));
     213           1 :             CATCH_REQUIRE(opt.get_option('v', true) == opt.get_option('v'));
     214           1 :             CATCH_REQUIRE(opt.is_defined("verbose"));
     215           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
     216           1 :             CATCH_REQUIRE(opt.size("verbose") == 1);
     217             : 
     218             :             // other parameters
     219           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     220           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     221             :         }
     222             : 
     223           4 :         CATCH_WHEN("using short form")
     224             :         {
     225           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-v");
     226             : 
     227           1 :             char const * cargv[] =
     228             :             {
     229             :                 "/usr/bin/arguments",
     230             :                 nullptr
     231             :             };
     232           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     233           1 :             char ** argv = const_cast<char **>(cargv);
     234             : 
     235           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     236             : 
     237             :             // check that the result is valid
     238             : 
     239             :             // an invalid parameter, MUST NOT EXIST
     240           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     241           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     242           1 :             CATCH_REQUIRE(opt.get_option('Z', true) == nullptr);
     243           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     244           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     245           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     246             : 
     247             :             // no default
     248           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
     249           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
     250           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
     251           1 :             CATCH_REQUIRE(opt.size("--") == 0);
     252             : 
     253             :             // the valid parameter
     254           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
     255           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
     256           1 :             CATCH_REQUIRE(opt.get_option('v', true) == opt.get_option("verbose"));
     257           1 :             CATCH_REQUIRE(opt.is_defined("verbose"));
     258           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
     259           1 :             CATCH_REQUIRE(opt.size("verbose") == 1);
     260             : 
     261             :             // other parameters
     262           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     263           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     264             :         }
     265             :     CATCH_END_SECTION()
     266             : 
     267          16 :     CATCH_START_SECTION("Verify a simple alias argument")
     268           2 :         advgetopt::option const options[] =
     269             :         {
     270             :             advgetopt::define_option(
     271             :                   advgetopt::Name("verbosity")
     272             :                 , advgetopt::ShortName('n')
     273             :                 , advgetopt::Flags(advgetopt::standalone_command_flags<advgetopt::GETOPT_FLAG_FLAG>())
     274             :                 , advgetopt::Alias("verbose")
     275             :             ),
     276             :             advgetopt::define_option(
     277             :                   advgetopt::Name("verbose")
     278             :                 , advgetopt::ShortName('v')
     279             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
     280             :                 , advgetopt::Help("print info as we work.")
     281             :             ),
     282             :             advgetopt::end_options()
     283             :         };
     284             : 
     285           2 :         advgetopt::options_environment environment_options;
     286           2 :         environment_options.f_project_name = "unittest";
     287           2 :         environment_options.f_options = options;
     288           2 :         environment_options.f_environment_flags = 0;
     289           2 :         environment_options.f_help_header = "Usage: test simple --verbosity option";
     290             : 
     291           4 :         CATCH_WHEN("using long form")
     292             :         {
     293           1 :             char const * cargv[] =
     294             :             {
     295             :                 "/usr/bin/arguments",
     296             :                 "--verbosity",
     297             :                 nullptr
     298             :             };
     299           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     300           1 :             char ** argv = const_cast<char **>(cargv);
     301             : 
     302           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     303             : 
     304             :             // check that the result is valid
     305             : 
     306             :             // an invalid parameter, MUST NOT EXIST
     307           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     308           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     309           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     310           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     311           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     312             : 
     313             :             // no default
     314           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
     315           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
     316           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
     317           1 :             CATCH_REQUIRE(opt.size("--") == 0);
     318             : 
     319             :             // the valid parameter
     320           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
     321           1 :             CATCH_REQUIRE(opt.get_option('v') == opt.get_option("verbose"));
     322           1 :             CATCH_REQUIRE(opt.is_defined("verbose"));
     323           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
     324           1 :             CATCH_REQUIRE(opt.size("verbose") == 1);
     325             : 
     326             :             // the alias parameter
     327           1 :             CATCH_REQUIRE(opt.get_option("verbosity") != nullptr);
     328           1 :             CATCH_REQUIRE(opt.get_option("verbosity") == opt.get_option("verbose"));
     329           1 :             CATCH_REQUIRE(opt.is_defined("verbosity"));
     330           1 :             CATCH_REQUIRE(opt.get_default("verbosity").empty());
     331           1 :             CATCH_REQUIRE(opt.size("verbosity") == 1);
     332             : 
     333             :             // other parameters
     334           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     335           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     336             :         }
     337             : 
     338           4 :         CATCH_WHEN("using short form")
     339             :         {
     340           1 :             char const * cargv[] =
     341             :             {
     342             :                 "/usr/bin/arguments",
     343             :                 "-n",
     344             :                 nullptr
     345             :             };
     346           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     347           1 :             char ** argv = const_cast<char **>(cargv);
     348             : 
     349           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     350             : 
     351             :             // check that the result is valid
     352             : 
     353             :             // an invalid parameter, MUST NOT EXIST
     354           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     355           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     356           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     357           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     358           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     359             : 
     360             :             // no default
     361           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
     362           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
     363           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
     364           1 :             CATCH_REQUIRE(opt.size("--") == 0);
     365             : 
     366             :             // the valid parameter
     367           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
     368           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
     369           1 :             CATCH_REQUIRE(opt.is_defined("verbose"));
     370           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
     371           1 :             CATCH_REQUIRE(opt.size("verbose") == 1);
     372             : 
     373             :             // the alias parameter
     374           1 :             CATCH_REQUIRE(opt.get_option("verbosity") != nullptr);
     375           1 :             CATCH_REQUIRE(opt.get_option("verbosity") == opt.get_option("verbose"));
     376           1 :             CATCH_REQUIRE(opt.is_defined("verbosity"));
     377           1 :             CATCH_REQUIRE(opt.get_option('n') == opt.get_option("verbose"));
     378           1 :             CATCH_REQUIRE(opt.get_option('n', true) == opt.get_option("verbosity", true));
     379           1 :             CATCH_REQUIRE(opt.get_option('n', true) != opt.get_option("verbose"));
     380           1 :             CATCH_REQUIRE(opt.get_default("verbosity").empty());
     381           1 :             CATCH_REQUIRE(opt.size("verbosity") == 1);
     382             : 
     383             :             // other parameters
     384           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     385           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     386             :         }
     387             :     CATCH_END_SECTION()
     388             : 
     389          16 :     CATCH_START_SECTION("Verify a simple alias argument in a variable")
     390           2 :         advgetopt::option const options[] =
     391             :         {
     392             :             advgetopt::define_option(
     393             :                   advgetopt::Name("verbose")
     394             :                 , advgetopt::ShortName('v')
     395             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_FLAG>())
     396             :                 , advgetopt::Help("print info as we work.")
     397             :             ),
     398             :             advgetopt::define_option(
     399             :                   advgetopt::Name("verbosity")
     400             :                 , advgetopt::ShortName('n')
     401             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_FLAG>())
     402             :                 , advgetopt::Alias("verbose")
     403             :             ),
     404             :             advgetopt::end_options()
     405             :         };
     406             : 
     407           2 :         advgetopt::options_environment environment_options;
     408           2 :         environment_options.f_project_name = "unittest";
     409           2 :         environment_options.f_options = options;
     410           2 :         environment_options.f_environment_flags = 0;
     411           2 :         environment_options.f_help_header = "Usage: test simple --verbosity option";
     412           2 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
     413             : 
     414           4 :         CATCH_WHEN("using long form")
     415             :         {
     416           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--verbosity");
     417             : 
     418           1 :             char const * cargv[] =
     419             :             {
     420             :                 "/usr/bin/arguments",
     421             :                 nullptr
     422             :             };
     423           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     424           1 :             char ** argv = const_cast<char **>(cargv);
     425             : 
     426           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     427             : 
     428             :             // check that the result is valid
     429             : 
     430             :             // an invalid parameter, MUST NOT EXIST
     431           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     432           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     433           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     434           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     435           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     436             : 
     437             :             // no default
     438           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
     439           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
     440           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
     441           1 :             CATCH_REQUIRE(opt.size("--") == 0);
     442             : 
     443             :             // the valid parameter
     444           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
     445           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
     446           1 :             CATCH_REQUIRE(opt.is_defined("verbose"));
     447           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
     448           1 :             CATCH_REQUIRE(opt.size("verbose") == 1);
     449             : 
     450             :             // the alias parameter
     451           1 :             CATCH_REQUIRE(opt.get_option("verbosity") != nullptr);
     452           1 :             CATCH_REQUIRE(opt.get_option("verbosity") == opt.get_option("verbose"));
     453           1 :             CATCH_REQUIRE(opt.is_defined("verbosity"));
     454           1 :             CATCH_REQUIRE(opt.get_default("verbosity").empty());
     455           1 :             CATCH_REQUIRE(opt.size("verbosity") == 1);
     456             : 
     457             :             // other parameters
     458           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     459           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     460             :         }
     461             : 
     462           4 :         CATCH_WHEN("using short form")
     463             :         {
     464           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-n");
     465             : 
     466           1 :             char const * cargv[] =
     467             :             {
     468             :                 "/usr/bin/arguments",
     469             :                 nullptr
     470             :             };
     471           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     472           1 :             char ** argv = const_cast<char **>(cargv);
     473             : 
     474           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     475             : 
     476             :             // check that the result is valid
     477             : 
     478             :             // an invalid parameter, MUST NOT EXIST
     479           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     480           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     481           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     482           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     483           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     484             : 
     485             :             // no default
     486           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
     487           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
     488           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
     489           1 :             CATCH_REQUIRE(opt.size("--") == 0);
     490             : 
     491             :             // the valid parameter
     492           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
     493           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
     494           1 :             CATCH_REQUIRE(opt.is_defined("verbose"));
     495           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
     496           1 :             CATCH_REQUIRE(opt.size("verbose") == 1);
     497             : 
     498             :             // the alias parameter
     499           1 :             CATCH_REQUIRE(opt.get_option("verbosity") != nullptr);
     500           1 :             CATCH_REQUIRE(opt.get_option("verbosity") == opt.get_option("verbose"));
     501           1 :             CATCH_REQUIRE(opt.is_defined("verbosity"));
     502           1 :             CATCH_REQUIRE(opt.get_default("verbosity").empty());
     503           1 :             CATCH_REQUIRE(opt.size("verbosity") == 1);
     504             : 
     505             :             // other parameters
     506           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     507           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     508             :         }
     509             :     CATCH_END_SECTION()
     510           8 : }
     511             : 
     512             : 
     513          13 : CATCH_TEST_CASE("require_argument", "[arguments][valid][required][getopt]")
     514             : {
     515          22 :     CATCH_START_SECTION("Verify a simple --out <filename> argument")
     516           3 :         advgetopt::option const options[] =
     517             :         {
     518             :             advgetopt::define_option(
     519             :                   advgetopt::Name("out")
     520             :                 , advgetopt::ShortName('o')
     521             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
     522             :                 , advgetopt::Help("output filename.")
     523             :             ),
     524             :             advgetopt::end_options()
     525             :         };
     526             : 
     527           3 :         advgetopt::options_environment environment_options;
     528           3 :         environment_options.f_project_name = "unittest";
     529           3 :         environment_options.f_options = options;
     530           3 :         environment_options.f_environment_flags = advgetopt::GETOPT_ENVIRONMENT_FLAG_SYSTEM_PARAMETERS;
     531           3 :         environment_options.f_help_header = "Usage: test simple --out <filename> option";
     532             : 
     533           6 :         CATCH_WHEN("using long form")
     534             :         {
     535           1 :             char const * cargv[] =
     536             :             {
     537             :                 "/usr/bin/arguments",
     538             :                 "--out",
     539             :                 "my-filename.out",
     540             :                 "--license",
     541             :                 nullptr
     542             :             };
     543           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     544           1 :             char ** argv = const_cast<char **>(cargv);
     545             : 
     546           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     547             : 
     548             :             // check that the result is valid
     549             : 
     550             :             // an invalid parameter, MUST NOT EXIST
     551           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     552           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     553           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     554           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     555           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     556             : 
     557             :             // the valid parameter
     558           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
     559           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
     560           1 :             CATCH_REQUIRE(opt.is_defined("out"));
     561           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
     562           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
     563           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
     564           1 :             CATCH_REQUIRE(opt.size("out") == 1);
     565             : 
     566             :             // the license system parameter
     567           1 :             CATCH_REQUIRE(opt.get_option("license") != nullptr);
     568           1 :             CATCH_REQUIRE(opt.get_option('L') != nullptr);
     569           1 :             CATCH_REQUIRE(opt.is_defined("license"));
     570           1 :             CATCH_REQUIRE(opt.get_default("license").empty());
     571           1 :             CATCH_REQUIRE(opt.size("license") == 1);
     572             : 
     573             :             // the copyright system parameter
     574           1 :             CATCH_REQUIRE(opt.get_option("copyright") != nullptr);
     575           1 :             CATCH_REQUIRE(opt.get_option('C') != nullptr);
     576           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("copyright"));
     577           1 :             CATCH_REQUIRE(opt.get_default("copyright").empty());
     578           1 :             CATCH_REQUIRE(opt.size("copyright") == 0);
     579             : 
     580             :             // other parameters
     581           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     582           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     583             :         }
     584             : 
     585           6 :         CATCH_WHEN("using long form with an equal sign")
     586             :         {
     587           1 :             char const * cargv[] =
     588             :             {
     589             :                 "/usr/bin/arguments",
     590             :                 "--out=my-filename.out",
     591             :                 nullptr
     592             :             };
     593           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     594           1 :             char ** argv = const_cast<char **>(cargv);
     595             : 
     596           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     597             : 
     598             :             // check that the result is valid
     599             : 
     600             :             // an invalid parameter, MUST NOT EXIST
     601           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     602           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     603           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     604           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     605           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     606             : 
     607             :             // the valid parameter
     608           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
     609           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
     610           1 :             CATCH_REQUIRE(opt.is_defined("out"));
     611           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
     612           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
     613           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
     614           1 :             CATCH_REQUIRE(opt.size("out") == 1);
     615             : 
     616             :             // other parameters
     617           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     618           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     619             :         }
     620             : 
     621           6 :         CATCH_WHEN("using short form")
     622             :         {
     623           1 :             char const * cargv[] =
     624             :             {
     625             :                 "/usr/bin/arguments",
     626             :                 "-o",
     627             :                 "my-filename.out",
     628             :                 nullptr
     629             :             };
     630           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     631           1 :             char ** argv = const_cast<char **>(cargv);
     632             : 
     633           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     634             : 
     635             :             // check that the result is valid
     636             : 
     637             :             // an invalid parameter, MUST NOT EXIST
     638           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     639           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     640           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     641           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     642           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     643             : 
     644             :             // the valid parameter
     645           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
     646           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
     647           1 :             CATCH_REQUIRE(opt.is_defined("out"));
     648           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
     649           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
     650           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
     651           1 :             CATCH_REQUIRE(opt.size("out") == 1);
     652             : 
     653             :             // other parameters
     654           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     655           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     656             :         }
     657             :     CATCH_END_SECTION()
     658             : 
     659          22 :     CATCH_START_SECTION("Verify a simple alias of --out <filename> argument")
     660           3 :         advgetopt::option const options[] =
     661             :         {
     662             :             advgetopt::define_option(
     663             :                   advgetopt::Name("out")
     664             :                 , advgetopt::ShortName('o')
     665             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
     666             :                 , advgetopt::Help("output filename.")
     667             :             ),
     668             :             advgetopt::define_option(
     669             :                   advgetopt::Name("results")
     670             :                 , advgetopt::ShortName('r')
     671             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
     672             :                 , advgetopt::Alias("out")
     673             :             ),
     674             :             advgetopt::end_options()
     675             :         };
     676             : 
     677           3 :         advgetopt::options_environment environment_options;
     678           3 :         environment_options.f_project_name = "unittest";
     679           3 :         environment_options.f_options = options;
     680           3 :         environment_options.f_environment_flags = 0;
     681           3 :         environment_options.f_help_header = "Usage: test simple --results <filename> option";
     682             : 
     683           6 :         CATCH_WHEN("using long form")
     684             :         {
     685           1 :             char const * cargv[] =
     686             :             {
     687             :                 "/usr/bin/arguments",
     688             :                 "--results",
     689             :                 "my-filename.out",
     690             :                 nullptr
     691             :             };
     692           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     693           1 :             char ** argv = const_cast<char **>(cargv);
     694             : 
     695           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     696             : 
     697             :             // check that the result is valid
     698             : 
     699             :             // an invalid parameter, MUST NOT EXIST
     700           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     701           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     702           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     703           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     704           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     705             : 
     706             :             // the valid parameter
     707           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
     708           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
     709           1 :             CATCH_REQUIRE(opt.is_defined("out"));
     710           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
     711           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
     712           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
     713           1 :             CATCH_REQUIRE(opt.size("out") == 1);
     714             : 
     715             :             // the alias parameter
     716           1 :             CATCH_REQUIRE(opt.get_option("results") != nullptr);
     717           1 :             CATCH_REQUIRE(opt.get_option("results") == opt.get_option("out"));
     718           1 :             CATCH_REQUIRE(opt.is_defined("results"));
     719           1 :             CATCH_REQUIRE(opt.is_defined("results"));
     720           1 :             CATCH_REQUIRE(opt.get_string("results") == "my-filename.out");
     721           1 :             CATCH_REQUIRE(opt.get_string("results", 0) == "my-filename.out");
     722           1 :             CATCH_REQUIRE(opt.get_default("results").empty());
     723           1 :             CATCH_REQUIRE(opt.size("results") == 1);
     724             : 
     725             :             // other parameters
     726           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     727           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     728             :         }
     729             : 
     730           6 :         CATCH_WHEN("using long form with an equal sign")
     731             :         {
     732           1 :             char const * cargv[] =
     733             :             {
     734             :                 "/usr/bin/arguments",
     735             :                 "--results=my-filename.out",
     736             :                 nullptr
     737             :             };
     738           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     739           1 :             char ** argv = const_cast<char **>(cargv);
     740             : 
     741           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     742             : 
     743             :             // check that the result is valid
     744             : 
     745             :             // an invalid parameter, MUST NOT EXIST
     746           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     747           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     748           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     749           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     750           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     751             : 
     752             :             // the valid parameter
     753           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
     754           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
     755           1 :             CATCH_REQUIRE(opt.is_defined("out"));
     756           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
     757           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
     758           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
     759           1 :             CATCH_REQUIRE(opt.size("out") == 1);
     760             : 
     761             :             // the alias parameter
     762           1 :             CATCH_REQUIRE(opt.get_option("results") != nullptr);
     763           1 :             CATCH_REQUIRE(opt.get_option("results") == opt.get_option("out"));
     764           1 :             CATCH_REQUIRE(opt.is_defined("results"));
     765           1 :             CATCH_REQUIRE(opt.is_defined("results"));
     766           1 :             CATCH_REQUIRE(opt.get_string("results") == "my-filename.out");
     767           1 :             CATCH_REQUIRE(opt.get_string("results", 0) == "my-filename.out");
     768           1 :             CATCH_REQUIRE(opt.get_default("results").empty());
     769           1 :             CATCH_REQUIRE(opt.size("results") == 1);
     770             : 
     771             :             // other parameters
     772           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     773           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     774             :         }
     775             : 
     776           6 :         CATCH_WHEN("using short form")
     777             :         {
     778           1 :             char const * cargv[] =
     779             :             {
     780             :                 "/usr/bin/arguments",
     781             :                 "-r",
     782             :                 "my-filename.out",
     783             :                 nullptr
     784             :             };
     785           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     786           1 :             char ** argv = const_cast<char **>(cargv);
     787             : 
     788           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     789             : 
     790             :             // check that the result is valid
     791             : 
     792             :             // an invalid parameter, MUST NOT EXIST
     793           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     794           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     795           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     796           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     797           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     798             : 
     799             :             // the valid parameter
     800           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
     801           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
     802           1 :             CATCH_REQUIRE(opt.is_defined("out"));
     803           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
     804           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
     805           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
     806           1 :             CATCH_REQUIRE(opt.size("out") == 1);
     807             : 
     808             :             // the alias parameter
     809           1 :             CATCH_REQUIRE(opt.get_option("results") != nullptr);
     810           1 :             CATCH_REQUIRE(opt.get_option("results") == opt.get_option("out"));
     811           1 :             CATCH_REQUIRE(opt.is_defined("results"));
     812           1 :             CATCH_REQUIRE(opt.get_string("results") == "my-filename.out");
     813           1 :             CATCH_REQUIRE(opt.get_string("results", 0) == "my-filename.out");
     814           1 :             CATCH_REQUIRE(opt.get_default("results").empty());
     815           1 :             CATCH_REQUIRE(opt.size("results") == 1);
     816             : 
     817             :             // other parameters
     818           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     819           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     820             :         }
     821             :     CATCH_END_SECTION()
     822             : 
     823          22 :     CATCH_START_SECTION("Verify a simple --out <filename> argument in a variable")
     824           3 :         advgetopt::option const options[] =
     825             :         {
     826             :             advgetopt::define_option(
     827             :                   advgetopt::Name("out_dir")
     828             :                 , advgetopt::ShortName('o')
     829             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
     830             :                 , advgetopt::Help("output filename.")
     831             :             ),
     832             :             advgetopt::end_options()
     833             :         };
     834             : 
     835           3 :         advgetopt::options_environment environment_options;
     836           3 :         environment_options.f_project_name = "unittest";
     837           3 :         environment_options.f_options = options;
     838           3 :         environment_options.f_environment_flags = 0;
     839           3 :         environment_options.f_help_header = "Usage: test simple --out_dir <filename> option";
     840           3 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
     841             : 
     842           6 :         CATCH_WHEN("using long form")
     843             :         {
     844           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--out_dir my-filename.out");
     845             : 
     846           1 :             char const * cargv[] =
     847             :             {
     848             :                 "/usr/bin/arguments",
     849             :                 nullptr
     850             :             };
     851           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     852           1 :             char ** argv = const_cast<char **>(cargv);
     853             : 
     854           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     855             : 
     856             :             // check that the result is valid
     857             : 
     858             :             // an invalid parameter, MUST NOT EXIST
     859           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     860           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     861           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     862           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     863           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     864             : 
     865             :             // the valid parameter
     866           1 :             CATCH_REQUIRE(opt.get_option("out-dir") != nullptr);
     867           1 :             CATCH_REQUIRE(opt.get_option("out_dir") != nullptr);
     868           1 :             CATCH_REQUIRE(opt.get_option("out_dir") == opt.get_option("out-dir"));
     869           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
     870           1 :             CATCH_REQUIRE(opt.is_defined("out-dir"));
     871           1 :             CATCH_REQUIRE(opt.get_string("out-dir") == "my-filename.out");
     872           1 :             CATCH_REQUIRE(opt.get_string("out-dir", 0) == "my-filename.out");
     873           1 :             CATCH_REQUIRE(opt.get_default("out-dir").empty());
     874           1 :             CATCH_REQUIRE(opt.size("out-dir") == 1);
     875             : 
     876             :             // other parameters
     877           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     878           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     879             :         }
     880             : 
     881           6 :         CATCH_WHEN("using long form with an equal sign")
     882             :         {
     883           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--out_dir=my-filename.out");
     884             : 
     885           1 :             char const * cargv[] =
     886             :             {
     887             :                 "/usr/bin/arguments",
     888             :                 nullptr
     889             :             };
     890           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     891           1 :             char ** argv = const_cast<char **>(cargv);
     892             : 
     893           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     894             : 
     895             :             // check that the result is valid
     896             : 
     897             :             // an invalid parameter, MUST NOT EXIST
     898           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     899           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     900           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     901           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     902           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     903             : 
     904             :             // the valid parameter
     905           1 :             CATCH_REQUIRE(opt.get_option("out_dir") != nullptr);
     906           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
     907           1 :             CATCH_REQUIRE(opt.is_defined("out_dir"));
     908           1 :             CATCH_REQUIRE(opt.get_string("out_dir") == "my-filename.out");
     909           1 :             CATCH_REQUIRE(opt.get_string("out_dir", 0) == "my-filename.out");
     910           1 :             CATCH_REQUIRE(opt.get_default("out_dir").empty());
     911           1 :             CATCH_REQUIRE(opt.size("out_dir") == 1);
     912             : 
     913             :             // other parameters
     914           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     915           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     916             :         }
     917             : 
     918           6 :         CATCH_WHEN("using short form")
     919             :         {
     920           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-o my-filename.out");
     921             : 
     922           1 :             char const * cargv[] =
     923             :             {
     924             :                 "/usr/bin/arguments",
     925             :                 nullptr
     926             :             };
     927           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     928           1 :             char ** argv = const_cast<char **>(cargv);
     929             : 
     930           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     931             : 
     932             :             // check that the result is valid
     933             : 
     934             :             // an invalid parameter, MUST NOT EXIST
     935           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     936           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
     937           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
     938           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
     939           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
     940             : 
     941             :             // the valid parameter
     942           1 :             CATCH_REQUIRE(opt.get_option("out_dir") != nullptr);
     943           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
     944           1 :             CATCH_REQUIRE(opt.is_defined("out-dir"));
     945           1 :             CATCH_REQUIRE(opt.get_string("out_dir") == "my-filename.out");
     946           1 :             CATCH_REQUIRE(opt.get_string("out-dir", 0) == "my-filename.out");
     947           1 :             CATCH_REQUIRE(opt.get_default("out_dir").empty());
     948           1 :             CATCH_REQUIRE(opt.size("out-dir") == 1);
     949             : 
     950             :             // other parameters
     951           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
     952           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
     953             :         }
     954             :     CATCH_END_SECTION()
     955             : 
     956          22 :     CATCH_START_SECTION("Verify a simple alias of --out <filename> argument in a variable")
     957           2 :         advgetopt::option const options[] =
     958             :         {
     959             :             advgetopt::define_option(
     960             :                   advgetopt::Name("out")
     961             :                 , advgetopt::ShortName('o')
     962             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
     963             :                 , advgetopt::Help("output filename.")
     964             :             ),
     965             :             advgetopt::define_option(
     966             :                   advgetopt::Name("results")
     967             :                 , advgetopt::ShortName('r')
     968             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
     969             :                 , advgetopt::Alias("o")
     970             :             ),
     971             :             advgetopt::end_options()
     972             :         };
     973             : 
     974           2 :         advgetopt::options_environment environment_options;
     975           2 :         environment_options.f_project_name = "unittest";
     976           2 :         environment_options.f_options = options;
     977           2 :         environment_options.f_environment_flags = 0;
     978           2 :         environment_options.f_help_header = "Usage: test simple alias of --out <filename> option";
     979           2 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
     980             : 
     981           4 :         CATCH_WHEN("using long form")
     982             :         {
     983           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--results my-filename.out");
     984             : 
     985           1 :             char const * cargv[] =
     986             :             {
     987             :                 "/usr/bin/arguments",
     988             :                 nullptr
     989             :             };
     990           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     991           1 :             char ** argv = const_cast<char **>(cargv);
     992             : 
     993           2 :             advgetopt::getopt opt(environment_options, argc, argv);
     994             : 
     995             :             // check that the result is valid
     996             : 
     997             :             // an invalid parameter, MUST NOT EXIST
     998           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
     999           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1000           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1001           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1002           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1003             : 
    1004             :             // the valid parameter
    1005           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1006           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1007           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1008           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1009           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1010           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1011           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    1012             : 
    1013             :             // the alias parameter
    1014           1 :             CATCH_REQUIRE(opt.get_option("results") != nullptr);
    1015           1 :             CATCH_REQUIRE(opt.get_option("results") == opt.get_option("out"));
    1016           1 :             CATCH_REQUIRE(opt.is_defined("results"));
    1017           1 :             CATCH_REQUIRE(opt.get_string("results") == "my-filename.out");
    1018           1 :             CATCH_REQUIRE(opt.get_string("results", 0) == "my-filename.out");
    1019           1 :             CATCH_REQUIRE(opt.get_default("results").empty());
    1020           1 :             CATCH_REQUIRE(opt.size("results") == 1);
    1021             : 
    1022             :             // other parameters
    1023           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1024           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1025             :         }
    1026             : 
    1027           4 :         CATCH_WHEN("using short form")
    1028             :         {
    1029           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-r my-filename.out");
    1030             : 
    1031           1 :             char const * cargv[] =
    1032             :             {
    1033             :                 "/usr/bin/arguments",
    1034             :                 nullptr
    1035             :             };
    1036           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1037           1 :             char ** argv = const_cast<char **>(cargv);
    1038             : 
    1039           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1040             : 
    1041             :             // check that the result is valid
    1042             : 
    1043             :             // an invalid parameter, MUST NOT EXIST
    1044           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1045           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1046           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1047           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1048           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1049             : 
    1050             :             // the valid parameter
    1051           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1052           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1053           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1054           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1055           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1056           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1057           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    1058             : 
    1059             :             // the alias parameter
    1060           1 :             CATCH_REQUIRE(opt.get_option("results") != nullptr);
    1061           1 :             CATCH_REQUIRE(opt.get_option("results") == opt.get_option("out"));
    1062           1 :             CATCH_REQUIRE(opt.is_defined("results"));
    1063           1 :             CATCH_REQUIRE(opt.get_string("results") == "my-filename.out");
    1064           1 :             CATCH_REQUIRE(opt.get_string("results", 0) == "my-filename.out");
    1065           1 :             CATCH_REQUIRE(opt.get_default("results").empty());
    1066           1 :             CATCH_REQUIRE(opt.size("results") == 1);
    1067             : 
    1068             :             // other parameters
    1069           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1070           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1071             :         }
    1072             :     CATCH_END_SECTION()
    1073          11 : }
    1074             : 
    1075             : 
    1076           8 : CATCH_TEST_CASE("require_arguments", "[arguments][valid][required][multiple][getopt]")
    1077             : {
    1078          12 :     CATCH_START_SECTION("Verify a simple --out <filename> ... argument")
    1079           2 :         advgetopt::option const options[] =
    1080             :         {
    1081             :             advgetopt::define_option(
    1082             :                   advgetopt::Name("out")
    1083             :                 , advgetopt::ShortName('o')
    1084             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED, advgetopt::GETOPT_FLAG_MULTIPLE>())
    1085             :                 , advgetopt::Help("output filename.")
    1086             :             ),
    1087             :             advgetopt::end_options()
    1088             :         };
    1089             : 
    1090           2 :         advgetopt::options_environment environment_options;
    1091           2 :         environment_options.f_project_name = "unittest";
    1092           2 :         environment_options.f_options = options;
    1093           2 :         environment_options.f_environment_flags = 0;
    1094           2 :         environment_options.f_help_header = "Usage: test simple --out <filename> ... option";
    1095             : 
    1096           4 :         CATCH_WHEN("using long form")
    1097             :         {
    1098           1 :             char const * cargv[] =
    1099             :             {
    1100             :                 "/usr/bin/arguments",
    1101             :                 "--out",
    1102             :                 "my-filename.out",
    1103             :                 "another.out",
    1104             :                 "last.out",
    1105             :                 nullptr
    1106             :             };
    1107           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1108           1 :             char ** argv = const_cast<char **>(cargv);
    1109             : 
    1110           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1111             : 
    1112             :             // check that the result is valid
    1113             : 
    1114             :             // an invalid parameter, MUST NOT EXIST
    1115           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1116           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1117           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1118           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1119           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1120             : 
    1121             :             // the valid parameter
    1122           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1123           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1124           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1125           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1126           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1127           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    1128           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    1129           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1130           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    1131             : 
    1132             :             // other parameters
    1133           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1134           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1135             :         }
    1136             : 
    1137           4 :         CATCH_WHEN("using short form")
    1138             :         {
    1139           1 :             char const * cargv[] =
    1140             :             {
    1141             :                 "/usr/bin/arguments",
    1142             :                 "-o",
    1143             :                 "my-filename.out",
    1144             :                 "another.out",
    1145             :                 "last.out",
    1146             :                 nullptr
    1147             :             };
    1148           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1149           1 :             char ** argv = const_cast<char **>(cargv);
    1150             : 
    1151           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1152             : 
    1153             :             // check that the result is valid
    1154             : 
    1155             :             // an invalid parameter, MUST NOT EXIST
    1156           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1157           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1158           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1159           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1160           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1161             : 
    1162             :             // the valid parameter
    1163           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1164           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1165           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1166           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1167           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1168           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    1169           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    1170           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1171           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    1172             : 
    1173             :             // other parameters
    1174           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1175           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1176             :         }
    1177             :     CATCH_END_SECTION()
    1178             : 
    1179          12 :     CATCH_START_SECTION("Verify a simple alias of --out <filename> ... argument")
    1180           2 :         advgetopt::option const options[] =
    1181             :         {
    1182             :             advgetopt::define_option(
    1183             :                   advgetopt::Name("out")
    1184             :                 , advgetopt::ShortName('o')
    1185             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED, advgetopt::GETOPT_FLAG_MULTIPLE>())
    1186             :                 , advgetopt::Help("output filename.")
    1187             :             ),
    1188             :             advgetopt::define_option(
    1189             :                   advgetopt::Name("results")
    1190             :                 , advgetopt::ShortName('r')
    1191             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED, advgetopt::GETOPT_FLAG_MULTIPLE>())
    1192             :                 , advgetopt::Alias("out")
    1193             :             ),
    1194             :             advgetopt::end_options()
    1195             :         };
    1196             : 
    1197           2 :         advgetopt::options_environment environment_options;
    1198           2 :         environment_options.f_project_name = "unittest";
    1199           2 :         environment_options.f_options = options;
    1200           2 :         environment_options.f_environment_flags = 0;
    1201           2 :         environment_options.f_help_header = "Usage: test simple alias of --out <filename> ... option";
    1202             : 
    1203           4 :         CATCH_WHEN("using long form")
    1204             :         {
    1205           1 :             char const * cargv[] =
    1206             :             {
    1207             :                 "/usr/bin/arguments",
    1208             :                 "--results",
    1209             :                 "my-filename.out",
    1210             :                 "another.out",
    1211             :                 "last.out",
    1212             :                 nullptr
    1213             :             };
    1214           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1215           1 :             char ** argv = const_cast<char **>(cargv);
    1216             : 
    1217           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1218             : 
    1219             :             // check that the result is valid
    1220             : 
    1221             :             // an invalid parameter, MUST NOT EXIST
    1222           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1223           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1224           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1225           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1226           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1227             : 
    1228             :             // the valid parameter
    1229           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1230           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1231           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1232           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1233           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1234           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    1235           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    1236           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1237           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    1238             : 
    1239             :             // the alias parameter
    1240           1 :             CATCH_REQUIRE(opt.get_option("results") != nullptr);
    1241           1 :             CATCH_REQUIRE(opt.get_option("results") == opt.get_option("out"));
    1242           1 :             CATCH_REQUIRE(opt.is_defined("results"));
    1243           1 :             CATCH_REQUIRE(opt.get_string("results") == "my-filename.out");
    1244           1 :             CATCH_REQUIRE(opt.get_string("results", 0) == "my-filename.out");
    1245           1 :             CATCH_REQUIRE(opt.get_string("results", 1) == "another.out");
    1246           1 :             CATCH_REQUIRE(opt.get_string("results", 2) == "last.out");
    1247           1 :             CATCH_REQUIRE(opt.get_default("results").empty());
    1248           1 :             CATCH_REQUIRE(opt.size("results") == 3);
    1249             : 
    1250             :             // other parameters
    1251           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1252           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1253             :         }
    1254             : 
    1255           4 :         CATCH_WHEN("using short form")
    1256             :         {
    1257           1 :             char const * cargv[] =
    1258             :             {
    1259             :                 "/usr/bin/arguments",
    1260             :                 "-r",
    1261             :                 "my-filename.out",
    1262             :                 "another.out",
    1263             :                 "last.out",
    1264             :                 nullptr
    1265             :             };
    1266           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1267           1 :             char ** argv = const_cast<char **>(cargv);
    1268             : 
    1269           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1270             : 
    1271             :             // check that the result is valid
    1272             : 
    1273             :             // an invalid parameter, MUST NOT EXIST
    1274           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1275           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1276           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1277           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1278           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1279             : 
    1280             :             // the valid parameter
    1281           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1282           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1283           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1284           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1285           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1286           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    1287           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    1288           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1289           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    1290             : 
    1291             :             // the alias parameter
    1292           1 :             CATCH_REQUIRE(opt.get_option("results") != nullptr);
    1293           1 :             CATCH_REQUIRE(opt.get_option("results") == opt.get_option("out"));
    1294           1 :             CATCH_REQUIRE(opt.is_defined("results"));
    1295           1 :             CATCH_REQUIRE(opt.get_string("results") == "my-filename.out");
    1296           1 :             CATCH_REQUIRE(opt.get_string("results", 0) == "my-filename.out");
    1297           1 :             CATCH_REQUIRE(opt.get_string("results", 1) == "another.out");
    1298           1 :             CATCH_REQUIRE(opt.get_string("results", 2) == "last.out");
    1299           1 :             CATCH_REQUIRE(opt.get_default("results").empty());
    1300           1 :             CATCH_REQUIRE(opt.size("results") == 3);
    1301             : 
    1302             :             // other parameters
    1303           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1304           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1305             :         }
    1306             :     CATCH_END_SECTION()
    1307             : 
    1308          12 :     CATCH_START_SECTION("Verify a simple --out <filename> ... argument in a variable")
    1309           2 :         advgetopt::option const options[] =
    1310             :         {
    1311             :             advgetopt::define_option(
    1312             :                   advgetopt::Name("out")
    1313             :                 , advgetopt::ShortName('o')
    1314             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_REQUIRED, advgetopt::GETOPT_FLAG_MULTIPLE>())
    1315             :                 , advgetopt::Help("output filename.")
    1316             :             ),
    1317             :             advgetopt::end_options()
    1318             :         };
    1319             : 
    1320           2 :         advgetopt::options_environment environment_options;
    1321           2 :         environment_options.f_project_name = "unittest";
    1322           2 :         environment_options.f_options = options;
    1323           2 :         environment_options.f_environment_flags = 0;
    1324           2 :         environment_options.f_help_header = "Usage: test simple --out <filename> ... option";
    1325           2 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    1326             : 
    1327           4 :         CATCH_WHEN("using long form")
    1328             :         {
    1329           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--out \"my filename.out\" another.out last.out");
    1330             : 
    1331           1 :             char const * cargv[] =
    1332             :             {
    1333             :                 "/usr/bin/arguments",
    1334             :                 nullptr
    1335             :             };
    1336           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1337           1 :             char ** argv = const_cast<char **>(cargv);
    1338             : 
    1339           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1340             : 
    1341             :             // check that the result is valid
    1342             : 
    1343             :             // an invalid parameter, MUST NOT EXIST
    1344           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1345           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1346           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1347           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1348           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1349             : 
    1350             :             // the valid parameter
    1351           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1352           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1353           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1354           1 :             CATCH_REQUIRE(opt.get_string("out") == "my filename.out");
    1355           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my filename.out");
    1356           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    1357           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    1358           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1359           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    1360             : 
    1361             :             // other parameters
    1362           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1363           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1364             :         }
    1365             : 
    1366           4 :         CATCH_WHEN("using short form")
    1367             :         {
    1368           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-o 'my filename.out' another.out last.out");
    1369             : 
    1370           1 :             char const * cargv[] =
    1371             :             {
    1372             :                 "/usr/bin/arguments",
    1373             :                 nullptr
    1374             :             };
    1375           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1376           1 :             char ** argv = const_cast<char **>(cargv);
    1377             : 
    1378           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1379             : 
    1380             :             // check that the result is valid
    1381             : 
    1382             :             // an invalid parameter, MUST NOT EXIST
    1383           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1384           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1385           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1386           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1387           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1388             : 
    1389             :             // the valid parameter
    1390           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1391           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1392           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1393           1 :             CATCH_REQUIRE(opt.get_string("out") == "my filename.out");
    1394           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my filename.out");
    1395           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    1396           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    1397           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1398           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    1399             : 
    1400             :             // other parameters
    1401           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1402           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1403             :         }
    1404             :     CATCH_END_SECTION()
    1405           6 : }
    1406             : 
    1407             : 
    1408          17 : CATCH_TEST_CASE("optional_arguments", "[arguments][valid][multiple][getopt]")
    1409             : {
    1410          30 :     CATCH_START_SECTION("Verify a simple --out [<filename> ...] argument")
    1411           9 :         char const * const separators[] =
    1412             :         {
    1413             :             ",",
    1414             :             nullptr
    1415             :         };
    1416             : 
    1417           9 :         advgetopt::option const options[] =
    1418             :         {
    1419             :             advgetopt::define_option(
    1420             :                   advgetopt::Name("out")
    1421             :                 , advgetopt::ShortName('o')
    1422             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_MULTIPLE>())
    1423             :                 , advgetopt::Help("output filename.")
    1424             :                 , advgetopt::Separators(separators)
    1425          54 :             ),
    1426             :             advgetopt::end_options()
    1427          63 :         };
    1428             : 
    1429           9 :         advgetopt::options_environment environment_options;
    1430           9 :         environment_options.f_project_name = "unittest";
    1431           9 :         environment_options.f_options = options;
    1432           9 :         environment_options.f_environment_flags = 0;
    1433           9 :         environment_options.f_help_header = "Usage: test simple --out <filename> ... option";
    1434             : 
    1435          18 :         CATCH_WHEN("using long form and no arguments")
    1436             :         {
    1437           1 :             char const * cargv[] =
    1438             :             {
    1439             :                 "/usr/bin/arguments",
    1440             :                 "--out",
    1441             :                 nullptr
    1442             :             };
    1443           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1444           1 :             char ** argv = const_cast<char **>(cargv);
    1445             : 
    1446           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1447             : 
    1448             :             // check that the result is valid
    1449             : 
    1450             :             // an invalid parameter, MUST NOT EXIST
    1451           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1452           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1453           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1454           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1455           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1456             : 
    1457             :             // the valid parameter
    1458           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1459           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1460           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1461           1 :             CATCH_REQUIRE(opt.get_string("out").empty());
    1462           1 :             CATCH_REQUIRE(opt.get_string("out", 0).empty());
    1463           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1464           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    1465             : 
    1466             :             // other parameters
    1467           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1468           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1469             :         }
    1470             : 
    1471          18 :         CATCH_WHEN("using long form and one empty argument and an equal sign")
    1472             :         {
    1473           1 :             char const * cargv[] =
    1474             :             {
    1475             :                 "/usr/bin/arguments",
    1476             :                 "--out=",
    1477             :                 nullptr
    1478             :             };
    1479           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1480           1 :             char ** argv = const_cast<char **>(cargv);
    1481             : 
    1482           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1483             : 
    1484             :             // check that the result is valid
    1485             : 
    1486             :             // an invalid parameter, MUST NOT EXIST
    1487           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1488           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1489           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1490           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1491           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1492             : 
    1493             :             // the valid parameter
    1494           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1495           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1496           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1497           1 :             CATCH_REQUIRE(opt.get_string("out").empty());
    1498           1 :             CATCH_REQUIRE(opt.get_string("out", 0).empty());
    1499           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1500           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    1501             : 
    1502             :             // other parameters
    1503           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1504           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1505             :         }
    1506             : 
    1507          18 :         CATCH_WHEN("using long form and one argument")
    1508             :         {
    1509           1 :             char const * cargv[] =
    1510             :             {
    1511             :                 "/usr/bin/arguments",
    1512             :                 "--out",
    1513             :                 "my-filename.out",
    1514             :                 nullptr
    1515             :             };
    1516           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1517           1 :             char ** argv = const_cast<char **>(cargv);
    1518             : 
    1519           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1520             : 
    1521             :             // check that the result is valid
    1522             : 
    1523             :             // an invalid parameter, MUST NOT EXIST
    1524           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1525           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1526           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1527           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1528           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1529             : 
    1530             :             // the valid parameter
    1531           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1532           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1533           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1534           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1535           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1536           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1537           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    1538             : 
    1539             :             // other parameters
    1540           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1541           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1542             :         }
    1543             : 
    1544          18 :         CATCH_WHEN("using long form and one argument and an equal sign")
    1545             :         {
    1546           1 :             char const * cargv[] =
    1547             :             {
    1548             :                 "/usr/bin/arguments",
    1549             :                 "--out=my-filename.out",
    1550             :                 nullptr
    1551             :             };
    1552           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1553           1 :             char ** argv = const_cast<char **>(cargv);
    1554             : 
    1555           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1556             : 
    1557             :             // check that the result is valid
    1558             : 
    1559             :             // an invalid parameter, MUST NOT EXIST
    1560           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1561           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1562           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1563           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1564           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1565             : 
    1566             :             // the valid parameter
    1567           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1568           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1569           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1570           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1571           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1572           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1573           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    1574             : 
    1575             :             // other parameters
    1576           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1577           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1578             :         }
    1579             : 
    1580          18 :         CATCH_WHEN("using long form and three arguments")
    1581             :         {
    1582           1 :             char const * cargv[] =
    1583             :             {
    1584             :                 "/usr/bin/arguments",
    1585             :                 "--out",
    1586             :                 "my-filename.out",
    1587             :                 "another.out",
    1588             :                 "last.out",
    1589             :                 nullptr
    1590             :             };
    1591           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1592           1 :             char ** argv = const_cast<char **>(cargv);
    1593             : 
    1594           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1595             : 
    1596             :             // check that the result is valid
    1597             : 
    1598             :             // an invalid parameter, MUST NOT EXIST
    1599           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1600           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1601           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1602           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1603           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1604             : 
    1605             :             // the valid parameter
    1606           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1607           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1608           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1609           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1610           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1611           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    1612           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    1613           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1614           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    1615             : 
    1616             :             // other parameters
    1617           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1618           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1619             :         }
    1620             : 
    1621          18 :         CATCH_WHEN("using long form and three arguments and an equal sign")
    1622             :         {
    1623           1 :             char const * cargv[] =
    1624             :             {
    1625             :                 "/usr/bin/arguments",
    1626             :                 "--out=my-filename.out,another.out,last.out",
    1627             :                 nullptr
    1628             :             };
    1629           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1630           1 :             char ** argv = const_cast<char **>(cargv);
    1631             : 
    1632           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1633             : 
    1634             :             // check that the result is valid
    1635             : 
    1636             :             // an invalid parameter, MUST NOT EXIST
    1637           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1638           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1639           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1640           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1641           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1642             : 
    1643             :             // the valid parameter
    1644           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1645           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1646           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1647           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1648           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1649           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    1650           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    1651           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1652           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    1653             : 
    1654             :             // other parameters
    1655           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1656           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1657             :         }
    1658             : 
    1659          18 :         CATCH_WHEN("using short form and no arguments")
    1660             :         {
    1661           1 :             char const * cargv[] =
    1662             :             {
    1663             :                 "/usr/bin/arguments",
    1664             :                 "-o",
    1665             :                 nullptr
    1666             :             };
    1667           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1668           1 :             char ** argv = const_cast<char **>(cargv);
    1669             : 
    1670           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1671             : 
    1672             :             // check that the result is valid
    1673             : 
    1674             :             // an invalid parameter, MUST NOT EXIST
    1675           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1676           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1677           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1678           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1679           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1680             : 
    1681             :             // the valid parameter
    1682           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1683           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1684           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1685           1 :             CATCH_REQUIRE(opt.get_string("out").empty());
    1686           1 :             CATCH_REQUIRE(opt.get_string("out", 0).empty());
    1687           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1688           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    1689             : 
    1690             :             // other parameters
    1691           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1692           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1693             :         }
    1694             : 
    1695          18 :         CATCH_WHEN("using short form and one argument")
    1696             :         {
    1697           1 :             char const * cargv[] =
    1698             :             {
    1699             :                 "/usr/bin/arguments",
    1700             :                 "-o",
    1701             :                 "my-filename.out",
    1702             :                 nullptr
    1703             :             };
    1704           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1705           1 :             char ** argv = const_cast<char **>(cargv);
    1706             : 
    1707           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1708             : 
    1709             :             // check that the result is valid
    1710             : 
    1711             :             // an invalid parameter, MUST NOT EXIST
    1712           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1713           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1714           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1715           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1716           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1717             : 
    1718             :             // the valid parameter
    1719           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1720           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1721           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1722           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1723           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1724           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1725           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    1726             : 
    1727             :             // other parameters
    1728           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1729           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1730             :         }
    1731             : 
    1732          18 :         CATCH_WHEN("using short form and three arguments")
    1733             :         {
    1734           1 :             char const * cargv[] =
    1735             :             {
    1736             :                 "/usr/bin/arguments",
    1737             :                 "-o",
    1738             :                 "my-filename.out",
    1739             :                 "another.out",
    1740             :                 "last.out",
    1741             :                 nullptr
    1742             :             };
    1743           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1744           1 :             char ** argv = const_cast<char **>(cargv);
    1745             : 
    1746           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1747             : 
    1748             :             // check that the result is valid
    1749             : 
    1750             :             // an invalid parameter, MUST NOT EXIST
    1751           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1752           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1753           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1754           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1755           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1756             : 
    1757             :             // the valid parameter
    1758           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1759           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1760           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1761           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1762           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1763           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    1764           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    1765           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1766           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    1767             : 
    1768             :             // other parameters
    1769           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1770           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1771             :         }
    1772             :     CATCH_END_SECTION()
    1773             : 
    1774          30 :     CATCH_START_SECTION("Verify a simple --out [<filename> ...] argument in a variable")
    1775           6 :         advgetopt::option const options[] =
    1776             :         {
    1777             :             advgetopt::define_option(
    1778             :                   advgetopt::Name("out")
    1779             :                 , advgetopt::ShortName('o')
    1780             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_MULTIPLE>())
    1781             :                 , advgetopt::Help("output filename.")
    1782             :             ),
    1783             :             advgetopt::end_options()
    1784             :         };
    1785             : 
    1786           6 :         advgetopt::options_environment environment_options;
    1787           6 :         environment_options.f_project_name = "unittest";
    1788           6 :         environment_options.f_options = options;
    1789           6 :         environment_options.f_environment_flags = 0;
    1790           6 :         environment_options.f_help_header = "Usage: test simple --out <filename> ... option";
    1791           6 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    1792             : 
    1793          12 :         CATCH_WHEN("using long form and no arguments")
    1794             :         {
    1795           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--out");
    1796             : 
    1797           1 :             char const * cargv[] =
    1798             :             {
    1799             :                 "/usr/bin/arguments",
    1800             :                 nullptr
    1801             :             };
    1802           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1803           1 :             char ** argv = const_cast<char **>(cargv);
    1804             : 
    1805           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1806             : 
    1807             :             // check that the result is valid
    1808             : 
    1809             :             // an invalid parameter, MUST NOT EXIST
    1810           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1811           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1812           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1813           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1814           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1815             : 
    1816             :             // the valid parameter
    1817           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1818           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1819           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1820           1 :             CATCH_REQUIRE(opt.get_string("out").empty());
    1821           1 :             CATCH_REQUIRE(opt.get_string("out", 0).empty());
    1822           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1823           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    1824             : 
    1825             :             // other parameters
    1826           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1827           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1828             :         }
    1829             : 
    1830          12 :         CATCH_WHEN("using long form and one argument")
    1831             :         {
    1832           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--out my-filename.out");
    1833             : 
    1834           1 :             char const * cargv[] =
    1835             :             {
    1836             :                 "/usr/bin/arguments",
    1837             :                 nullptr
    1838             :             };
    1839           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1840           1 :             char ** argv = const_cast<char **>(cargv);
    1841             : 
    1842           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1843             : 
    1844             :             // check that the result is valid
    1845             : 
    1846             :             // an invalid parameter, MUST NOT EXIST
    1847           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1848           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1849           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1850           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1851           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1852             : 
    1853             :             // the valid parameter
    1854           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1855           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1856           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1857           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1858           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1859           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1860           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    1861             : 
    1862             :             // other parameters
    1863           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1864           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1865             :         }
    1866             : 
    1867          12 :         CATCH_WHEN("using long form and three arguments")
    1868             :         {
    1869           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--out my-filename.out another.out last.out");
    1870             : 
    1871           1 :             char const * cargv[] =
    1872             :             {
    1873             :                 "/usr/bin/arguments",
    1874             :                 nullptr
    1875             :             };
    1876           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1877           1 :             char ** argv = const_cast<char **>(cargv);
    1878             : 
    1879           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1880             : 
    1881             :             // check that the result is valid
    1882             : 
    1883             :             // an invalid parameter, MUST NOT EXIST
    1884           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1885           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1886           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1887           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1888           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1889             : 
    1890             :             // the valid parameter
    1891           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1892           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1893           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1894           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1895           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1896           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    1897           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    1898           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1899           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    1900             : 
    1901             :             // other parameters
    1902           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1903           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1904             :         }
    1905             : 
    1906          12 :         CATCH_WHEN("using short form and no arguments")
    1907             :         {
    1908           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-o");
    1909             : 
    1910           1 :             char const * cargv[] =
    1911             :             {
    1912             :                 "/usr/bin/arguments",
    1913             :                 nullptr
    1914             :             };
    1915           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1916           1 :             char ** argv = const_cast<char **>(cargv);
    1917             : 
    1918           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1919             : 
    1920             :             // check that the result is valid
    1921             : 
    1922             :             // an invalid parameter, MUST NOT EXIST
    1923           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1924           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1925           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1926           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1927           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1928             : 
    1929             :             // the valid parameter
    1930           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1931           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1932           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1933           1 :             CATCH_REQUIRE(opt.get_string("out").empty());
    1934           1 :             CATCH_REQUIRE(opt.get_string("out", 0).empty());
    1935           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1936           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    1937             : 
    1938             :             // other parameters
    1939           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1940           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1941             :         }
    1942             : 
    1943          12 :         CATCH_WHEN("using short form and one argument")
    1944             :         {
    1945           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-o my-filename.out");
    1946             : 
    1947           1 :             char const * cargv[] =
    1948             :             {
    1949             :                 "/usr/bin/arguments",
    1950             :                 nullptr
    1951             :             };
    1952           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1953           1 :             char ** argv = const_cast<char **>(cargv);
    1954             : 
    1955           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1956             : 
    1957             :             // check that the result is valid
    1958             : 
    1959             :             // an invalid parameter, MUST NOT EXIST
    1960           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1961           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1962           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    1963           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    1964           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    1965             : 
    1966             :             // the valid parameter
    1967           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    1968           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    1969           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    1970           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    1971           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    1972           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    1973           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    1974             : 
    1975             :             // other parameters
    1976           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    1977           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    1978             :         }
    1979             : 
    1980          12 :         CATCH_WHEN("using short form and three arguments")
    1981             :         {
    1982           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-o my-filename.out another.out last.out");
    1983             : 
    1984           1 :             char const * cargv[] =
    1985             :             {
    1986             :                 "/usr/bin/arguments",
    1987             :                 nullptr
    1988             :             };
    1989           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1990           1 :             char ** argv = const_cast<char **>(cargv);
    1991             : 
    1992           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    1993             : 
    1994             :             // check that the result is valid
    1995             : 
    1996             :             // an invalid parameter, MUST NOT EXIST
    1997           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    1998           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    1999           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2000           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2001           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2002             : 
    2003             :             // the valid parameter
    2004           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2005           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    2006           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    2007           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    2008           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    2009           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    2010           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    2011           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    2012           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    2013             : 
    2014             :             // other parameters
    2015           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2016           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2017             :         }
    2018             :     CATCH_END_SECTION()
    2019          15 : }
    2020             : 
    2021             : 
    2022           8 : CATCH_TEST_CASE("config_dir_argument", "[arguments][valid][getopt][config]")
    2023             : {
    2024          12 :     CATCH_START_SECTION("Verify that we do get the --config-dir option when we have a standalone configuration filename")
    2025             :     {
    2026           1 :         advgetopt::option const options[] =
    2027             :         {
    2028             :             advgetopt::define_option(
    2029             :                   advgetopt::Name("out")
    2030             :                 , advgetopt::ShortName('o')
    2031             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    2032             :                 , advgetopt::Help("output filename.")
    2033             :             ),
    2034             :             advgetopt::end_options()
    2035             :         };
    2036             : 
    2037           1 :         advgetopt::options_environment environment_options;
    2038           1 :         environment_options.f_project_name = "unittest";
    2039           1 :         environment_options.f_options = options;
    2040           1 :         environment_options.f_environment_flags = advgetopt::GETOPT_ENVIRONMENT_FLAG_SYSTEM_PARAMETERS;
    2041           1 :         environment_options.f_configuration_filename = "snapwatchdog.conf";
    2042           1 :         environment_options.f_help_header = "Usage: test --config-dir";
    2043             : 
    2044           1 :         char const * cargv[] =
    2045             :         {
    2046             :             "/usr/bin/arguments",
    2047             :             "--out",
    2048             :             "my-filename.out",
    2049             :             "--license",
    2050             :             "--config-dir",
    2051             :             "/opt/m2osw/config",
    2052             :             nullptr
    2053             :         };
    2054           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2055           1 :         char ** argv = const_cast<char **>(cargv);
    2056             : 
    2057           2 :         advgetopt::getopt opt(environment_options, argc, argv);
    2058             : 
    2059             :         // check that the result is valid
    2060             : 
    2061             :         // an invalid parameter, MUST NOT EXIST
    2062           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2063           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2064           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2065           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2066           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2067             : 
    2068             :         // the valid parameter
    2069           1 :         CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2070           1 :         CATCH_REQUIRE(opt.get_option('o') == opt.get_option("out"));
    2071           1 :         CATCH_REQUIRE(opt.is_defined("out"));
    2072           1 :         CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    2073           1 :         CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    2074           1 :         CATCH_REQUIRE(opt.get_default("out").empty());
    2075           1 :         CATCH_REQUIRE(opt.size("out") == 1);
    2076             : 
    2077             :         // the license system parameter
    2078           1 :         CATCH_REQUIRE(opt.get_option("license") != nullptr);
    2079           1 :         CATCH_REQUIRE(opt.get_option('L') != nullptr);
    2080           1 :         CATCH_REQUIRE(opt.is_defined("license"));
    2081           1 :         CATCH_REQUIRE(opt.get_default("license").empty());
    2082           1 :         CATCH_REQUIRE(opt.size("license") == 1);
    2083             : 
    2084             :         // the copyright system parameter
    2085           1 :         CATCH_REQUIRE(opt.get_option("copyright") != nullptr);
    2086           1 :         CATCH_REQUIRE(opt.get_option('C') == opt.get_option("copyright"));
    2087           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("copyright"));
    2088           1 :         CATCH_REQUIRE(opt.get_default("copyright").empty());
    2089           1 :         CATCH_REQUIRE(opt.size("copyright") == 0);
    2090             : 
    2091             :         // the config-dir system parameter
    2092           1 :         CATCH_REQUIRE(opt.get_option("config-dir") != nullptr);
    2093           1 :         CATCH_REQUIRE(opt.is_defined("config-dir"));
    2094           1 :         CATCH_REQUIRE(opt.get_default("config-dir").empty());
    2095           1 :         CATCH_REQUIRE(opt.size("config-dir") == 1);
    2096           1 :         CATCH_REQUIRE(opt.get_string("config-dir") == "/opt/m2osw/config");
    2097             : 
    2098             :         // other parameters
    2099           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2100           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2101             :     }
    2102             :     CATCH_END_SECTION()
    2103             : 
    2104          12 :     CATCH_START_SECTION("Verify that we do not get the --config-dir option when the standalone configuration filename is nullptr")
    2105             :     {
    2106           1 :         advgetopt::option const options[] =
    2107             :         {
    2108             :             advgetopt::define_option(
    2109             :                   advgetopt::Name("out")
    2110             :                 , advgetopt::ShortName('o')
    2111             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    2112             :                 , advgetopt::Help("output filename.")
    2113             :             ),
    2114             :             advgetopt::end_options()
    2115             :         };
    2116             : 
    2117           1 :         advgetopt::options_environment environment_options;
    2118           1 :         environment_options.f_project_name = "unittest";
    2119           1 :         environment_options.f_options = options;
    2120           1 :         environment_options.f_environment_flags = advgetopt::GETOPT_ENVIRONMENT_FLAG_SYSTEM_PARAMETERS;
    2121           1 :         environment_options.f_configuration_filename = nullptr;
    2122           1 :         environment_options.f_help_header = "Usage: test --config-dir";
    2123             : 
    2124           1 :         char const * cargv[] =
    2125             :         {
    2126             :             "/usr/bin/arguments",
    2127             :             "--out",
    2128             :             "my-filename.out",
    2129             :             "--license",
    2130             :             nullptr
    2131             :         };
    2132           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2133           1 :         char ** argv = const_cast<char **>(cargv);
    2134             : 
    2135           2 :         advgetopt::getopt opt(environment_options, argc, argv);
    2136             : 
    2137             :         // check that the result is valid
    2138             : 
    2139             :         // an invalid parameter, MUST NOT EXIST
    2140           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2141           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2142           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2143           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2144           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2145             : 
    2146             :         // the valid parameter
    2147           1 :         CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2148           1 :         CATCH_REQUIRE(opt.get_option('o') == opt.get_option("out"));
    2149           1 :         CATCH_REQUIRE(opt.is_defined("out"));
    2150           1 :         CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    2151           1 :         CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    2152           1 :         CATCH_REQUIRE(opt.get_default("out").empty());
    2153           1 :         CATCH_REQUIRE(opt.size("out") == 1);
    2154             : 
    2155             :         // the license system parameter
    2156           1 :         CATCH_REQUIRE(opt.get_option("license") != nullptr);
    2157           1 :         CATCH_REQUIRE(opt.get_option('L') != nullptr);
    2158           1 :         CATCH_REQUIRE(opt.is_defined("license"));
    2159           1 :         CATCH_REQUIRE(opt.get_default("license").empty());
    2160           1 :         CATCH_REQUIRE(opt.size("license") == 1);
    2161             : 
    2162             :         // the copyright system parameter
    2163           1 :         CATCH_REQUIRE(opt.get_option("copyright") != nullptr);
    2164           1 :         CATCH_REQUIRE(opt.get_option('C') == opt.get_option("copyright"));
    2165           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("copyright"));
    2166           1 :         CATCH_REQUIRE(opt.get_default("copyright").empty());
    2167           1 :         CATCH_REQUIRE(opt.size("copyright") == 0);
    2168             : 
    2169             :         // no config-dir system parameter when the configuration filename is missing
    2170           1 :         CATCH_REQUIRE(opt.get_option("config-dir") == nullptr);
    2171           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("config-dir"));
    2172           1 :         CATCH_REQUIRE(opt.get_default("config-dir").empty());
    2173           1 :         CATCH_REQUIRE(opt.size("config-dir") == 0);
    2174             : 
    2175             :         // other parameters
    2176           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2177           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2178             :     }
    2179             :     CATCH_END_SECTION()
    2180             : 
    2181          12 :     CATCH_START_SECTION("Verify that we do not get the --config-dir option when the standalone configuration filename is \"\"")
    2182             :     {
    2183           1 :         advgetopt::option const options[] =
    2184             :         {
    2185             :             advgetopt::define_option(
    2186             :                   advgetopt::Name("out")
    2187             :                 , advgetopt::ShortName('o')
    2188             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    2189             :                 , advgetopt::Help("output filename.")
    2190             :             ),
    2191             :             advgetopt::end_options()
    2192             :         };
    2193             : 
    2194           1 :         advgetopt::options_environment environment_options;
    2195           1 :         environment_options.f_project_name = "unittest";
    2196           1 :         environment_options.f_options = options;
    2197           1 :         environment_options.f_environment_flags = advgetopt::GETOPT_ENVIRONMENT_FLAG_SYSTEM_PARAMETERS;
    2198           1 :         environment_options.f_configuration_filename = "";
    2199           1 :         environment_options.f_help_header = "Usage: test --config-dir";
    2200             : 
    2201           1 :         char const * cargv[] =
    2202             :         {
    2203             :             "/usr/bin/arguments",
    2204             :             "--out",
    2205             :             "my-filename.out",
    2206             :             "--license",
    2207             :             nullptr
    2208             :         };
    2209           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2210           1 :         char ** argv = const_cast<char **>(cargv);
    2211             : 
    2212           2 :         advgetopt::getopt opt(environment_options, argc, argv);
    2213             : 
    2214             :         // check that the result is valid
    2215             : 
    2216             :         // an invalid parameter, MUST NOT EXIST
    2217           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2218           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2219           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2220           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2221           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2222             : 
    2223             :         // the valid parameter
    2224           1 :         CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2225           1 :         CATCH_REQUIRE(opt.get_option('o') == opt.get_option("out"));
    2226           1 :         CATCH_REQUIRE(opt.is_defined("out"));
    2227           1 :         CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    2228           1 :         CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    2229           1 :         CATCH_REQUIRE(opt.get_default("out").empty());
    2230           1 :         CATCH_REQUIRE(opt.size("out") == 1);
    2231             : 
    2232             :         // the license system parameter
    2233           1 :         CATCH_REQUIRE(opt.get_option("license") != nullptr);
    2234           1 :         CATCH_REQUIRE(opt.get_option('L') != nullptr);
    2235           1 :         CATCH_REQUIRE(opt.is_defined("license"));
    2236           1 :         CATCH_REQUIRE(opt.get_default("license").empty());
    2237           1 :         CATCH_REQUIRE(opt.size("license") == 1);
    2238             : 
    2239             :         // the copyright system parameter
    2240           1 :         CATCH_REQUIRE(opt.get_option("copyright") != nullptr);
    2241           1 :         CATCH_REQUIRE(opt.get_option('C') == opt.get_option("copyright"));
    2242           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("copyright"));
    2243           1 :         CATCH_REQUIRE(opt.get_default("copyright").empty());
    2244           1 :         CATCH_REQUIRE(opt.size("copyright") == 0);
    2245             : 
    2246             :         // no config-dir system parameter when the configuration filename is missing
    2247           1 :         CATCH_REQUIRE(opt.get_option("config-dir") == nullptr);
    2248           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("config-dir"));
    2249           1 :         CATCH_REQUIRE(opt.get_default("config-dir").empty());
    2250           1 :         CATCH_REQUIRE(opt.size("config-dir") == 0);
    2251             : 
    2252             :         // other parameters
    2253           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2254           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2255             :     }
    2256             :     CATCH_END_SECTION()
    2257             : 
    2258          12 :     CATCH_START_SECTION("Test adding '-c' to '--config-dir'")
    2259             :     {
    2260           1 :         advgetopt::option const options[] =
    2261             :         {
    2262             :             advgetopt::define_option(
    2263             :                   advgetopt::Name("out")
    2264             :                 , advgetopt::ShortName('o')
    2265             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    2266             :                 , advgetopt::Help("output filename.")
    2267             :             ),
    2268             :             advgetopt::end_options()
    2269             :         };
    2270             : 
    2271           1 :         advgetopt::options_environment environment_options;
    2272           1 :         environment_options.f_project_name = "unittest";
    2273           1 :         environment_options.f_options = options;
    2274           1 :         environment_options.f_environment_flags = advgetopt::GETOPT_ENVIRONMENT_FLAG_SYSTEM_PARAMETERS;
    2275           1 :         environment_options.f_configuration_filename = "snapwatchdog.conf";
    2276           1 :         environment_options.f_help_header = "Usage: test --config-dir";
    2277             : 
    2278           1 :         char const * cargv[] =
    2279             :         {
    2280             :             "/usr/bin/arguments",
    2281             :             "--out",
    2282             :             "my-filename.out",
    2283             :             "--license",
    2284             :             "-c",
    2285             :             "/opt/m2osw/config",
    2286             :             nullptr
    2287             :         };
    2288           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2289           1 :         char ** argv = const_cast<char **>(cargv);
    2290             : 
    2291           2 :         advgetopt::getopt opt(environment_options);
    2292           1 :         opt.parse_program_name(argv);
    2293           1 :         opt.link_aliases();
    2294             : 
    2295           2 :         advgetopt::option_info::pointer_t config_dir(opt.get_option("config-dir"));
    2296           1 :         CATCH_REQUIRE(config_dir != nullptr);
    2297           1 :         opt.set_short_name("config-dir", U'c');
    2298             : 
    2299           1 :         opt.parse_arguments(argc, argv, advgetopt::option_source_t::SOURCE_COMMAND_LINE);
    2300             : 
    2301             :         // check that the result is valid
    2302             : 
    2303             :         // an invalid parameter, MUST NOT EXIST
    2304           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2305           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2306           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2307           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2308           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2309             : 
    2310             :         // the valid parameter
    2311           1 :         CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2312           1 :         CATCH_REQUIRE(opt.get_option('o') == opt.get_option("out"));
    2313           1 :         CATCH_REQUIRE(opt.is_defined("out"));
    2314           1 :         CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    2315           1 :         CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    2316           1 :         CATCH_REQUIRE(opt.get_default("out").empty());
    2317           1 :         CATCH_REQUIRE(opt.size("out") == 1);
    2318             : 
    2319             :         // the license system parameter
    2320           1 :         CATCH_REQUIRE(opt.get_option("license") != nullptr);
    2321           1 :         CATCH_REQUIRE(opt.get_option('L') != nullptr);
    2322           1 :         CATCH_REQUIRE(opt.is_defined("license"));
    2323           1 :         CATCH_REQUIRE(opt.get_default("license").empty());
    2324           1 :         CATCH_REQUIRE(opt.size("license") == 1);
    2325             : 
    2326             :         // the copyright system parameter
    2327           1 :         CATCH_REQUIRE(opt.get_option("copyright") != nullptr);
    2328           1 :         CATCH_REQUIRE(opt.get_option('C') == opt.get_option("copyright"));
    2329           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("copyright"));
    2330           1 :         CATCH_REQUIRE(opt.get_default("copyright").empty());
    2331           1 :         CATCH_REQUIRE(opt.size("copyright") == 0);
    2332             : 
    2333             :         // the config-dir system parameter
    2334           1 :         CATCH_REQUIRE(opt.get_option("config-dir") != nullptr);
    2335           1 :         CATCH_REQUIRE(opt.is_defined("config-dir"));
    2336           1 :         CATCH_REQUIRE(opt.get_default("config-dir").empty());
    2337           1 :         CATCH_REQUIRE(opt.size("config-dir") == 1);
    2338           1 :         CATCH_REQUIRE(opt.get_string("config-dir") == "/opt/m2osw/config");
    2339             : 
    2340             :         // other parameters
    2341           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2342           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2343             :     }
    2344             :     CATCH_END_SECTION()
    2345             : 
    2346          12 :     CATCH_START_SECTION("Test our own parsing with '--config-dir' and f_configuration_filename set to nullptr")
    2347             :     {
    2348           1 :         advgetopt::option const options[] =
    2349             :         {
    2350             :             advgetopt::define_option(
    2351             :                   advgetopt::Name("out")
    2352             :                 , advgetopt::ShortName('o')
    2353             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    2354             :                 , advgetopt::Help("output filename.")
    2355             :             ),
    2356             :             advgetopt::end_options()
    2357             :         };
    2358             : 
    2359           1 :         advgetopt::options_environment environment_options;
    2360           1 :         environment_options.f_project_name = "unittest";
    2361           1 :         environment_options.f_options = options;
    2362           1 :         environment_options.f_environment_flags = advgetopt::GETOPT_ENVIRONMENT_FLAG_SYSTEM_PARAMETERS;
    2363           1 :         environment_options.f_configuration_filename = nullptr;
    2364           1 :         environment_options.f_help_header = "Usage: test --config-dir";
    2365             : 
    2366           1 :         char const * cargv[] =
    2367             :         {
    2368             :             "/usr/bin/arguments",
    2369             :             "--out",
    2370             :             "my-filename.out",
    2371             :             "--license",
    2372             :             nullptr
    2373             :         };
    2374           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2375           1 :         char ** argv = const_cast<char **>(cargv);
    2376             : 
    2377           2 :         advgetopt::getopt opt(environment_options);
    2378           1 :         opt.parse_program_name(argv);
    2379           1 :         opt.link_aliases();
    2380             : 
    2381           1 :         CATCH_REQUIRE(opt.get_option("config-dir") == nullptr);
    2382             : 
    2383           1 :         opt.parse_arguments(argc, argv, advgetopt::option_source_t::SOURCE_COMMAND_LINE);
    2384             : 
    2385             :         // check that the result is valid
    2386             : 
    2387             :         // an invalid parameter, MUST NOT EXIST
    2388           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2389           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2390           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2391           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2392           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2393             : 
    2394             :         // the valid parameter
    2395           1 :         CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2396           1 :         CATCH_REQUIRE(opt.get_option('o') == opt.get_option("out"));
    2397           1 :         CATCH_REQUIRE(opt.is_defined("out"));
    2398           1 :         CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    2399           1 :         CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    2400           1 :         CATCH_REQUIRE(opt.get_default("out").empty());
    2401           1 :         CATCH_REQUIRE(opt.size("out") == 1);
    2402             : 
    2403             :         // the license system parameter
    2404           1 :         CATCH_REQUIRE(opt.get_option("license") != nullptr);
    2405           1 :         CATCH_REQUIRE(opt.get_option('L') != nullptr);
    2406           1 :         CATCH_REQUIRE(opt.is_defined("license"));
    2407           1 :         CATCH_REQUIRE(opt.get_default("license").empty());
    2408           1 :         CATCH_REQUIRE(opt.size("license") == 1);
    2409             : 
    2410             :         // the copyright system parameter
    2411           1 :         CATCH_REQUIRE(opt.get_option("copyright") != nullptr);
    2412           1 :         CATCH_REQUIRE(opt.get_option('C') == opt.get_option("copyright"));
    2413           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("copyright"));
    2414           1 :         CATCH_REQUIRE(opt.get_default("copyright").empty());
    2415           1 :         CATCH_REQUIRE(opt.size("copyright") == 0);
    2416             : 
    2417             :         // the config-dir system parameter
    2418           1 :         CATCH_REQUIRE(opt.get_option("config-dir") == nullptr);
    2419           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("config-dir"));
    2420           1 :         CATCH_REQUIRE(opt.get_default("config-dir").empty());
    2421           1 :         CATCH_REQUIRE(opt.size("config-dir") == 0);
    2422             : 
    2423             :         // other parameters
    2424           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2425           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2426             :     }
    2427             :     CATCH_END_SECTION()
    2428             : 
    2429          12 :     CATCH_START_SECTION("Test our own parsing with '--config-dir' and f_configuration_filename set to \"\"")
    2430             :     {
    2431           1 :         advgetopt::option const options[] =
    2432             :         {
    2433             :             advgetopt::define_option(
    2434             :                   advgetopt::Name("out")
    2435             :                 , advgetopt::ShortName('o')
    2436             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    2437             :                 , advgetopt::Help("output filename.")
    2438             :             ),
    2439             :             advgetopt::end_options()
    2440             :         };
    2441             : 
    2442           1 :         advgetopt::options_environment environment_options;
    2443           1 :         environment_options.f_project_name = "unittest";
    2444           1 :         environment_options.f_options = options;
    2445           1 :         environment_options.f_environment_flags = advgetopt::GETOPT_ENVIRONMENT_FLAG_SYSTEM_PARAMETERS;
    2446           1 :         environment_options.f_configuration_filename = "";
    2447           1 :         environment_options.f_help_header = "Usage: test --config-dir";
    2448             : 
    2449           1 :         char const * cargv[] =
    2450             :         {
    2451             :             "/usr/bin/arguments",
    2452             :             "--out",
    2453             :             "my-filename.out",
    2454             :             "--license",
    2455             :             nullptr
    2456             :         };
    2457           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2458           1 :         char ** argv = const_cast<char **>(cargv);
    2459             : 
    2460           2 :         advgetopt::getopt opt(environment_options);
    2461           1 :         opt.parse_program_name(argv);
    2462           1 :         opt.link_aliases();
    2463             : 
    2464           1 :         CATCH_REQUIRE(opt.get_option("config-dir") == nullptr);
    2465             : 
    2466           1 :         opt.parse_arguments(argc, argv, advgetopt::option_source_t::SOURCE_COMMAND_LINE);
    2467             : 
    2468             :         // check that the result is valid
    2469             : 
    2470             :         // an invalid parameter, MUST NOT EXIST
    2471           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2472           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2473           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2474           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2475           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2476             : 
    2477             :         // the valid parameter
    2478           1 :         CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2479           1 :         CATCH_REQUIRE(opt.get_option('o') == opt.get_option("out"));
    2480           1 :         CATCH_REQUIRE(opt.is_defined("out"));
    2481           1 :         CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    2482           1 :         CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    2483           1 :         CATCH_REQUIRE(opt.get_default("out").empty());
    2484           1 :         CATCH_REQUIRE(opt.size("out") == 1);
    2485             : 
    2486             :         // the license system parameter
    2487           1 :         CATCH_REQUIRE(opt.get_option("license") != nullptr);
    2488           1 :         CATCH_REQUIRE(opt.get_option('L') != nullptr);
    2489           1 :         CATCH_REQUIRE(opt.is_defined("license"));
    2490           1 :         CATCH_REQUIRE(opt.get_default("license").empty());
    2491           1 :         CATCH_REQUIRE(opt.size("license") == 1);
    2492             : 
    2493             :         // the copyright system parameter
    2494           1 :         CATCH_REQUIRE(opt.get_option("copyright") != nullptr);
    2495           1 :         CATCH_REQUIRE(opt.get_option('C') == opt.get_option("copyright"));
    2496           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("copyright"));
    2497           1 :         CATCH_REQUIRE(opt.get_default("copyright").empty());
    2498           1 :         CATCH_REQUIRE(opt.size("copyright") == 0);
    2499             : 
    2500             :         // the config-dir system parameter
    2501           1 :         CATCH_REQUIRE(opt.get_option("config-dir") == nullptr);
    2502           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("config-dir"));
    2503           1 :         CATCH_REQUIRE(opt.get_default("config-dir").empty());
    2504           1 :         CATCH_REQUIRE(opt.size("config-dir") == 0);
    2505             : 
    2506             :         // other parameters
    2507           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2508           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2509             :     }
    2510             :     CATCH_END_SECTION()
    2511           6 : }
    2512             : 
    2513             : 
    2514          18 : CATCH_TEST_CASE("default_argument", "[arguments][valid][getopt]")
    2515             : {
    2516          32 :     CATCH_START_SECTION("Verify a simple [<filename>] argument")
    2517           6 :         advgetopt::option const options[] =
    2518             :         {
    2519             :             advgetopt::define_option(
    2520             :                   advgetopt::Name("out")
    2521             :                 , advgetopt::ShortName('o')
    2522             :                 , advgetopt::Flags(advgetopt::any_flags<advgetopt::GETOPT_FLAG_COMMAND_LINE
    2523             :                                                       , advgetopt::GETOPT_FLAG_DEFAULT_OPTION>())
    2524             :                 , advgetopt::Help("output filename.")
    2525             :             ),
    2526             :             advgetopt::end_options()
    2527             :         };
    2528             : 
    2529           6 :         advgetopt::options_environment environment_options;
    2530           6 :         environment_options.f_project_name = "unittest";
    2531           6 :         environment_options.f_options = options;
    2532           6 :         environment_options.f_environment_flags = 0;
    2533           6 :         environment_options.f_help_header = "Usage: test simple [<filename>] option";
    2534             : 
    2535          12 :         CATCH_WHEN("no arguments")
    2536             :         {
    2537           1 :             char const * cargv[] =
    2538             :             {
    2539             :                 "/usr/bin/arguments",
    2540             :                 nullptr
    2541             :             };
    2542           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2543           1 :             char ** argv = const_cast<char **>(cargv);
    2544             : 
    2545           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    2546             : 
    2547             :             // check that the result is valid
    2548             : 
    2549             :             // an invalid parameter, MUST NOT EXIST
    2550           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2551           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2552           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2553           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2554           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2555             : 
    2556             :             // the valid parameter
    2557           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2558           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    2559           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("out"));
    2560           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    2561           1 :             CATCH_REQUIRE(opt.size("out") == 0);
    2562             : 
    2563             :             // the valid parameter is the default
    2564           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    2565           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    2566           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
    2567           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    2568           1 :             CATCH_REQUIRE(opt.size("--") == 0);
    2569             : 
    2570             :             // other parameters
    2571           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2572           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2573             :         }
    2574             : 
    2575          12 :         CATCH_WHEN("one argument")
    2576             :         {
    2577           1 :             char const * cargv[] =
    2578             :             {
    2579             :                 "/usr/bin/arguments",
    2580             :                 "my-filename.out",
    2581             :                 nullptr
    2582             :             };
    2583           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2584           1 :             char ** argv = const_cast<char **>(cargv);
    2585             : 
    2586           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    2587             : 
    2588             :             // check that the result is valid
    2589             : 
    2590             :             // an invalid parameter, MUST NOT EXIST
    2591           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2592           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2593           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2594           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2595           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2596             : 
    2597             :             // the valid parameter
    2598           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2599           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    2600           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    2601           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    2602           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    2603           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    2604           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    2605             : 
    2606             :             // the valid parameter is the default
    2607           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    2608           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    2609           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    2610           1 :             CATCH_REQUIRE(opt.get_string("--") == "my-filename.out");
    2611           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "my-filename.out");
    2612           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    2613           1 :             CATCH_REQUIRE(opt.size("--") == 1);
    2614             : 
    2615             :             // other parameters
    2616           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2617           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2618             :         }
    2619             : 
    2620          12 :         CATCH_WHEN("three arguments")
    2621             :         {
    2622           1 :             char const * cargv[] =
    2623             :             {
    2624             :                 "/usr/bin/arguments",
    2625             :                 "my-filename.out",
    2626             :                 "another.out",
    2627             :                 "last.out",
    2628             :                 nullptr
    2629             :             };
    2630           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2631           1 :             char ** argv = const_cast<char **>(cargv);
    2632             : 
    2633           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    2634             : 
    2635             :             // check that the result is valid
    2636             : 
    2637             :             // an invalid parameter, MUST NOT EXIST
    2638           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2639           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2640           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2641           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2642           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2643             : 
    2644             :             // the valid parameter
    2645           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2646           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    2647           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    2648           1 :             CATCH_REQUIRE(opt.get_string("out") == "last.out");
    2649           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "last.out");
    2650           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    2651           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    2652             : 
    2653             :             // the valid parameter is the default
    2654           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    2655           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    2656           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    2657           1 :             CATCH_REQUIRE(opt.get_string("--") == "last.out");
    2658           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "last.out");
    2659           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    2660           1 :             CATCH_REQUIRE(opt.size("--") == 1);
    2661             : 
    2662             :             // other parameters
    2663           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2664           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2665             :         }
    2666             : 
    2667          12 :         CATCH_WHEN("using the '--' separator and no arguments")
    2668             :         {
    2669           1 :             char const * cargv[] =
    2670             :             {
    2671             :                 "/usr/bin/arguments",
    2672             :                 "--",
    2673             :                 nullptr
    2674             :             };
    2675           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2676           1 :             char ** argv = const_cast<char **>(cargv);
    2677             : 
    2678           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    2679             : 
    2680             :             // check that the result is valid
    2681             : 
    2682             :             // an invalid parameter, MUST NOT EXIST
    2683           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2684           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2685           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2686           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2687           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2688             : 
    2689             :             // the valid parameter
    2690           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2691           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    2692           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("out"));
    2693           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    2694           1 :             CATCH_REQUIRE(opt.size("out") == 0);
    2695             : 
    2696             :             // the valid parameter is the default
    2697           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    2698           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    2699           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
    2700           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    2701           1 :             CATCH_REQUIRE(opt.size("--") == 0);
    2702             : 
    2703             :             // other parameters
    2704           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2705           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2706             :         }
    2707             : 
    2708          12 :         CATCH_WHEN("using the '--' separator and one argument")
    2709             :         {
    2710           1 :             char const * cargv[] =
    2711             :             {
    2712             :                 "/usr/bin/arguments",
    2713             :                 "--",
    2714             :                 "--my-filename.out",
    2715             :                 nullptr
    2716             :             };
    2717           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2718           1 :             char ** argv = const_cast<char **>(cargv);
    2719             : 
    2720           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    2721             : 
    2722             :             // check that the result is valid
    2723             : 
    2724             :             // an invalid parameter, MUST NOT EXIST
    2725           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2726           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2727           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2728           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2729           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2730             : 
    2731             :             // the valid parameter
    2732           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2733           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    2734           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    2735           1 :             CATCH_REQUIRE(opt.get_string("out") == "--my-filename.out");
    2736           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "--my-filename.out");
    2737           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    2738           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    2739             : 
    2740             :             // the valid parameter is the default
    2741           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    2742           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    2743           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    2744           1 :             CATCH_REQUIRE(opt.get_string("--") == "--my-filename.out");
    2745           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "--my-filename.out");
    2746           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    2747           1 :             CATCH_REQUIRE(opt.size("--") == 1);
    2748             : 
    2749             :             // other parameters
    2750           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2751           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2752             :         }
    2753             : 
    2754          12 :         CATCH_WHEN("using the '--' separator and three arguments")
    2755             :         {
    2756           1 :             char const * cargv[] =
    2757             :             {
    2758             :                 "/usr/bin/arguments",
    2759             :                 "--",
    2760             :                 "my-filename.out",
    2761             :                 "-another.out",
    2762             :                 "--last.out",
    2763             :                 nullptr
    2764             :             };
    2765           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2766           1 :             char ** argv = const_cast<char **>(cargv);
    2767             : 
    2768           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    2769             : 
    2770             :             // check that the result is valid
    2771             : 
    2772             :             // an invalid parameter, MUST NOT EXIST
    2773           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2774           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2775           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2776           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2777           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2778             : 
    2779             :             // the valid parameter
    2780           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2781           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    2782           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    2783           1 :             CATCH_REQUIRE(opt.get_string("out") == "--last.out");
    2784           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "--last.out");
    2785           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    2786           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    2787             : 
    2788             :             // the valid parameter is the default
    2789           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    2790           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    2791           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    2792           1 :             CATCH_REQUIRE(opt.get_string("--") == "--last.out");
    2793           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "--last.out");
    2794           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    2795           1 :             CATCH_REQUIRE(opt.size("--") == 1);
    2796             : 
    2797             :             // other parameters
    2798           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2799           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2800             :         }
    2801             :     CATCH_END_SECTION()
    2802             : 
    2803          32 :     CATCH_START_SECTION("Verify a simple [<filename>] argument in a variable")
    2804           8 :         advgetopt::option const options[] =
    2805             :         {
    2806             :             advgetopt::define_option(
    2807             :                   advgetopt::Name("out")
    2808             :                 , advgetopt::ShortName('o')
    2809             :                 , advgetopt::Flags(advgetopt::any_flags<advgetopt::GETOPT_FLAG_ENVIRONMENT_VARIABLE
    2810             :                                                       , advgetopt::GETOPT_FLAG_DEFAULT_OPTION>())
    2811             :                 , advgetopt::Help("output filename.")
    2812             :             ),
    2813             :             advgetopt::end_options()
    2814             :         };
    2815             : 
    2816           8 :         advgetopt::options_environment environment_options;
    2817           8 :         environment_options.f_project_name = "unittest";
    2818           8 :         environment_options.f_options = options;
    2819           8 :         environment_options.f_environment_flags = 0;
    2820           8 :         environment_options.f_help_header = "Usage: test simple --out <filename> ... option";
    2821           8 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    2822             : 
    2823          16 :         CATCH_WHEN("no arguments")
    2824             :         {
    2825           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "");
    2826             : 
    2827           1 :             char const * cargv[] =
    2828             :             {
    2829             :                 "/usr/bin/arguments",
    2830             :                 nullptr
    2831             :             };
    2832           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2833           1 :             char ** argv = const_cast<char **>(cargv);
    2834             : 
    2835           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    2836             : 
    2837             :             // check that the result is valid
    2838             : 
    2839             :             // an invalid parameter, MUST NOT EXIST
    2840           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2841           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2842           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2843           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2844           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2845             : 
    2846             :             // the valid parameter
    2847           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2848           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    2849           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("out"));
    2850           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    2851           1 :             CATCH_REQUIRE(opt.size("out") == 0);
    2852             : 
    2853             :             // the valid parameter is the default
    2854           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    2855           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    2856           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
    2857           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    2858           1 :             CATCH_REQUIRE(opt.size("--") == 0);
    2859             : 
    2860             :             // other parameters
    2861           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2862           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2863             :         }
    2864             : 
    2865          16 :         CATCH_WHEN("one argument")
    2866             :         {
    2867           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "my-filename.out");
    2868             : 
    2869           1 :             char const * cargv[] =
    2870             :             {
    2871             :                 "/usr/bin/arguments",
    2872             :                 nullptr
    2873             :             };
    2874           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2875           1 :             char ** argv = const_cast<char **>(cargv);
    2876             : 
    2877           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    2878             : 
    2879             :             // check that the result is valid
    2880             : 
    2881             :             // an invalid parameter, MUST NOT EXIST
    2882           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2883           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2884           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2885           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2886           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2887             : 
    2888             :             // the valid parameter
    2889           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2890           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    2891           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    2892           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    2893           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    2894           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    2895           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    2896             : 
    2897             :             // the valid parameter is the default
    2898           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    2899           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    2900           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    2901           1 :             CATCH_REQUIRE(opt.get_string("--") == "my-filename.out");
    2902           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "my-filename.out");
    2903           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    2904           1 :             CATCH_REQUIRE(opt.size("--") == 1);
    2905             : 
    2906             :             // other parameters
    2907           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2908           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2909             :         }
    2910             : 
    2911          16 :         CATCH_WHEN("three arguments")
    2912             :         {
    2913           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "my-filename.out another.out last.out");
    2914             : 
    2915           1 :             char const * cargv[] =
    2916             :             {
    2917             :                 "/usr/bin/arguments",
    2918             :                 nullptr
    2919             :             };
    2920           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2921           1 :             char ** argv = const_cast<char **>(cargv);
    2922             : 
    2923           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    2924             : 
    2925             :             // check that the result is valid
    2926             : 
    2927             :             // an invalid parameter, MUST NOT EXIST
    2928           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2929           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2930           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2931           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2932           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2933             : 
    2934             :             // the valid parameter
    2935           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2936           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    2937           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    2938           1 :             CATCH_REQUIRE(opt.get_string("out") == "last.out");
    2939           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "last.out");
    2940           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    2941           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    2942             : 
    2943             :             // the valid parameter is the default
    2944           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    2945           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    2946           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    2947           1 :             CATCH_REQUIRE(opt.get_string("--") == "last.out");
    2948           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "last.out");
    2949           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    2950           1 :             CATCH_REQUIRE(opt.size("--") == 1);
    2951             : 
    2952             :             // other parameters
    2953           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    2954           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    2955             :         }
    2956             : 
    2957          16 :         CATCH_WHEN("four arguments with a '-'")
    2958             :         {
    2959           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "my-filename.out another.out - last.out");
    2960             : 
    2961           1 :             char const * cargv[] =
    2962             :             {
    2963             :                 "/usr/bin/arguments",
    2964             :                 nullptr
    2965             :             };
    2966           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    2967           1 :             char ** argv = const_cast<char **>(cargv);
    2968             : 
    2969           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    2970             : 
    2971             :             // check that the result is valid
    2972             : 
    2973             :             // an invalid parameter, MUST NOT EXIST
    2974           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    2975           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    2976           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    2977           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    2978           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    2979             : 
    2980             :             // the valid parameter
    2981           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    2982           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    2983           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    2984           1 :             CATCH_REQUIRE(opt.get_string("out") == "last.out");
    2985           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "last.out");
    2986           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    2987           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    2988             : 
    2989             :             // the valid parameter is the default
    2990           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    2991           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    2992           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    2993           1 :             CATCH_REQUIRE(opt.get_string("--") == "last.out");
    2994           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "last.out");
    2995           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    2996           1 :             CATCH_REQUIRE(opt.size("--") == 1);
    2997             : 
    2998             :             // other parameters
    2999           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3000           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3001             :         }
    3002             : 
    3003          16 :         CATCH_WHEN("using the '--' separator and no arguments")
    3004             :         {
    3005           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--");
    3006             : 
    3007           1 :             char const * cargv[] =
    3008             :             {
    3009             :                 "/usr/bin/arguments",
    3010             :                 nullptr
    3011             :             };
    3012           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3013           1 :             char ** argv = const_cast<char **>(cargv);
    3014             : 
    3015           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3016             : 
    3017             :             // check that the result is valid
    3018             : 
    3019             :             // an invalid parameter, MUST NOT EXIST
    3020           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3021           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3022           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3023           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3024           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3025             : 
    3026             :             // the valid parameter
    3027           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3028           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3029           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("out"));
    3030           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    3031           1 :             CATCH_REQUIRE(opt.size("out") == 0);
    3032             : 
    3033             :             // the valid parameter is the default
    3034           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    3035           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    3036           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
    3037           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    3038           1 :             CATCH_REQUIRE(opt.size("--") == 0);
    3039             : 
    3040             :             // other parameters
    3041           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3042           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3043             :         }
    3044             : 
    3045          16 :         CATCH_WHEN("using the '--' separator and one argument")
    3046             :         {
    3047           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-- my-filename.out");
    3048             : 
    3049           1 :             char const * cargv[] =
    3050             :             {
    3051             :                 "/usr/bin/arguments",
    3052             :                 nullptr
    3053             :             };
    3054           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3055           1 :             char ** argv = const_cast<char **>(cargv);
    3056             : 
    3057           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3058             : 
    3059             :             // check that the result is valid
    3060             : 
    3061             :             // an invalid parameter, MUST NOT EXIST
    3062           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3063           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3064           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3065           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3066           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3067             : 
    3068             :             // the valid parameter
    3069           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3070           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3071           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    3072           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    3073           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    3074           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    3075           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    3076             : 
    3077             :             // the valid parameter is the default
    3078           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    3079           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    3080           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    3081           1 :             CATCH_REQUIRE(opt.get_string("--") == "my-filename.out");
    3082           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "my-filename.out");
    3083           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    3084           1 :             CATCH_REQUIRE(opt.size("--") == 1);
    3085             : 
    3086             :             // other parameters
    3087           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3088           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3089             :         }
    3090             : 
    3091          16 :         CATCH_WHEN("using the '--' separator and three arguments")
    3092             :         {
    3093           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-- my-filename.out -another.out --last.out");
    3094             : 
    3095           1 :             char const * cargv[] =
    3096             :             {
    3097             :                 "/usr/bin/arguments",
    3098             :                 nullptr
    3099             :             };
    3100           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3101           1 :             char ** argv = const_cast<char **>(cargv);
    3102             : 
    3103           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3104             : 
    3105             :             // check that the result is valid
    3106             : 
    3107             :             // an invalid parameter, MUST NOT EXIST
    3108           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3109           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3110           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3111           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3112           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3113             : 
    3114             :             // the valid parameter
    3115           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3116           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3117           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    3118           1 :             CATCH_REQUIRE(opt.get_string("out") == "--last.out");
    3119           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "--last.out");
    3120           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    3121           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    3122             : 
    3123             :             // the valid parameter is the default
    3124           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    3125           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    3126           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    3127           1 :             CATCH_REQUIRE(opt.get_string("--") == "--last.out");
    3128           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "--last.out");
    3129           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    3130           1 :             CATCH_REQUIRE(opt.size("--") == 1);
    3131             : 
    3132             :             // other parameters
    3133           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3134           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3135             :         }
    3136             : 
    3137          16 :         CATCH_WHEN("using the '--' separator and four arguments with a '-'")
    3138             :         {
    3139           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-- my-filename.out -another.out - --last.out");
    3140             : 
    3141           1 :             char const * cargv[] =
    3142             :             {
    3143             :                 "/usr/bin/arguments",
    3144             :                 nullptr
    3145             :             };
    3146           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3147           1 :             char ** argv = const_cast<char **>(cargv);
    3148             : 
    3149           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3150             : 
    3151             :             // check that the result is valid
    3152             : 
    3153             :             // an invalid parameter, MUST NOT EXIST
    3154           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3155           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3156           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3157           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3158           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3159             : 
    3160             :             // the valid parameter
    3161           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3162           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3163           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    3164           1 :             CATCH_REQUIRE(opt.get_string("out") == "--last.out");
    3165           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "--last.out");
    3166           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    3167           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    3168             : 
    3169             :             // the valid parameter is the default
    3170           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    3171           1 :             CATCH_REQUIRE(opt.get_option("--") == opt.get_option("out"));
    3172           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    3173           1 :             CATCH_REQUIRE(opt.get_string("--") == "--last.out");
    3174           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "--last.out");
    3175           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    3176           1 :             CATCH_REQUIRE(opt.size("--") == 1);
    3177             : 
    3178             :             // other parameters
    3179           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3180           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3181             :         }
    3182             :     CATCH_END_SECTION()
    3183             : 
    3184          32 :     CATCH_START_SECTION("Verify that we can have a non-require argument with an invalid default")
    3185           2 :         advgetopt::option const options[] =
    3186             :         {
    3187             :             advgetopt::define_option(
    3188             :                   advgetopt::Name("before")
    3189             :                 , advgetopt::ShortName('b')
    3190             :                 , advgetopt::Flags(advgetopt::command_flags<>())
    3191             :                 , advgetopt::Help("appears before.")
    3192             :                 , advgetopt::DefaultValue("early")
    3193             :             ),
    3194             :             advgetopt::define_option(
    3195             :                   advgetopt::Name("out")
    3196             :                 , advgetopt::ShortName('o')
    3197             :                 , advgetopt::Flags(advgetopt::command_flags<>())
    3198             :                 , advgetopt::Help("output filename.")
    3199             :                 , advgetopt::DefaultValue("default-name")
    3200             :                 , advgetopt::Validator("/[a-z]+/")
    3201             :             ),
    3202             :             advgetopt::define_option(
    3203             :                   advgetopt::Name("after")
    3204             :                 , advgetopt::ShortName('a')
    3205             :                 , advgetopt::Flags(advgetopt::command_flags<>())
    3206             :                 , advgetopt::Help("appears after.")
    3207             :                 , advgetopt::DefaultValue("late")
    3208             :             ),
    3209             :             advgetopt::end_options()
    3210             :         };
    3211             : 
    3212           2 :         advgetopt::options_environment environment_options;
    3213           2 :         environment_options.f_project_name = "unittest";
    3214           2 :         environment_options.f_options = options;
    3215           2 :         environment_options.f_environment_flags = 0;
    3216           2 :         environment_options.f_help_header = "Usage: test simple --out <filename> ... option";
    3217           2 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    3218             : 
    3219           4 :         CATCH_WHEN("no parameters to arguments")
    3220             :         {
    3221           1 :             char const * cargv[] =
    3222             :             {
    3223             :                 "/usr/bin/arguments",
    3224             :                 "--before",
    3225             :                 "--out",
    3226             :                 "--after",
    3227             :                 nullptr
    3228             :             };
    3229           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3230           1 :             char ** argv = const_cast<char **>(cargv);
    3231             : 
    3232           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3233             : 
    3234             :             // check that the result is valid
    3235             : 
    3236             :             // an invalid parameter, MUST NOT EXIST
    3237           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3238           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3239           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3240           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3241           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3242             : 
    3243             :             // the valid parameter
    3244           1 :             CATCH_REQUIRE(opt.get_option("before") != nullptr);
    3245           1 :             CATCH_REQUIRE(opt.get_option('b') != nullptr);
    3246           1 :             CATCH_REQUIRE(opt.is_defined("before"));
    3247           1 :             CATCH_REQUIRE(opt.get_string("before") == "early");
    3248           1 :             CATCH_REQUIRE(opt.get_string("before", 0) == "early");
    3249           1 :             CATCH_REQUIRE(opt.get_default("before") == "early");
    3250           1 :             CATCH_REQUIRE(opt.size("before") == 1);
    3251             : 
    3252             :             // the valid parameter
    3253           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3254           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3255           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    3256           1 :             CATCH_REQUIRE(opt.get_string("out") == "default-name");
    3257           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "default-name");
    3258           1 :             CATCH_REQUIRE(opt.get_default("out") == "default-name");
    3259           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    3260             : 
    3261             :             // the valid parameter
    3262           1 :             CATCH_REQUIRE(opt.get_option("after") != nullptr);
    3263           1 :             CATCH_REQUIRE(opt.get_option('a') != nullptr);
    3264           1 :             CATCH_REQUIRE(opt.is_defined("after"));
    3265           1 :             CATCH_REQUIRE(opt.get_string("after") == "late");
    3266           1 :             CATCH_REQUIRE(opt.get_string("after", 0) == "late");
    3267           1 :             CATCH_REQUIRE(opt.get_default("after") == "late");
    3268           1 :             CATCH_REQUIRE(opt.size("after") == 1);
    3269             : 
    3270             :             // other parameters
    3271           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3272           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3273             :         }
    3274             : 
    3275           4 :         CATCH_WHEN("parameters to some arguments")
    3276             :         {
    3277           1 :             char const * cargv[] =
    3278             :             {
    3279             :                 "/usr/bin/arguments",
    3280             :                 "--before",
    3281             :                 "avant",
    3282             :                 "--out",
    3283             :                 "--after",
    3284             :                 "apr\xC3\xA8s", // UTF-8 of "`e"
    3285             :                 nullptr
    3286             :             };
    3287           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3288           1 :             char ** argv = const_cast<char **>(cargv);
    3289             : 
    3290           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3291             : 
    3292             :             // check that the result is valid
    3293             : 
    3294             :             // an invalid parameter, MUST NOT EXIST
    3295           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3296           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3297           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3298           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3299           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3300             : 
    3301             :             // the valid parameter
    3302           1 :             CATCH_REQUIRE(opt.get_option("before") != nullptr);
    3303           1 :             CATCH_REQUIRE(opt.get_option('b') != nullptr);
    3304           1 :             CATCH_REQUIRE(opt.is_defined("before"));
    3305           1 :             CATCH_REQUIRE(opt.get_string("before") == "avant");
    3306           1 :             CATCH_REQUIRE(opt.get_string("before", 0) == "avant");
    3307           1 :             CATCH_REQUIRE(opt.get_default("before") == "early");
    3308           1 :             CATCH_REQUIRE(opt.size("before") == 1);
    3309             : 
    3310             :             // the valid parameter
    3311           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3312           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3313           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    3314           1 :             CATCH_REQUIRE(opt.get_string("out") == "default-name");
    3315           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "default-name");
    3316           1 :             CATCH_REQUIRE(opt.get_default("out") == "default-name");
    3317           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    3318             : 
    3319             :             // the valid parameter
    3320           1 :             CATCH_REQUIRE(opt.get_option("after") != nullptr);
    3321           1 :             CATCH_REQUIRE(opt.get_option('a') != nullptr);
    3322           1 :             CATCH_REQUIRE(opt.is_defined("after"));
    3323           1 :             CATCH_REQUIRE(opt.get_string("after") == "apr\xC3\xA8s");
    3324           1 :             CATCH_REQUIRE(opt.get_string("after", 0) == "apr\xC3\xA8s");
    3325           1 :             CATCH_REQUIRE(opt.get_default("after") == "late");
    3326           1 :             CATCH_REQUIRE(opt.size("after") == 1);
    3327             : 
    3328             :             // other parameters
    3329           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3330           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3331             :         }
    3332             :     CATCH_END_SECTION()
    3333          16 : }
    3334             : 
    3335             : 
    3336          14 : CATCH_TEST_CASE("default_arguments", "[arguments][valid][multiple][getopt]")
    3337             : {
    3338          24 :     CATCH_START_SECTION("Verify a simple [<filename> ...] argument")
    3339           4 :         advgetopt::option const options[] =
    3340             :         {
    3341             :             advgetopt::define_option(
    3342             :                   advgetopt::Name("out")
    3343             :                 , advgetopt::ShortName('o')
    3344             :                 , advgetopt::Flags(advgetopt::any_flags<advgetopt::GETOPT_FLAG_COMMAND_LINE
    3345             :                                                       , advgetopt::GETOPT_FLAG_DEFAULT_OPTION
    3346             :                                                       , advgetopt::GETOPT_FLAG_MULTIPLE>())
    3347             :                 , advgetopt::Help("output filename.")
    3348             :             ),
    3349             :             advgetopt::end_options()
    3350             :         };
    3351             : 
    3352           4 :         advgetopt::options_environment environment_options;
    3353           4 :         environment_options.f_project_name = "unittest";
    3354           4 :         environment_options.f_options = options;
    3355           4 :         environment_options.f_environment_flags = 0;
    3356           4 :         environment_options.f_help_header = "Usage: test simple [<filename>] option";
    3357             : 
    3358           8 :         CATCH_WHEN("no arguments")
    3359             :         {
    3360           1 :             char const * cargv[] =
    3361             :             {
    3362             :                 "/usr/bin/arguments",
    3363             :                 nullptr
    3364             :             };
    3365           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3366           1 :             char ** argv = const_cast<char **>(cargv);
    3367             : 
    3368           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3369             : 
    3370             :             // check that the result is valid
    3371             : 
    3372             :             // an invalid parameter, MUST NOT EXIST
    3373           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3374           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3375           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3376           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3377           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3378             : 
    3379             :             // the valid parameter
    3380           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3381           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3382           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("out"));
    3383           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    3384           1 :             CATCH_REQUIRE(opt.size("out") == 0);
    3385             : 
    3386             :             // other parameters
    3387           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3388           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3389             :         }
    3390             : 
    3391           8 :         CATCH_WHEN("one argument")
    3392             :         {
    3393           1 :             char const * cargv[] =
    3394             :             {
    3395             :                 "/usr/bin/arguments",
    3396             :                 "my-filename.out",
    3397             :                 nullptr
    3398             :             };
    3399           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3400           1 :             char ** argv = const_cast<char **>(cargv);
    3401             : 
    3402           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3403             : 
    3404             :             // check that the result is valid
    3405             : 
    3406             :             // an invalid parameter, MUST NOT EXIST
    3407           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3408           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3409           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3410           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3411           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3412             : 
    3413             :             // the valid parameter
    3414           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3415           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3416           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    3417           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    3418           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    3419           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    3420           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    3421             : 
    3422             :             // other parameters
    3423           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3424           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3425             :         }
    3426             : 
    3427           8 :         CATCH_WHEN("three arguments")
    3428             :         {
    3429           1 :             char const * cargv[] =
    3430             :             {
    3431             :                 "/usr/bin/arguments",
    3432             :                 "my-filename.out",
    3433             :                 "another.out",
    3434             :                 "last.out",
    3435             :                 nullptr
    3436             :             };
    3437           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3438           1 :             char ** argv = const_cast<char **>(cargv);
    3439             : 
    3440           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3441             : 
    3442             :             // check that the result is valid
    3443             : 
    3444             :             // an invalid parameter, MUST NOT EXIST
    3445           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3446           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3447           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3448           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3449           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3450             : 
    3451             :             // the valid parameter
    3452           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3453           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3454           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    3455           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    3456           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    3457           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    3458           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    3459           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    3460           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    3461             : 
    3462             :             // other parameters
    3463           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3464           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3465             :         }
    3466             : 
    3467           8 :         CATCH_WHEN("four arguments with a '-'")
    3468             :         {
    3469           1 :             char const * cargv[] =
    3470             :             {
    3471             :                 "/usr/bin/arguments",
    3472             :                 "my-filename.out",
    3473             :                 "another.out",
    3474             :                 "-",
    3475             :                 "last.out",
    3476             :                 nullptr
    3477             :             };
    3478           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3479           1 :             char ** argv = const_cast<char **>(cargv);
    3480             : 
    3481           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3482             : 
    3483             :             // check that the result is valid
    3484             : 
    3485             :             // an invalid parameter, MUST NOT EXIST
    3486           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3487           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3488           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3489           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3490           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3491             : 
    3492             :             // the valid parameter
    3493           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3494           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3495           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    3496           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    3497           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    3498           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    3499           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "-");
    3500           1 :             CATCH_REQUIRE(opt.get_string("out", 3) == "last.out");
    3501           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    3502           1 :             CATCH_REQUIRE(opt.size("out") == 4);
    3503             : 
    3504             :             // other parameters
    3505           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3506           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3507             :         }
    3508             :     CATCH_END_SECTION()
    3509             : 
    3510          24 :     CATCH_START_SECTION("Verify a simple [<filename> ...] argument with the default name (a.k.a. \"--\")")
    3511           4 :         advgetopt::option const options[] =
    3512             :         {
    3513             :             advgetopt::define_option(
    3514             :                   advgetopt::Name("--")
    3515             :                 , advgetopt::Flags(advgetopt::any_flags<advgetopt::GETOPT_FLAG_COMMAND_LINE
    3516             :                                                       , advgetopt::GETOPT_FLAG_DEFAULT_OPTION
    3517             :                                                       , advgetopt::GETOPT_FLAG_MULTIPLE>())
    3518             :                 , advgetopt::Help("output filename.")
    3519             :             ),
    3520             :             advgetopt::end_options()
    3521             :         };
    3522             : 
    3523           4 :         advgetopt::options_environment environment_options;
    3524           4 :         environment_options.f_project_name = "unittest";
    3525           4 :         environment_options.f_options = options;
    3526           4 :         environment_options.f_environment_flags = 0;
    3527           4 :         environment_options.f_help_header = "Usage: test simple [<filename>] option";
    3528             : 
    3529           8 :         CATCH_WHEN("no arguments")
    3530             :         {
    3531           1 :             char const * cargv[] =
    3532             :             {
    3533             :                 "/usr/bin/arguments",
    3534             :                 nullptr
    3535             :             };
    3536           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3537           1 :             char ** argv = const_cast<char **>(cargv);
    3538             : 
    3539           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3540             : 
    3541             :             // check that the result is valid
    3542             : 
    3543             :             // an invalid parameter, MUST NOT EXIST
    3544           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3545           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3546           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3547           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3548           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3549             : 
    3550             :             // the valid parameter
    3551           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    3552           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("--"));
    3553           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    3554           1 :             CATCH_REQUIRE(opt.size("--") == 0);
    3555             : 
    3556             :             // other parameters
    3557           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3558           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3559             :         }
    3560             : 
    3561           8 :         CATCH_WHEN("one argument")
    3562             :         {
    3563           1 :             char const * cargv[] =
    3564             :             {
    3565             :                 "/usr/bin/arguments",
    3566             :                 "my-filename.out",
    3567             :                 nullptr
    3568             :             };
    3569           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3570           1 :             char ** argv = const_cast<char **>(cargv);
    3571             : 
    3572           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3573             : 
    3574             :             // check that the result is valid
    3575             : 
    3576             :             // an invalid parameter, MUST NOT EXIST
    3577           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3578           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3579           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3580           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3581           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3582             : 
    3583             :             // the valid parameter
    3584           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    3585           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    3586           1 :             CATCH_REQUIRE(opt.get_string("--") == "my-filename.out");
    3587           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "my-filename.out");
    3588           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    3589           1 :             CATCH_REQUIRE(opt.size("--") == 1);
    3590             : 
    3591             :             // other parameters
    3592           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3593           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3594             :         }
    3595             : 
    3596           8 :         CATCH_WHEN("three arguments")
    3597             :         {
    3598           1 :             char const * cargv[] =
    3599             :             {
    3600             :                 "/usr/bin/arguments",
    3601             :                 "my-filename.out",
    3602             :                 "another.out",
    3603             :                 "last.out",
    3604             :                 nullptr
    3605             :             };
    3606           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3607           1 :             char ** argv = const_cast<char **>(cargv);
    3608             : 
    3609           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3610             : 
    3611             :             // check that the result is valid
    3612             : 
    3613             :             // an invalid parameter, MUST NOT EXIST
    3614           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3615           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3616           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3617           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3618           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3619             : 
    3620             :             // the valid parameter
    3621           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    3622           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    3623           1 :             CATCH_REQUIRE(opt.get_string("--") == "my-filename.out");
    3624           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "my-filename.out");
    3625           1 :             CATCH_REQUIRE(opt.get_string("--", 1) == "another.out");
    3626           1 :             CATCH_REQUIRE(opt.get_string("--", 2) == "last.out");
    3627           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    3628           1 :             CATCH_REQUIRE(opt.size("--") == 3);
    3629             : 
    3630             :             // other parameters
    3631           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3632           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3633             :         }
    3634             : 
    3635           8 :         CATCH_WHEN("four arguments with a '-'")
    3636             :         {
    3637           1 :             char const * cargv[] =
    3638             :             {
    3639             :                 "/usr/bin/arguments",
    3640             :                 "my-filename.out",
    3641             :                 "another.out",
    3642             :                 "-",
    3643             :                 "last.out",
    3644             :                 nullptr
    3645             :             };
    3646           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3647           1 :             char ** argv = const_cast<char **>(cargv);
    3648             : 
    3649           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3650             : 
    3651             :             // check that the result is valid
    3652             : 
    3653             :             // an invalid parameter, MUST NOT EXIST
    3654           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3655           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3656           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3657           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3658           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3659             : 
    3660             :             // the valid parameter
    3661           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    3662           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    3663           1 :             CATCH_REQUIRE(opt.get_string("--") == "my-filename.out");
    3664           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "my-filename.out");
    3665           1 :             CATCH_REQUIRE(opt.get_string("--", 1) == "another.out");
    3666           1 :             CATCH_REQUIRE(opt.get_string("--", 2) == "-");
    3667           1 :             CATCH_REQUIRE(opt.get_string("--", 3) == "last.out");
    3668           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    3669           1 :             CATCH_REQUIRE(opt.size("--") == 4);
    3670             : 
    3671             :             // other parameters
    3672           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3673           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3674             :         }
    3675             :     CATCH_END_SECTION()
    3676             : 
    3677          24 :     CATCH_START_SECTION("Verify a simple [<filename> ...] argument in a variable")
    3678           4 :         advgetopt::option const options[] =
    3679             :         {
    3680             :             advgetopt::define_option(
    3681             :                   advgetopt::Name("out")
    3682             :                 , advgetopt::ShortName('o')
    3683             :                 , advgetopt::Flags(advgetopt::any_flags<advgetopt::GETOPT_FLAG_ENVIRONMENT_VARIABLE
    3684             :                                                       , advgetopt::GETOPT_FLAG_DEFAULT_OPTION
    3685             :                                                       , advgetopt::GETOPT_FLAG_MULTIPLE>())
    3686             :                 , advgetopt::Help("output filename.")
    3687             :             ),
    3688             :             advgetopt::end_options()
    3689             :         };
    3690             : 
    3691           4 :         advgetopt::options_environment environment_options;
    3692           4 :         environment_options.f_project_name = "unittest";
    3693           4 :         environment_options.f_options = options;
    3694           4 :         environment_options.f_environment_flags = 0;
    3695           4 :         environment_options.f_help_header = "Usage: test simple --out <filename> ... option";
    3696           4 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    3697             : 
    3698           8 :         CATCH_WHEN("no arguments")
    3699             :         {
    3700           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "");
    3701             : 
    3702           1 :             char const * cargv[] =
    3703             :             {
    3704             :                 "/usr/bin/arguments",
    3705             :                 nullptr
    3706             :             };
    3707           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3708           1 :             char ** argv = const_cast<char **>(cargv);
    3709             : 
    3710           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3711             : 
    3712             :             // check that the result is valid
    3713             : 
    3714             :             // an invalid parameter, MUST NOT EXIST
    3715           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3716           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3717           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3718           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3719           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3720             : 
    3721             :             // the valid parameter
    3722           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3723           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3724           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("out"));
    3725           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    3726           1 :             CATCH_REQUIRE(opt.size("out") == 0);
    3727             : 
    3728             :             // other parameters
    3729           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3730           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3731             :         }
    3732             : 
    3733           8 :         CATCH_WHEN("one argument")
    3734             :         {
    3735           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "my-filename.out");
    3736             : 
    3737           1 :             char const * cargv[] =
    3738             :             {
    3739             :                 "/usr/bin/arguments",
    3740             :                 nullptr
    3741             :             };
    3742           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3743           1 :             char ** argv = const_cast<char **>(cargv);
    3744             : 
    3745           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3746             : 
    3747             :             // check that the result is valid
    3748             : 
    3749             :             // an invalid parameter, MUST NOT EXIST
    3750           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3751           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3752           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3753           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3754           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3755             : 
    3756             :             // the valid parameter
    3757           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3758           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3759           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    3760           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    3761           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    3762           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    3763           1 :             CATCH_REQUIRE(opt.size("out") == 1);
    3764             : 
    3765             :             // other parameters
    3766           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3767           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3768             :         }
    3769             : 
    3770           8 :         CATCH_WHEN("three arguments")
    3771             :         {
    3772           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "my-filename.out another.out last.out");
    3773             : 
    3774           1 :             char const * cargv[] =
    3775             :             {
    3776             :                 "/usr/bin/arguments",
    3777             :                 nullptr
    3778             :             };
    3779           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3780           1 :             char ** argv = const_cast<char **>(cargv);
    3781             : 
    3782           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3783             : 
    3784             :             // check that the result is valid
    3785             : 
    3786             :             // an invalid parameter, MUST NOT EXIST
    3787           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3788           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3789           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3790           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3791           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3792             : 
    3793             :             // the valid parameter
    3794           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3795           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3796           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    3797           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    3798           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    3799           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    3800           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "last.out");
    3801           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    3802           1 :             CATCH_REQUIRE(opt.size("out") == 3);
    3803             : 
    3804             :             // other parameters
    3805           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3806           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3807             :         }
    3808             : 
    3809           8 :         CATCH_WHEN("four arguments with a '-'")
    3810             :         {
    3811           2 :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "my-filename.out another.out - last.out");
    3812             : 
    3813           1 :             char const * cargv[] =
    3814             :             {
    3815             :                 "/usr/bin/arguments",
    3816             :                 nullptr
    3817             :             };
    3818           1 :             int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3819           1 :             char ** argv = const_cast<char **>(cargv);
    3820             : 
    3821           2 :             advgetopt::getopt opt(environment_options, argc, argv);
    3822             : 
    3823             :             // check that the result is valid
    3824             : 
    3825             :             // an invalid parameter, MUST NOT EXIST
    3826           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3827           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3828           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    3829           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3830           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    3831             : 
    3832             :             // the valid parameter
    3833           1 :             CATCH_REQUIRE(opt.get_option("out") != nullptr);
    3834           1 :             CATCH_REQUIRE(opt.get_option('o') != nullptr);
    3835           1 :             CATCH_REQUIRE(opt.is_defined("out"));
    3836           1 :             CATCH_REQUIRE(opt.get_string("out") == "my-filename.out");
    3837           1 :             CATCH_REQUIRE(opt.get_string("out", 0) == "my-filename.out");
    3838           1 :             CATCH_REQUIRE(opt.get_string("out", 1) == "another.out");
    3839           1 :             CATCH_REQUIRE(opt.get_string("out", 2) == "-");
    3840           1 :             CATCH_REQUIRE(opt.get_string("out", 3) == "last.out");
    3841           1 :             CATCH_REQUIRE(opt.get_default("out").empty());
    3842           1 :             CATCH_REQUIRE(opt.size("out") == 4);
    3843             : 
    3844             :             // other parameters
    3845           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3846           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3847             :         }
    3848             :     CATCH_END_SECTION()
    3849          12 : }
    3850             : 
    3851             : 
    3852           5 : CATCH_TEST_CASE("manual_arguments", "[arguments][valid][getopt]")
    3853             : {
    3854           6 :     CATCH_START_SECTION("Verify a few arguments added manually")
    3855             : 
    3856             :         // create a getopt object
    3857             :         //
    3858           1 :         advgetopt::options_environment environment_options;
    3859           1 :         environment_options.f_project_name = "unittest";
    3860           1 :         environment_options.f_help_header = "Usage: test simple --verbose option";
    3861           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    3862             : 
    3863           2 :         advgetopt::getopt opt(environment_options);
    3864             : 
    3865             :             // an invalid parameter, MUST NEVER EXIST
    3866             :             //
    3867           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3868           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3869           1 :             CATCH_REQUIRE_THROWS_MATCHES(
    3870             :                       opt.is_defined("invalid-parameter")
    3871             :                     , advgetopt::getopt_initialization
    3872             :                     , Catch::Matchers::ExceptionMessage(
    3873             :                                   "getopt_exception: function called too soon, parser is not done yet (i.e. is_defined(), get_string(), get_integer(), get_double() cannot be called until the parser is done)"));
    3874           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3875           1 :             CATCH_REQUIRE_THROWS_MATCHES(
    3876             :                       opt.size("invalid-parameter")
    3877             :                     , advgetopt::getopt_initialization
    3878             :                     , Catch::Matchers::ExceptionMessage(
    3879             :                                   "getopt_exception: function called too soon, parser is not done yet (i.e. is_defined(), get_string(), get_integer(), get_double() cannot be called until the parser is done)"));
    3880             : 
    3881             :             // verbose
    3882             :             //
    3883           1 :             CATCH_REQUIRE(opt.get_option("verbose") == nullptr);
    3884           1 :             CATCH_REQUIRE(opt.get_option('v') == nullptr);
    3885           1 :             CATCH_REQUIRE_THROWS_MATCHES(
    3886             :                       opt.is_defined("verbose")
    3887             :                     , advgetopt::getopt_initialization
    3888             :                     , Catch::Matchers::ExceptionMessage(
    3889             :                                   "getopt_exception: function called too soon, parser is not done yet (i.e. is_defined(), get_string(), get_integer(), get_double() cannot be called until the parser is done)"));
    3890           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    3891           1 :             CATCH_REQUIRE_THROWS_MATCHES(
    3892             :                       opt.size("verbose")
    3893             :                     , advgetopt::getopt_initialization
    3894             :                     , Catch::Matchers::ExceptionMessage(
    3895             :                                   "getopt_exception: function called too soon, parser is not done yet (i.e. is_defined(), get_string(), get_integer(), get_double() cannot be called until the parser is done)"));
    3896             : 
    3897             :             // help
    3898             :             //
    3899           1 :             CATCH_REQUIRE(opt.get_option("help") == nullptr);
    3900           1 :             CATCH_REQUIRE(opt.get_option('h') == nullptr);
    3901           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    3902             : 
    3903             :             // default
    3904             :             //
    3905           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
    3906           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    3907             : 
    3908             :             // other parameters
    3909             :             //
    3910           1 :             CATCH_REQUIRE(opt.get_program_name().empty());
    3911           1 :             CATCH_REQUIRE(opt.get_program_fullname().empty());
    3912             : 
    3913             :         // setup the program name early
    3914             :         //
    3915           1 :         char const * cargv[] =
    3916             :         {
    3917             :             "/usr/bin/arguments",
    3918             :             "--verbose",
    3919             :             "--help",
    3920             :             nullptr
    3921             :         };
    3922           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    3923           1 :         char ** argv = const_cast<char **>(cargv);
    3924             : 
    3925           1 :         opt.parse_program_name(argv);
    3926             : 
    3927             :             // an invalid parameter, MUST NEVER EXIST
    3928             :             //
    3929           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3930           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3931           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3932             : 
    3933             :             // verbose
    3934             :             //
    3935           1 :             CATCH_REQUIRE(opt.get_option("verbose") == nullptr);
    3936           1 :             CATCH_REQUIRE(opt.get_option('v') == nullptr);
    3937           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    3938             : 
    3939             :             // help
    3940             :             //
    3941           1 :             CATCH_REQUIRE(opt.get_option("help") == nullptr);
    3942           1 :             CATCH_REQUIRE(opt.get_option('h') == nullptr);
    3943           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    3944             : 
    3945             :             // default
    3946             :             //
    3947           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
    3948           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    3949             : 
    3950             :             // other parameters
    3951             :             //
    3952           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3953           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3954             : 
    3955             :         // verify nullptr has no effect
    3956             :         //
    3957           1 :         opt.parse_options_info(nullptr);
    3958             : 
    3959             :             // an invalid parameter, MUST NEVER EXIST
    3960             :             //
    3961           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    3962           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    3963           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    3964             : 
    3965             :             // verbose
    3966             :             //
    3967           1 :             CATCH_REQUIRE(opt.get_option("verbose") == nullptr);
    3968           1 :             CATCH_REQUIRE(opt.get_option('v') == nullptr);
    3969           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    3970             : 
    3971             :             // help
    3972             :             //
    3973           1 :             CATCH_REQUIRE(opt.get_option("help") == nullptr);
    3974           1 :             CATCH_REQUIRE(opt.get_option('h') == nullptr);
    3975           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    3976             : 
    3977             :             // default
    3978             :             //
    3979           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
    3980           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    3981             : 
    3982             :             // other parameters
    3983             :             //
    3984           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    3985           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    3986             : 
    3987             :         // add --verbose
    3988             :         //
    3989           1 :         advgetopt::option const verbose_option[] =
    3990             :         {
    3991             :             advgetopt::define_option(
    3992             :                   advgetopt::Name("verbose")
    3993             :                 , advgetopt::ShortName('v')
    3994             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    3995             :                 , advgetopt::Help("print info as we work.")
    3996             :             ),
    3997             :             advgetopt::end_options()
    3998             :         };
    3999           1 :         opt.parse_options_info(verbose_option);
    4000             : 
    4001             :             // an invalid parameter, MUST NEVER EXIST
    4002             :             //
    4003           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    4004           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    4005           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    4006             : 
    4007             :             // verbose
    4008             :             //
    4009           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    4010           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
    4011           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    4012             : 
    4013             :             // help
    4014             :             //
    4015           1 :             CATCH_REQUIRE(opt.get_option("help") == nullptr);
    4016           1 :             CATCH_REQUIRE(opt.get_option('h') == nullptr);
    4017           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    4018             : 
    4019             :             // default
    4020             :             //
    4021           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
    4022           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    4023             : 
    4024             :             // other parameters
    4025             :             //
    4026           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    4027           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    4028             : 
    4029             :         // add --help
    4030             :         //
    4031           1 :         advgetopt::option const help_option[] =
    4032             :         {
    4033             :             advgetopt::define_option(
    4034             :                   advgetopt::Name("help")
    4035             :                 , advgetopt::ShortName('h')
    4036             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    4037             :                 , advgetopt::Help("print this help screen.")
    4038             :             ),
    4039             :             advgetopt::end_options()
    4040             :         };
    4041           1 :         opt.parse_options_info(help_option);
    4042             : 
    4043             :             // an invalid parameter, MUST NEVER EXIST
    4044             :             //
    4045           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    4046           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    4047           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    4048             : 
    4049             :             // verbose
    4050             :             //
    4051           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    4052           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
    4053           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    4054             : 
    4055             :             // help
    4056             :             //
    4057           1 :             CATCH_REQUIRE(opt.get_option("help") != nullptr);
    4058           1 :             CATCH_REQUIRE(opt.get_option('h') != nullptr);
    4059           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    4060             : 
    4061             :             // default
    4062             :             //
    4063           1 :             CATCH_REQUIRE(opt.get_option("--") == nullptr);
    4064           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    4065             : 
    4066             :             // other parameters
    4067             :             //
    4068           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    4069           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    4070             : 
    4071             :         // add -- (default option)
    4072             :         //
    4073           1 :         advgetopt::option const default_option[] =
    4074             :         {
    4075             :             advgetopt::define_option(
    4076             :                   advgetopt::Name("--")
    4077             :                 , advgetopt::Flags(advgetopt::all_flags<advgetopt::GETOPT_FLAG_MULTIPLE>())
    4078             :                 , advgetopt::Help("filenames to handle by this command.")
    4079             :             ),
    4080             :             advgetopt::end_options()
    4081             :         };
    4082           1 :         opt.parse_options_info(default_option);
    4083             : 
    4084             :             // an invalid parameter, MUST NEVER EXIST
    4085             :             //
    4086           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    4087           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    4088           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    4089             : 
    4090             :             // verbose
    4091             :             //
    4092           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    4093           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
    4094           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    4095             : 
    4096             :             // help
    4097             :             //
    4098           1 :             CATCH_REQUIRE(opt.get_option("help") != nullptr);
    4099           1 :             CATCH_REQUIRE(opt.get_option('h') != nullptr);
    4100           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    4101             : 
    4102             :             // default
    4103             :             //
    4104           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    4105           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    4106             : 
    4107             :             // other parameters
    4108             :             //
    4109           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    4110           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    4111             : 
    4112             :         // first parse the environment variable
    4113             :         //
    4114           2 :         snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "file.exe file.so file.dll file.lib file.a");
    4115           1 :         opt.parse_environment_variable();
    4116             : 
    4117             :             // an invalid parameter, MUST NEVER EXIST
    4118             :             //
    4119           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    4120           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    4121           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    4122           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    4123           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    4124             : 
    4125             :             // verbose
    4126             :             //
    4127           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    4128           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
    4129           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("verbose"));
    4130           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    4131           1 :             CATCH_REQUIRE(opt.size("verbose") == 0);
    4132             : 
    4133             :             // help
    4134             :             //
    4135           1 :             CATCH_REQUIRE(opt.get_option("help") != nullptr);
    4136           1 :             CATCH_REQUIRE(opt.get_option('h') != nullptr);
    4137           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("help"));
    4138           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    4139           1 :             CATCH_REQUIRE(opt.size("help") == 0);
    4140             : 
    4141             :             // default
    4142             :             //
    4143           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    4144           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    4145           1 :             CATCH_REQUIRE(opt.get_string("--") == "file.exe");
    4146           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "file.exe");
    4147           1 :             CATCH_REQUIRE(opt.get_string("--", 1) == "file.so");
    4148           1 :             CATCH_REQUIRE(opt.get_string("--", 2) == "file.dll");
    4149           1 :             CATCH_REQUIRE(opt.get_string("--", 3) == "file.lib");
    4150           1 :             CATCH_REQUIRE(opt.get_string("--", 4) == "file.a");
    4151           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    4152           1 :             CATCH_REQUIRE(opt.size("--") == 5);
    4153             : 
    4154             :             // other parameters
    4155             :             //
    4156           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    4157           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    4158             : 
    4159             :         // now parse our command line arguments
    4160             :         //
    4161           1 :         opt.parse_arguments(argc, argv, advgetopt::option_source_t::SOURCE_COMMAND_LINE);
    4162             : 
    4163             :             // an invalid parameter, MUST NEVER EXIST
    4164             :             //
    4165           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    4166           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    4167           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    4168           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    4169           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    4170             : 
    4171             :             // verbose
    4172             :             //
    4173           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    4174           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
    4175           1 :             CATCH_REQUIRE(opt.is_defined("verbose"));
    4176           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    4177           1 :             CATCH_REQUIRE(opt.size("verbose") == 1);
    4178             : 
    4179             :             // help
    4180             :             //
    4181           1 :             CATCH_REQUIRE(opt.get_option("help") != nullptr);
    4182           1 :             CATCH_REQUIRE(opt.get_option('h') != nullptr);
    4183           1 :             CATCH_REQUIRE(opt.is_defined("help"));
    4184           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    4185           1 :             CATCH_REQUIRE(opt.size("help") == 1);
    4186             : 
    4187             :             // default
    4188             :             //
    4189           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    4190           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    4191           1 :             CATCH_REQUIRE(opt.get_string("--") == "file.exe");
    4192           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "file.exe");
    4193           1 :             CATCH_REQUIRE(opt.get_string("--", 1) == "file.so");
    4194           1 :             CATCH_REQUIRE(opt.get_string("--", 2) == "file.dll");
    4195           1 :             CATCH_REQUIRE(opt.get_string("--", 3) == "file.lib");
    4196           1 :             CATCH_REQUIRE(opt.get_string("--", 4) == "file.a");
    4197           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    4198           1 :             CATCH_REQUIRE(opt.size("--") == 5);
    4199             : 
    4200             :             // other parameters
    4201             :             //
    4202           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    4203           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    4204             : 
    4205             :     CATCH_END_SECTION()
    4206             : 
    4207           6 :     CATCH_START_SECTION("Verify a few arguments added manually and system options")
    4208             :         // create a getopt object with options
    4209             :         //
    4210           1 :         advgetopt::option const options[] =
    4211             :         {
    4212             :             advgetopt::define_option(
    4213             :                   advgetopt::Name("verbose")
    4214             :                 , advgetopt::ShortName('v')
    4215             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    4216             :                 , advgetopt::Help("print info as we work.")
    4217             :             ),
    4218             :             advgetopt::define_option(
    4219             :                   advgetopt::Name("size")
    4220             :                 , advgetopt::ShortName('s')
    4221             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    4222             :                 , advgetopt::DefaultValue("123")
    4223             :                 , advgetopt::Help("define a size.")
    4224             :             ),
    4225             :             advgetopt::define_option(
    4226             :                   advgetopt::Name("--")
    4227             :                 , advgetopt::Flags(advgetopt::all_flags<advgetopt::GETOPT_FLAG_MULTIPLE>())
    4228             :                 , advgetopt::Help("filenames to handle by this command.")
    4229             :             ),
    4230             :             advgetopt::end_options()
    4231             :         };
    4232             : 
    4233           1 :         advgetopt::options_environment environment_options;
    4234           1 :         environment_options.f_project_name = "unittest";
    4235           1 :         environment_options.f_options = options;
    4236           1 :         environment_options.f_environment_flags = advgetopt::GETOPT_ENVIRONMENT_FLAG_SYSTEM_PARAMETERS;
    4237           1 :         environment_options.f_help_header = "Usage: test simple --verbose option";
    4238           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    4239             : 
    4240           2 :         advgetopt::getopt opt(environment_options);
    4241             : 
    4242             :             // an invalid parameter, MUST NEVER EXIST
    4243             :             //
    4244           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    4245           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    4246           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    4247             : 
    4248             :             // verbose
    4249             :             //
    4250           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    4251           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
    4252           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    4253             : 
    4254             :             // help
    4255             :             //
    4256           1 :             CATCH_REQUIRE(opt.get_option("help") != nullptr);
    4257           1 :             CATCH_REQUIRE(opt.get_option('h') != nullptr);
    4258           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    4259             : 
    4260             :             // default
    4261             :             //
    4262           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    4263           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    4264             : 
    4265             :             // size
    4266             :             //
    4267           1 :             CATCH_REQUIRE(opt.get_option("size") != nullptr);
    4268           1 :             CATCH_REQUIRE(opt.get_option('s') != nullptr);
    4269           1 :             CATCH_REQUIRE(opt.get_default("size") == "123");
    4270             : 
    4271             :             // pos
    4272             :             //
    4273           1 :             CATCH_REQUIRE(opt.get_option("pos") == nullptr);
    4274           1 :             CATCH_REQUIRE(opt.get_option('p') == nullptr);
    4275           1 :             CATCH_REQUIRE(opt.get_default("pos").empty());
    4276             : 
    4277             :             // other parameters
    4278             :             //
    4279           1 :             CATCH_REQUIRE(opt.get_program_name().empty());
    4280           1 :             CATCH_REQUIRE(opt.get_program_fullname().empty());
    4281             : 
    4282             :         // setup the program name early
    4283             :         //
    4284           1 :         char const * cargv[] =
    4285             :         {
    4286             :             "/usr/bin/arguments",
    4287             :             "--size",
    4288             :             "40132",
    4289             :             "--pos",
    4290             :             "43,91",
    4291             :             nullptr
    4292             :         };
    4293           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    4294           1 :         char ** argv = const_cast<char **>(cargv);
    4295             : 
    4296           1 :         opt.parse_program_name(argv);
    4297             : 
    4298             :             // an invalid parameter, MUST NEVER EXIST
    4299             :             //
    4300           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    4301           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    4302           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    4303             : 
    4304             :             // verbose
    4305             :             //
    4306           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    4307           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
    4308           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    4309             : 
    4310             :             // help
    4311             :             //
    4312           1 :             CATCH_REQUIRE(opt.get_option("help") != nullptr);
    4313           1 :             CATCH_REQUIRE(opt.get_option('h') != nullptr);
    4314           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    4315             : 
    4316             :             // size
    4317             :             //
    4318           1 :             CATCH_REQUIRE(opt.get_option("size") != nullptr);
    4319           1 :             CATCH_REQUIRE(opt.get_option('s') != nullptr);
    4320           1 :             CATCH_REQUIRE(opt.get_default("size") == "123");
    4321             : 
    4322             :             // pos
    4323             :             //
    4324           1 :             CATCH_REQUIRE(opt.get_option("pos") == nullptr);
    4325           1 :             CATCH_REQUIRE(opt.get_option('p') == nullptr);
    4326           1 :             CATCH_REQUIRE(opt.get_default("pos").empty());
    4327             : 
    4328             :             // default
    4329             :             //
    4330           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    4331           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    4332             : 
    4333             :             // other parameters
    4334             :             //
    4335           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    4336           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    4337             : 
    4338             :         // add --pos
    4339             :         //
    4340           1 :         advgetopt::option const help_option[] =
    4341             :         {
    4342             :             advgetopt::define_option(
    4343             :                   advgetopt::Name("pos")
    4344             :                 , advgetopt::ShortName('p')
    4345             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    4346             :                 , advgetopt::Help("specify position.")
    4347             :                 , advgetopt::DefaultValue("0,0")
    4348             :             ),
    4349             :             advgetopt::end_options()
    4350             :         };
    4351           1 :         opt.parse_options_info(help_option);
    4352             : 
    4353             :             // an invalid parameter, MUST NEVER EXIST
    4354             :             //
    4355           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    4356           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    4357           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    4358             : 
    4359             :             // verbose
    4360             :             //
    4361           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    4362           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
    4363           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    4364             : 
    4365             :             // help
    4366             :             //
    4367           1 :             CATCH_REQUIRE(opt.get_option("help") != nullptr);
    4368           1 :             CATCH_REQUIRE(opt.get_option('h') != nullptr);
    4369           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    4370             : 
    4371             :             // size
    4372             :             //
    4373           1 :             CATCH_REQUIRE(opt.get_option("size") != nullptr);
    4374           1 :             CATCH_REQUIRE(opt.get_option('s') != nullptr);
    4375           1 :             CATCH_REQUIRE(opt.get_default("size") == "123");
    4376             : 
    4377             :             // pos
    4378             :             //
    4379           1 :             CATCH_REQUIRE(opt.get_option("pos") != nullptr);
    4380           1 :             CATCH_REQUIRE(opt.get_option('p') != nullptr);
    4381           1 :             CATCH_REQUIRE(opt.get_default("pos") == "0,0");
    4382             : 
    4383             :             // default
    4384             :             //
    4385           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    4386           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    4387             : 
    4388             :             // other parameters
    4389             :             //
    4390           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    4391           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    4392             : 
    4393             :         // first parse the environment variable
    4394             :         //
    4395           2 :         snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "file.exe file.so file.dll file.lib file.a");
    4396           1 :         opt.parse_environment_variable();
    4397             : 
    4398             :             // an invalid parameter, MUST NEVER EXIST
    4399             :             //
    4400           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    4401           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    4402           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    4403           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    4404           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    4405             : 
    4406             :             // verbose
    4407             :             //
    4408           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    4409           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
    4410           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("verbose"));
    4411           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    4412           1 :             CATCH_REQUIRE(opt.size("verbose") == 0);
    4413             : 
    4414             :             // help
    4415             :             //
    4416           1 :             CATCH_REQUIRE(opt.get_option("help") != nullptr);
    4417           1 :             CATCH_REQUIRE(opt.get_option('h') != nullptr);
    4418           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("help"));
    4419           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    4420           1 :             CATCH_REQUIRE(opt.size("help") == 0);
    4421             : 
    4422             :             // size
    4423             :             //
    4424           1 :             CATCH_REQUIRE(opt.get_option("size") != nullptr);
    4425           1 :             CATCH_REQUIRE(opt.get_option('s') != nullptr);
    4426           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("size"));
    4427           1 :             CATCH_REQUIRE(opt.get_default("size") == "123");
    4428           1 :             CATCH_REQUIRE(opt.size("size") == 0);
    4429             : 
    4430             :             // pos
    4431             :             //
    4432           1 :             CATCH_REQUIRE(opt.get_option("pos") != nullptr);
    4433           1 :             CATCH_REQUIRE(opt.get_option('p') != nullptr);
    4434           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("pos"));
    4435           1 :             CATCH_REQUIRE(opt.get_default("pos") == "0,0");
    4436           1 :             CATCH_REQUIRE(opt.size("pos") == 0);
    4437             : 
    4438             :             // default
    4439             :             //
    4440           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    4441           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    4442           1 :             CATCH_REQUIRE(opt.get_string("--") == "file.exe");
    4443           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "file.exe");
    4444           1 :             CATCH_REQUIRE(opt.get_string("--", 1) == "file.so");
    4445           1 :             CATCH_REQUIRE(opt.get_string("--", 2) == "file.dll");
    4446           1 :             CATCH_REQUIRE(opt.get_string("--", 3) == "file.lib");
    4447           1 :             CATCH_REQUIRE(opt.get_string("--", 4) == "file.a");
    4448           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    4449           1 :             CATCH_REQUIRE(opt.size("--") == 5);
    4450             : 
    4451             :             // other parameters
    4452             :             //
    4453           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    4454           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    4455             : 
    4456             :         // now parse our command line arguments
    4457             :         //
    4458           1 :         opt.parse_arguments(argc, argv, advgetopt::option_source_t::SOURCE_COMMAND_LINE);
    4459             : 
    4460             :             // an invalid parameter, MUST NEVER EXIST
    4461             :             //
    4462           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    4463           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    4464           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    4465           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    4466           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    4467             : 
    4468             :             // verbose
    4469             :             //
    4470           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    4471           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
    4472           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("verbose"));
    4473           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    4474           1 :             CATCH_REQUIRE(opt.size("verbose") == 0);
    4475             : 
    4476             :             // help
    4477             :             //
    4478           1 :             CATCH_REQUIRE(opt.get_option("help") != nullptr);
    4479           1 :             CATCH_REQUIRE(opt.get_option('h') != nullptr);
    4480           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("help"));
    4481           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    4482           1 :             CATCH_REQUIRE(opt.size("help") == 0);
    4483             : 
    4484             :             // size
    4485             :             //
    4486           1 :             CATCH_REQUIRE(opt.get_option("size") != nullptr);
    4487           1 :             CATCH_REQUIRE(opt.get_option('s') != nullptr);
    4488           1 :             CATCH_REQUIRE(opt.is_defined("size"));
    4489           1 :             CATCH_REQUIRE(opt.get_string("size") == "40132");
    4490           1 :             CATCH_REQUIRE(opt.get_string("size", 0) == "40132");
    4491           1 :             CATCH_REQUIRE(opt.get_long("size") == 40132);
    4492           1 :             CATCH_REQUIRE(opt.get_long("size", 0) == 40132);
    4493           1 :             CATCH_REQUIRE(opt.get_default("size") == "123");
    4494           1 :             CATCH_REQUIRE(opt.size("size") == 1);
    4495             : 
    4496             :             // pos
    4497             :             //
    4498           1 :             CATCH_REQUIRE(opt.get_option("pos") != nullptr);
    4499           1 :             CATCH_REQUIRE(opt.get_option('p') != nullptr);
    4500           1 :             CATCH_REQUIRE(opt.is_defined("pos"));
    4501           1 :             CATCH_REQUIRE(opt.get_string("pos") == "43,91");
    4502           1 :             CATCH_REQUIRE(opt.get_string("pos", 0) == "43,91");
    4503           1 :             CATCH_REQUIRE(opt.get_default("pos") == "0,0");
    4504           1 :             CATCH_REQUIRE(opt.size("pos") == 1);
    4505             : 
    4506             :             // default
    4507             :             //
    4508           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    4509           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    4510           1 :             CATCH_REQUIRE(opt.get_string("--") == "file.exe");
    4511           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "file.exe");
    4512           1 :             CATCH_REQUIRE(opt.get_string("--", 1) == "file.so");
    4513           1 :             CATCH_REQUIRE(opt.get_string("--", 2) == "file.dll");
    4514           1 :             CATCH_REQUIRE(opt.get_string("--", 3) == "file.lib");
    4515           1 :             CATCH_REQUIRE(opt.get_string("--", 4) == "file.a");
    4516           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    4517           1 :             CATCH_REQUIRE(opt.size("--") == 5);
    4518             : 
    4519             :             // other parameters
    4520             :             //
    4521           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    4522           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    4523             : 
    4524             :         // second set of arguments
    4525             :         //
    4526           1 :         char const * cargv2[] =
    4527             :         {
    4528             :             "/usr/bin/arguments",
    4529             :             "--help",
    4530             :             "--verbose",
    4531             :             nullptr
    4532             :         };
    4533           1 :         int const argc2(sizeof(cargv2) / sizeof(cargv2[0]) - 1);
    4534           1 :         char ** argv2 = const_cast<char **>(cargv2);
    4535             : 
    4536           1 :         opt.parse_arguments(argc2, argv2, advgetopt::option_source_t::SOURCE_COMMAND_LINE);
    4537             : 
    4538             :             // an invalid parameter, MUST NEVER EXIST
    4539             :             //
    4540           1 :             CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    4541           1 :             CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    4542           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    4543           1 :             CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    4544           1 :             CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    4545             : 
    4546             :             // verbose
    4547             :             //
    4548           1 :             CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    4549           1 :             CATCH_REQUIRE(opt.get_option('v') != nullptr);
    4550           1 :             CATCH_REQUIRE(opt.is_defined("verbose"));
    4551           1 :             CATCH_REQUIRE(opt.get_string("verbose").empty());
    4552           1 :             CATCH_REQUIRE(opt.get_string("verbose", 0).empty());
    4553           1 :             CATCH_REQUIRE(opt.get_default("verbose").empty());
    4554           1 :             CATCH_REQUIRE(opt.size("verbose") == 1);
    4555             : 
    4556             :             // help
    4557             :             //
    4558           1 :             CATCH_REQUIRE(opt.get_option("help") != nullptr);
    4559           1 :             CATCH_REQUIRE(opt.get_option('h') != nullptr);
    4560           1 :             CATCH_REQUIRE(opt.is_defined("help"));
    4561           1 :             CATCH_REQUIRE(opt.get_string("help").empty());
    4562           1 :             CATCH_REQUIRE(opt.get_string("help", 0).empty());
    4563           1 :             CATCH_REQUIRE(opt.get_default("help").empty());
    4564           1 :             CATCH_REQUIRE(opt.size("help") == 1);
    4565             : 
    4566             :             // size
    4567             :             //
    4568           1 :             CATCH_REQUIRE(opt.get_option("size") != nullptr);
    4569           1 :             CATCH_REQUIRE(opt.get_option('s') != nullptr);
    4570           1 :             CATCH_REQUIRE(opt.is_defined("size"));
    4571           1 :             CATCH_REQUIRE(opt.get_string("size") == "40132");
    4572           1 :             CATCH_REQUIRE(opt.get_string("size", 0) == "40132");
    4573           1 :             CATCH_REQUIRE(opt.get_long("size") == 40132);
    4574           1 :             CATCH_REQUIRE(opt.get_long("size", 0) == 40132);
    4575           1 :             CATCH_REQUIRE(opt.get_default("size") == "123");
    4576           1 :             CATCH_REQUIRE(opt.size("size") == 1);
    4577             : 
    4578             :             // pos
    4579             :             //
    4580           1 :             CATCH_REQUIRE(opt.get_option("pos") != nullptr);
    4581           1 :             CATCH_REQUIRE(opt.get_option('p') != nullptr);
    4582           1 :             CATCH_REQUIRE(opt.is_defined("pos"));
    4583           1 :             CATCH_REQUIRE(opt.get_string("pos") == "43,91");
    4584           1 :             CATCH_REQUIRE(opt.get_string("pos", 0) == "43,91");
    4585           1 :             CATCH_REQUIRE(opt.get_default("pos") == "0,0");
    4586           1 :             CATCH_REQUIRE(opt.size("pos") == 1);
    4587             : 
    4588             :             // default
    4589             :             //
    4590           1 :             CATCH_REQUIRE(opt.get_option("--") != nullptr);
    4591           1 :             CATCH_REQUIRE(opt.is_defined("--"));
    4592           1 :             CATCH_REQUIRE(opt.get_string("--") == "file.exe");
    4593           1 :             CATCH_REQUIRE(opt.get_string("--", 0) == "file.exe");
    4594           1 :             CATCH_REQUIRE(opt.get_string("--", 1) == "file.so");
    4595           1 :             CATCH_REQUIRE(opt.get_string("--", 2) == "file.dll");
    4596           1 :             CATCH_REQUIRE(opt.get_string("--", 3) == "file.lib");
    4597           1 :             CATCH_REQUIRE(opt.get_string("--", 4) == "file.a");
    4598           1 :             CATCH_REQUIRE(opt.get_default("--").empty());
    4599           1 :             CATCH_REQUIRE(opt.size("--") == 5);
    4600             : 
    4601             :             // other parameters
    4602             :             //
    4603           1 :             CATCH_REQUIRE(opt.get_program_name() == "arguments");
    4604           1 :             CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    4605             : 
    4606             :     CATCH_END_SECTION()
    4607             : 
    4608           6 :     CATCH_START_SECTION("Verify that not calling link_aliases() causes problems")
    4609             :         // create a getopt object, we will part the options "manually" later
    4610             :         //
    4611           1 :         advgetopt::options_environment environment_options;
    4612           1 :         environment_options.f_project_name = "unittest";
    4613           1 :         environment_options.f_help_header = "Usage: test --licence as equivalent to --license";
    4614           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    4615           1 :         environment_options.f_environment_flags = advgetopt::GETOPT_ENVIRONMENT_FLAG_SYSTEM_PARAMETERS;
    4616             : 
    4617           2 :         advgetopt::getopt opt(environment_options);
    4618             : 
    4619           1 :         const advgetopt::option options[] =
    4620             :         {
    4621             :             advgetopt::define_option(
    4622             :                   advgetopt::Name("verbose")
    4623             :                 , advgetopt::ShortName('v')
    4624             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    4625             :                 , advgetopt::Help("print info as we work.")
    4626             :             ),
    4627             :             advgetopt::define_option(
    4628             :                   advgetopt::Name("licence")    // French spelling
    4629             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    4630             :                 , advgetopt::Alias("license")   // forgot system flags?
    4631             :             ),
    4632             :             advgetopt::end_options()
    4633             :         };
    4634             : 
    4635           1 :         opt.parse_options_info(options);
    4636             : 
    4637             :         // "forgot" to call the opt.link_aliases() here
    4638             : 
    4639           1 :         char const * cargv[] =
    4640             :         {
    4641             :             "/usr/bin/arguments",
    4642             :             "--verbose",
    4643             :             "--licence",
    4644             :             nullptr
    4645             :         };
    4646           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    4647           1 :         char ** argv = const_cast<char **>(cargv);
    4648             : 
    4649           1 :         CATCH_REQUIRE_THROWS_MATCHES(
    4650             :                   opt.parse_arguments(argc, argv, advgetopt::option_source_t::SOURCE_COMMAND_LINE)
    4651             :                 , advgetopt::getopt_undefined
    4652             :                 , Catch::Matchers::ExceptionMessage(
    4653             :                               "getopt_exception: getopt::get_alias_destination(): alias is missing. Did you call link_aliases()?"));
    4654             :     CATCH_END_SECTION()
    4655           3 : }
    4656             : 
    4657             : 
    4658           6 : CATCH_TEST_CASE("auto_process_system_arguments", "[arguments][valid][getopt]")
    4659             : {
    4660           8 :     CATCH_START_SECTION("Test auto-processing of system arguments (with many CATCH_WHEN)")
    4661             :     {
    4662           4 :         advgetopt::options_environment options;
    4663           4 :         options.f_project_name = "unittest";
    4664           4 :         options.f_environment_flags = advgetopt::GETOPT_ENVIRONMENT_FLAG_PROCESS_SYSTEM_PARAMETERS;
    4665           4 :         options.f_help_header = "Usage: testing system arguments.";
    4666           4 :         options.f_version = "2.0.1";
    4667           4 :         options.f_license = "MIT";
    4668           4 :         options.f_copyright = "Copyright (c) 2019  Made to Order Software Corp. -- All Rights Reserved";
    4669           4 :         options.f_build_date = "Jun  4 2019";
    4670           4 :         options.f_build_time = "23:02:36";
    4671             : 
    4672           8 :         CATCH_WHEN("Testing --version")
    4673             :         {
    4674           1 :             char const * cargv[] =
    4675             :             {
    4676             :                 "tests/system-arguments",
    4677             :                 "--version",
    4678             :                 nullptr
    4679             :             };
    4680           1 :             int const argc = sizeof(cargv) / sizeof(cargv[0]) - 1;
    4681           1 :             char ** argv = const_cast<char **>(cargv);
    4682             : 
    4683             :             // do our own try/catch because we want to test the message
    4684             :             // and exit code of the exception and it's easier to do it
    4685             :             // this way
    4686             :             //
    4687           2 :             snapdev::ostream_to_buf<char> out(std::cout);
    4688             :             try
    4689             :             {
    4690           1 :                 advgetopt::getopt::pointer_t opt(std::make_shared<advgetopt::getopt>(options, argc, argv));
    4691             : 
    4692             :                 // if it returns opt cannot be nullptr
    4693             :                 //
    4694           0 :                 CATCH_REQUIRE(opt == nullptr);
    4695             :             }
    4696           2 :             catch(advgetopt::getopt_exit const & e)
    4697             :             {
    4698             :                 // this is the expected route
    4699             :                 //
    4700           1 :                 CATCH_REQUIRE(e.what() == std::string("getopt_exception: system command processed."));
    4701           1 :                 CATCH_REQUIRE(e.code() == 0);
    4702           1 :                 CATCH_REQUIRE(out.str() == "2.0.1\n");
    4703             :             }
    4704           0 :             catch(std::exception const & e)
    4705             :             {
    4706             :                 // no other exception is considered valid here
    4707             :                 //
    4708           0 :                 CATCH_REQUIRE(e.what() == std::string("no other exception was expected..."));
    4709             :             }
    4710             :         }
    4711             : 
    4712           8 :         CATCH_WHEN("Testing --copyright")
    4713             :         {
    4714           1 :             char const * cargv[] =
    4715             :             {
    4716             :                 "tests/system-arguments",
    4717             :                 "--copyright",
    4718             :                 nullptr
    4719             :             };
    4720           1 :             int const argc = sizeof(cargv) / sizeof(cargv[0]) - 1;
    4721           1 :             char ** argv = const_cast<char **>(cargv);
    4722             : 
    4723             :             // do our own try/catch because we want to test the message
    4724             :             // and exit code of the exception and it's easier to do it
    4725             :             // this way
    4726             :             //
    4727           2 :             snapdev::ostream_to_buf<char> out(std::cout);
    4728             :             try
    4729             :             {
    4730           1 :                 advgetopt::getopt::pointer_t opt(std::make_shared<advgetopt::getopt>(options, argc, argv));
    4731             : 
    4732             :                 // if it returns opt cannot be nullptr
    4733             :                 //
    4734           0 :                 CATCH_REQUIRE(opt == nullptr);
    4735             :             }
    4736           2 :             catch(advgetopt::getopt_exit const & e)
    4737             :             {
    4738             :                 // this is the expected route
    4739             :                 //
    4740           1 :                 CATCH_REQUIRE(e.what() == std::string("getopt_exception: system command processed."));
    4741           1 :                 CATCH_REQUIRE(e.code() == 0);
    4742           1 :                 CATCH_REQUIRE(out.str() == "Copyright (c) 2019  Made to Order Software Corp. -- All Rights Reserved\n");
    4743             :             }
    4744           0 :             catch(std::exception const & e)
    4745             :             {
    4746             :                 // no other exception is considered valid here
    4747             :                 //
    4748           0 :                 CATCH_REQUIRE(e.what() == std::string("no other exception was expected..."));
    4749             :             }
    4750             :         }
    4751             : 
    4752           8 :         CATCH_WHEN("Testing --build-date")
    4753             :         {
    4754           1 :             char const * cargv[] =
    4755             :             {
    4756             :                 "tests/system-arguments",
    4757             :                 "--build-date",
    4758             :                 nullptr
    4759             :             };
    4760           1 :             int const argc = sizeof(cargv) / sizeof(cargv[0]) - 1;
    4761           1 :             char ** argv = const_cast<char **>(cargv);
    4762             : 
    4763             :             // do our own try/catch because we want to test the message
    4764             :             // and exit code of the exception and it's easier to do it
    4765             :             // this way
    4766             :             //
    4767           2 :             snapdev::ostream_to_buf<char> out(std::cout);
    4768             :             try
    4769             :             {
    4770           1 :                 advgetopt::getopt::pointer_t opt(std::make_shared<advgetopt::getopt>(options, argc, argv));
    4771             : 
    4772             :                 // if it returns opt cannot be nullptr
    4773             :                 //
    4774           0 :                 CATCH_REQUIRE(opt == nullptr);
    4775             :             }
    4776           2 :             catch(advgetopt::getopt_exit const & e)
    4777             :             {
    4778             :                 // this is the expected route
    4779             :                 //
    4780           1 :                 CATCH_REQUIRE(e.what() == std::string("getopt_exception: system command processed."));
    4781           1 :                 CATCH_REQUIRE(e.code() == 0);
    4782           1 :                 CATCH_REQUIRE(out.str() == "Built on Jun  4 2019 at 23:02:36\n");
    4783             :             }
    4784           0 :             catch(std::exception const & e)
    4785             :             {
    4786             :                 // no other exception is considered valid here
    4787             :                 //
    4788           0 :                 CATCH_REQUIRE(e.what() == std::string("no other exception was expected..."));
    4789             :             }
    4790             :         }
    4791             : 
    4792           8 :         CATCH_WHEN("Testing -L (For --license)")
    4793             :         {
    4794           1 :             char const * cargv[] =
    4795             :             {
    4796             :                 "tests/system-arguments",
    4797             :                 "-L",
    4798             :                 nullptr
    4799             :             };
    4800           1 :             int const argc = sizeof(cargv) / sizeof(cargv[0]) - 1;
    4801           1 :             char ** argv = const_cast<char **>(cargv);
    4802             : 
    4803             :             // do our own try/catch because we want to test the message
    4804             :             // and exit code of the exception and it's easier to do it
    4805             :             // this way
    4806             :             //
    4807           2 :             snapdev::ostream_to_buf<char> out(std::cout);
    4808             :             try
    4809             :             {
    4810           1 :                 advgetopt::getopt::pointer_t opt(std::make_shared<advgetopt::getopt>(options, argc, argv));
    4811             : 
    4812             :                 // if it returns opt cannot be nullptr
    4813             :                 //
    4814           0 :                 CATCH_REQUIRE(opt == nullptr);
    4815             :             }
    4816           2 :             catch(advgetopt::getopt_exit const & e)
    4817             :             {
    4818             :                 // this is the expected route
    4819             :                 //
    4820           1 :                 CATCH_REQUIRE(e.what() == std::string("getopt_exception: system command processed."));
    4821           1 :                 CATCH_REQUIRE(e.code() == 0);
    4822           1 :                 CATCH_REQUIRE(out.str() == "MIT\n");
    4823             :             }
    4824           0 :             catch(std::exception const & e)
    4825             :             {
    4826             :                 // no other exception is considered valid here
    4827             :                 //
    4828           0 :                 CATCH_REQUIRE(e.what() == std::string("no other exception was expected..."));
    4829             :             }
    4830             :         }
    4831             :     }
    4832             :     CATCH_END_SECTION()
    4833           4 : }
    4834             : 
    4835             : 
    4836           3 : CATCH_TEST_CASE("invalid_getopt_pointers", "[invalid][getopt][arguments]")
    4837             : {
    4838           2 :     CATCH_START_SECTION("Create getopt with argv set to nullptr.")
    4839           1 :         advgetopt::options_environment const environment_opt;
    4840             : 
    4841           1 :         CATCH_REQUIRE_THROWS_MATCHES(
    4842             :                   std::make_shared<advgetopt::getopt>(environment_opt, 3, nullptr)
    4843             :                 , advgetopt::getopt_logic_error
    4844             :                 , Catch::Matchers::ExceptionMessage(
    4845             :                     "getopt_logic_error: argv pointer cannot be nullptr"));
    4846             :     CATCH_END_SECTION()
    4847           1 : }
    4848             : 
    4849             : 
    4850           4 : CATCH_TEST_CASE("invalid_getopt_missing_options", "[invalid][getopt][arguments]")
    4851             : {
    4852           4 :     CATCH_START_SECTION("Create getopt with no options.")
    4853           1 :         advgetopt::options_environment options_empty;
    4854           1 :         options_empty.f_project_name = "unittest";
    4855           1 :         options_empty.f_options = nullptr;
    4856           1 :         options_empty.f_help_header = "Usage: try this one and we get a throw (empty list)";
    4857             : 
    4858           1 :         char const * cargv[] =
    4859             :         {
    4860             :             "/usr/bin/arguments",
    4861             :             "--no-options",
    4862             :             nullptr
    4863             :         };
    4864           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    4865           1 :         char ** argv = const_cast<char **>(cargv);
    4866             : 
    4867           1 :         CATCH_REQUIRE_THROWS_MATCHES(
    4868             :                   std::make_shared<advgetopt::getopt>(options_empty, argc, argv)
    4869             :                 , advgetopt::getopt_logic_error
    4870             :                 , Catch::Matchers::ExceptionMessage(
    4871             :                     "getopt_logic_error: an empty list of options is not legal, you must"
    4872             :                     " defined at least one (i.e. --version, --help...)"));
    4873             :     CATCH_END_SECTION()
    4874             : 
    4875           4 :     CATCH_START_SECTION("Create getopt with an empty list of options.")
    4876           1 :         const advgetopt::option options_empty_list[] =
    4877             :         {
    4878             :             {
    4879             :                 '\0',
    4880             :                 advgetopt::GETOPT_FLAG_END,
    4881             :                 nullptr,
    4882             :                 nullptr,
    4883             :                 nullptr,
    4884             :                 nullptr
    4885             :             }
    4886             :         };
    4887             : 
    4888           1 :         advgetopt::options_environment options_empty;
    4889           1 :         options_empty.f_project_name = "unittest";
    4890           1 :         options_empty.f_options = options_empty_list;
    4891           1 :         options_empty.f_help_header = "Usage: try this one and we get a throw (empty list)";
    4892             : 
    4893           1 :         char const * cargv[] =
    4894             :         {
    4895             :             "/usr/bin/arguments",
    4896             :             "--no-options",
    4897             :             nullptr
    4898             :         };
    4899           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    4900           1 :         char ** argv = const_cast<char **>(cargv);
    4901             : 
    4902           1 :         CATCH_REQUIRE_THROWS_MATCHES(
    4903             :                   std::make_shared<advgetopt::getopt>(options_empty, argc, argv)
    4904             :                 , advgetopt::getopt_logic_error
    4905             :                 , Catch::Matchers::ExceptionMessage(
    4906             :                     "getopt_logic_error: an empty list of options is not legal, you must"
    4907             :                     " defined at least one (i.e. --version, --help...)"));
    4908             :     CATCH_END_SECTION()
    4909           2 : }
    4910             : 
    4911             : 
    4912           6 : CATCH_TEST_CASE("invalid_getopt_missing_required_option", "[invalid][getopt][arguments][alias]")
    4913             : {
    4914           8 :     CATCH_START_SECTION("Specify the option without a corresponding parameter.")
    4915             :     {
    4916           1 :         const advgetopt::option options[] =
    4917             :         {
    4918             :             advgetopt::define_option(
    4919             :                   advgetopt::Name("verbose")
    4920             :                 , advgetopt::ShortName('v')
    4921             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    4922             :                 , advgetopt::Help("print info as we work.")
    4923             :             ),
    4924             :             advgetopt::define_option(
    4925             :                   advgetopt::Name("size")
    4926             :                 , advgetopt::Help("The size of the line.")
    4927             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    4928             :                 , advgetopt::DefaultValue("100")
    4929             :             ),
    4930             :             advgetopt::end_options()
    4931             :         };
    4932             : 
    4933           1 :         advgetopt::options_environment environment_options;
    4934           1 :         environment_options.f_project_name = "unittest";
    4935           1 :         environment_options.f_options = options;
    4936           1 :         environment_options.f_help_header = "Usage: use --size without a value.";
    4937             : 
    4938           1 :         char const * cargv[] =
    4939             :         {
    4940             :             "/usr/bin/arguments",
    4941             :             "--verbose",
    4942             :             "--size",
    4943             :             nullptr
    4944             :         };
    4945           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    4946           1 :         char ** argv = const_cast<char **>(cargv);
    4947             : 
    4948           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --size expects an argument.");
    4949           2 :         advgetopt::getopt opt(environment_options);
    4950             :         try
    4951             :         {
    4952           1 :             opt.finish_parsing(argc, argv);
    4953           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    4954             :         }
    4955           2 :         catch(advgetopt::getopt_exit const & e)
    4956             :         {
    4957           1 :             CATCH_REQUIRE(e.code() == 1);
    4958           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    4959             :         }
    4960           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    4961             : 
    4962             :         // check that the result is valid
    4963             : 
    4964             :         // an "invalid-parameter", MUST NOT EXIST
    4965           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    4966           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    4967           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    4968           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    4969           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    4970             : 
    4971             :         // no default
    4972           1 :         CATCH_REQUIRE(opt.get_option("--") == nullptr);
    4973           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("--"));
    4974           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    4975           1 :         CATCH_REQUIRE(opt.size("--") == 0);
    4976             : 
    4977             :         // the valid parameter
    4978           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    4979           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    4980           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    4981           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    4982           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    4983             : 
    4984             :         // the invalid parameter
    4985           1 :         CATCH_REQUIRE(opt.get_option("size") != nullptr);
    4986           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("size"));
    4987           1 :         CATCH_REQUIRE(opt.get_default("size") == "100");
    4988           1 :         CATCH_REQUIRE(opt.size("size") == 0);
    4989             : 
    4990             :         // other parameters
    4991           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    4992           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    4993             :     }
    4994             :     CATCH_END_SECTION()
    4995             : 
    4996           8 :     CATCH_START_SECTION("Specify the option with an equal sign but without a corresponding parameter.")
    4997             :     {
    4998           1 :         const advgetopt::option options[] =
    4999             :         {
    5000             :             advgetopt::define_option(
    5001             :                   advgetopt::Name("verbose")
    5002             :                 , advgetopt::ShortName('v')
    5003             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    5004             :                 , advgetopt::Help("print info as we work.")
    5005             :             ),
    5006             :             advgetopt::define_option(
    5007             :                   advgetopt::Name("size")
    5008             :                 , advgetopt::Help("The size of the line.")
    5009             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    5010             :                 , advgetopt::DefaultValue("100")
    5011             :             ),
    5012             :             advgetopt::end_options()
    5013             :         };
    5014             : 
    5015           1 :         advgetopt::options_environment environment_options;
    5016           1 :         environment_options.f_project_name = "unittest";
    5017           1 :         environment_options.f_options = options;
    5018           1 :         environment_options.f_help_header = "Usage: use --size without a value.";
    5019             : 
    5020           1 :         char const * cargv[] =
    5021             :         {
    5022             :             "/usr/bin/arguments",
    5023             :             "--verbose",
    5024             :             "--size=",
    5025             :             nullptr
    5026             :         };
    5027           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5028           1 :         char ** argv = const_cast<char **>(cargv);
    5029             : 
    5030           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --size must be given a value.");
    5031           2 :         advgetopt::getopt opt(environment_options);
    5032             :         try
    5033             :         {
    5034           1 :             opt.finish_parsing(argc, argv);
    5035           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5036             :         }
    5037           2 :         catch(advgetopt::getopt_exit const & e)
    5038             :         {
    5039           1 :             CATCH_REQUIRE(e.code() == 1);
    5040           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5041             :         }
    5042           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5043             : 
    5044             :         // check that the result is valid
    5045             : 
    5046             :         // an invalid parameter, MUST NOT EXIST
    5047           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5048           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5049           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5050           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5051           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5052             : 
    5053             :         // no default
    5054           1 :         CATCH_REQUIRE(opt.get_option("--") == nullptr);
    5055           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("--"));
    5056           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    5057           1 :         CATCH_REQUIRE(opt.size("--") == 0);
    5058             : 
    5059             :         // the valid parameter
    5060           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    5061           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    5062           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    5063           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    5064           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    5065             : 
    5066             :         // the invalid parameter
    5067           1 :         CATCH_REQUIRE(opt.get_option("size") != nullptr);
    5068           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("size"));
    5069           1 :         CATCH_REQUIRE(opt.get_default("size") == "100");
    5070           1 :         CATCH_REQUIRE(opt.size("size") == 0);
    5071             : 
    5072             :         // other parameters
    5073           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5074           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5075             :     }
    5076             :     CATCH_END_SECTION()
    5077             : 
    5078           8 :     CATCH_START_SECTION("Specify the option without a corresponding parameter followed by a long argument.")
    5079           1 :         const advgetopt::option options[] =
    5080             :         {
    5081             :             advgetopt::define_option(
    5082             :                   advgetopt::Name("verbose")
    5083             :                 , advgetopt::ShortName('v')
    5084             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    5085             :                 , advgetopt::Help("print info as we work.")
    5086             :             ),
    5087             :             advgetopt::define_option(
    5088             :                   advgetopt::Name("size")
    5089             :                 , advgetopt::Help("The size of the line.")
    5090             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    5091             :                 , advgetopt::DefaultValue("100")
    5092             :             ),
    5093             :             advgetopt::end_options()
    5094             :         };
    5095             : 
    5096           1 :         advgetopt::options_environment environment_options;
    5097           1 :         environment_options.f_project_name = "unittest";
    5098           1 :         environment_options.f_options = options;
    5099           1 :         environment_options.f_help_header = "Usage: use --size without a value.";
    5100             : 
    5101           1 :         char const * cargv[] =
    5102             :         {
    5103             :             "/usr/bin/arguments",
    5104             :             "--size",
    5105             :             "--verbose",
    5106             :             nullptr
    5107             :         };
    5108           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5109           1 :         char ** argv = const_cast<char **>(cargv);
    5110             : 
    5111           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --size expects an argument.");
    5112           2 :         advgetopt::getopt opt(environment_options);
    5113             :         try
    5114             :         {
    5115           1 :             opt.finish_parsing(argc, argv);
    5116           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5117             :         }
    5118           2 :         catch(advgetopt::getopt_exit const & e)
    5119             :         {
    5120           1 :             CATCH_REQUIRE(e.code() == 1);
    5121           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5122             :         }
    5123           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5124             : 
    5125             :         // check that the result is valid
    5126             : 
    5127             :         // an invalid parameter, MUST NOT EXIST
    5128           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5129           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5130           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5131           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5132           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5133             : 
    5134             :         // no default
    5135           1 :         CATCH_REQUIRE(opt.get_option("--") == nullptr);
    5136           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("--"));
    5137           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    5138           1 :         CATCH_REQUIRE(opt.size("--") == 0);
    5139             : 
    5140             :         // the valid parameter
    5141           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    5142           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    5143           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    5144           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    5145           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    5146             : 
    5147             :         // the invalid parameter
    5148           1 :         CATCH_REQUIRE(opt.get_option("size") != nullptr);
    5149           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("size"));
    5150           1 :         CATCH_REQUIRE(opt.get_default("size") == "100");
    5151           1 :         CATCH_REQUIRE(opt.size("size") == 0);
    5152             : 
    5153             :         // other parameters
    5154           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5155           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5156             :     CATCH_END_SECTION()
    5157             : 
    5158           8 :     CATCH_START_SECTION("Specify the option without a corresponding parameter followed by a short argument.")
    5159           1 :         const advgetopt::option options[] =
    5160             :         {
    5161             :             advgetopt::define_option(
    5162             :                   advgetopt::Name("verbose")
    5163             :                 , advgetopt::ShortName('v')
    5164             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    5165             :                 , advgetopt::Help("print info as we work.")
    5166             :             ),
    5167             :             advgetopt::define_option(
    5168             :                   advgetopt::Name("size")
    5169             :                 , advgetopt::Help("The size of the line.")
    5170             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    5171             :                 , advgetopt::DefaultValue("100")
    5172             :             ),
    5173             :             advgetopt::end_options()
    5174             :         };
    5175             : 
    5176           1 :         advgetopt::options_environment environment_options;
    5177           1 :         environment_options.f_project_name = "unittest";
    5178           1 :         environment_options.f_options = options;
    5179           1 :         environment_options.f_help_header = "Usage: use --size without a value.";
    5180             : 
    5181           1 :         char const * cargv[] =
    5182             :         {
    5183             :             "/usr/bin/arguments",
    5184             :             "--size",
    5185             :             "-v",
    5186             :             nullptr
    5187             :         };
    5188           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5189           1 :         char ** argv = const_cast<char **>(cargv);
    5190             : 
    5191           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --size expects an argument.");
    5192           2 :         advgetopt::getopt opt(environment_options);
    5193             :         try
    5194             :         {
    5195           1 :             opt.finish_parsing(argc, argv);
    5196           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5197             :         }
    5198           2 :         catch(advgetopt::getopt_exit const & e)
    5199             :         {
    5200           1 :             CATCH_REQUIRE(e.code() == 1);
    5201           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5202             :         }
    5203           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5204             : 
    5205             :         // check that the result is valid
    5206             : 
    5207             :         // an invalid parameter, MUST NOT EXIST
    5208           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5209           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5210           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5211           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5212           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5213             : 
    5214             :         // no default
    5215           1 :         CATCH_REQUIRE(opt.get_option("--") == nullptr);
    5216           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("--"));
    5217           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    5218           1 :         CATCH_REQUIRE(opt.size("--") == 0);
    5219             : 
    5220             :         // the valid parameter
    5221           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    5222           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    5223           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    5224           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    5225           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    5226             : 
    5227             :         // the invalid parameter
    5228           1 :         CATCH_REQUIRE(opt.get_option("size") != nullptr);
    5229           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("size"));
    5230           1 :         CATCH_REQUIRE(opt.get_default("size") == "100");
    5231           1 :         CATCH_REQUIRE(opt.size("size") == 0);
    5232             : 
    5233             :         // other parameters
    5234           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5235           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5236             :     CATCH_END_SECTION()
    5237           4 : }
    5238             : 
    5239             : 
    5240          11 : CATCH_TEST_CASE("invalid_default_options", "[invalid][getopt][arguments]")
    5241             : {
    5242          18 :     CATCH_START_SECTION("Using a standalone 'file.txt' when no default option is allowed.")
    5243           1 :         const advgetopt::option options[] =
    5244             :         {
    5245             :             advgetopt::define_option(
    5246             :                   advgetopt::Name("verbose")
    5247             :                 , advgetopt::ShortName('v')
    5248             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    5249             :                 , advgetopt::Help("print info as we work.")
    5250             :             ),
    5251             :             advgetopt::end_options()
    5252             :         };
    5253             : 
    5254           1 :         advgetopt::options_environment environment_options;
    5255           1 :         environment_options.f_project_name = "unittest";
    5256           1 :         environment_options.f_options = options;
    5257           1 :         environment_options.f_help_header = "Usage: use '--' when no default option was defined.";
    5258             : 
    5259           1 :         char const * cargv[] =
    5260             :         {
    5261             :             "/usr/bin/arguments",
    5262             :             "--verbose",
    5263             :             "file.txt",
    5264             :             nullptr
    5265             :         };
    5266           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5267           1 :         char ** argv = const_cast<char **>(cargv);
    5268             : 
    5269           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: no default options defined; we do not know what to do of \"file.txt\"; standalone parameters are not accepted by this program.");
    5270           2 :         advgetopt::getopt opt(environment_options);
    5271             :         try
    5272             :         {
    5273           1 :             opt.finish_parsing(argc, argv);
    5274           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5275             :         }
    5276           2 :         catch(advgetopt::getopt_exit const & e)
    5277             :         {
    5278           1 :             CATCH_REQUIRE(e.code() == 1);
    5279           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5280             :         }
    5281           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5282             : 
    5283             :         // check that the result is valid
    5284             : 
    5285             :         // an invalid parameter, MUST NOT EXIST
    5286           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5287           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5288           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5289           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5290           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5291             : 
    5292             :         // no default
    5293           1 :         CATCH_REQUIRE(opt.get_option("--") == nullptr);
    5294           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("--"));
    5295           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    5296           1 :         CATCH_REQUIRE(opt.size("--") == 0);
    5297             : 
    5298             :         // the valid parameter
    5299           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    5300           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    5301           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    5302           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    5303           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    5304             : 
    5305             :         // other parameters
    5306           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5307           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5308             :     CATCH_END_SECTION()
    5309             : 
    5310          18 :     CATCH_START_SECTION("Using a standalone 'file.txt' on the command line when only allowed in a variable.")
    5311           1 :         const advgetopt::option options[] =
    5312             :         {
    5313             :             advgetopt::define_option(
    5314             :                   advgetopt::Name("verbose")
    5315             :                 , advgetopt::ShortName('v')
    5316             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    5317             :                 , advgetopt::Help("print info as we work.")
    5318             :             ),
    5319             :             advgetopt::define_option(
    5320             :                   advgetopt::Name("--")
    5321             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_DEFAULT_OPTION>())
    5322             :                 , advgetopt::Help("default option.")
    5323             :             ),
    5324             :             advgetopt::end_options()
    5325             :         };
    5326             : 
    5327           1 :         advgetopt::options_environment environment_options;
    5328           1 :         environment_options.f_project_name = "unittest";
    5329           1 :         environment_options.f_options = options;
    5330           1 :         environment_options.f_help_header = "Usage: use '--' on the command line when only allowed in the variable.";
    5331           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    5332             : 
    5333           2 :         snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "allowed.jpg");
    5334             : 
    5335           1 :         char const * cargv[] =
    5336             :         {
    5337             :             "/usr/bin/arguments",
    5338             :             "--verbose",
    5339             :             "file.txt",
    5340             :             nullptr
    5341             :         };
    5342           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5343           1 :         char ** argv = const_cast<char **>(cargv);
    5344             : 
    5345           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: default options are not supported on the command line.");
    5346           2 :         advgetopt::getopt opt(environment_options);
    5347             :         try
    5348             :         {
    5349           1 :             opt.finish_parsing(argc, argv);
    5350           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5351             :         }
    5352           2 :         catch(advgetopt::getopt_exit const & e)
    5353             :         {
    5354           1 :             CATCH_REQUIRE(e.code() == 1);
    5355           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5356             :         }
    5357           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5358             : 
    5359             :         // check that the result is valid
    5360             : 
    5361             :         // an invalid parameter, MUST NOT EXIST
    5362           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5363           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5364           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5365           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5366           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5367             : 
    5368             :         // default on command line passed through
    5369           1 :         CATCH_REQUIRE(opt.get_option("--") != nullptr);
    5370           1 :         CATCH_REQUIRE(opt.is_defined("--"));
    5371           1 :         CATCH_REQUIRE(opt.get_string("--") == "allowed.jpg");
    5372           1 :         CATCH_REQUIRE(opt.get_string("--", 0) == "allowed.jpg");
    5373           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    5374           1 :         CATCH_REQUIRE(opt.size("--") == 1);
    5375             : 
    5376             :         // the valid parameter
    5377           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    5378           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    5379           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    5380           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    5381           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    5382             : 
    5383             :         // other parameters
    5384           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5385           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5386             :     CATCH_END_SECTION()
    5387             : 
    5388          18 :     CATCH_START_SECTION("Using a standalone 'file.txt' in a variable when only allowed on the command line.")
    5389           1 :         const advgetopt::option options[] =
    5390             :         {
    5391             :             advgetopt::define_option(
    5392             :                   advgetopt::Name("verbose")
    5393             :                 , advgetopt::ShortName('v')
    5394             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    5395             :                 , advgetopt::Help("print info as we work.")
    5396             :             ),
    5397             :             advgetopt::define_option(
    5398             :                   advgetopt::Name("--")
    5399             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_DEFAULT_OPTION>())
    5400             :                 , advgetopt::Help("default option.")
    5401             :             ),
    5402             :             advgetopt::end_options()
    5403             :         };
    5404             : 
    5405           1 :         advgetopt::options_environment environment_options;
    5406           1 :         environment_options.f_project_name = "unittest";
    5407           1 :         environment_options.f_options = options;
    5408           1 :         environment_options.f_help_header = "Usage: use '--' on the command line when only allowed in the variable.";
    5409           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    5410             : 
    5411           2 :         snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "file.txt");
    5412             : 
    5413           1 :         char const * cargv[] =
    5414             :         {
    5415             :             "/usr/bin/arguments",
    5416             :             "--verbose",
    5417             :             "allowed.jpg",
    5418             :             nullptr
    5419             :         };
    5420           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5421           1 :         char ** argv = const_cast<char **>(cargv);
    5422             : 
    5423           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: default options are not supported in the environment variable.");
    5424           2 :         advgetopt::getopt opt(environment_options);
    5425             :         try
    5426             :         {
    5427           1 :             opt.finish_parsing(argc, argv);
    5428           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5429             :         }
    5430           2 :         catch(advgetopt::getopt_exit const & e)
    5431             :         {
    5432           1 :             CATCH_REQUIRE(e.code() == 1);
    5433           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5434             :         }
    5435           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5436             : 
    5437             :         // check that the result is valid
    5438             : 
    5439             :         // an invalid parameter, MUST NOT EXIST
    5440           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5441           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5442           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5443           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5444           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5445             : 
    5446             :         // default on command line passed through
    5447           1 :         CATCH_REQUIRE(opt.get_option("--") != nullptr);
    5448           1 :         CATCH_REQUIRE(opt.is_defined("--"));
    5449           1 :         CATCH_REQUIRE(opt.get_string("--") == "allowed.jpg");
    5450           1 :         CATCH_REQUIRE(opt.get_string("--", 0) == "allowed.jpg");
    5451           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    5452           1 :         CATCH_REQUIRE(opt.size("--") == 1);
    5453             : 
    5454             :         // the valid parameter
    5455           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    5456           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    5457           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    5458           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    5459           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    5460             : 
    5461             :         // other parameters
    5462           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5463           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5464             :     CATCH_END_SECTION()
    5465             : 
    5466          18 :     CATCH_START_SECTION("Using a '--' when no default option is allowed.")
    5467           1 :         const advgetopt::option options[] =
    5468             :         {
    5469             :             advgetopt::define_option(
    5470             :                   advgetopt::Name("verbose")
    5471             :                 , advgetopt::ShortName('v')
    5472             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    5473             :                 , advgetopt::Help("print info as we work.")
    5474             :             ),
    5475             :             advgetopt::end_options()
    5476             :         };
    5477             : 
    5478           1 :         advgetopt::options_environment environment_options;
    5479           1 :         environment_options.f_project_name = "unittest";
    5480           1 :         environment_options.f_options = options;
    5481           1 :         environment_options.f_help_header = "Usage: use '--' when no default option was defined.";
    5482             : 
    5483           1 :         char const * cargv[] =
    5484             :         {
    5485             :             "/usr/bin/arguments",
    5486             :             "--verbose",
    5487             :             "--",
    5488             :             "file.txt",
    5489             :             nullptr
    5490             :         };
    5491           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5492           1 :         char ** argv = const_cast<char **>(cargv);
    5493             : 
    5494           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: no default options defined; thus \"--\" is not accepted by this program.");
    5495           2 :         advgetopt::getopt opt(environment_options);
    5496             :         try
    5497             :         {
    5498           1 :             opt.finish_parsing(argc, argv);
    5499           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5500             :         }
    5501           2 :         catch(advgetopt::getopt_exit const & e)
    5502             :         {
    5503           1 :             CATCH_REQUIRE(e.code() == 1);
    5504           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5505             :         }
    5506           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5507             : 
    5508             :         // check that the result is valid
    5509             : 
    5510             :         // an invalid parameter, MUST NOT EXIST
    5511           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5512           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5513           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5514           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5515           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5516             : 
    5517             :         // no default
    5518           1 :         CATCH_REQUIRE(opt.get_option("--") == nullptr);
    5519           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("--"));
    5520           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    5521           1 :         CATCH_REQUIRE(opt.size("--") == 0);
    5522             : 
    5523             :         // the valid parameter
    5524           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    5525           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    5526           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    5527           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    5528           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    5529             : 
    5530             :         // other parameters
    5531           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5532           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5533             :     CATCH_END_SECTION()
    5534             : 
    5535          18 :     CATCH_START_SECTION("Using a '--' when on the command line when only accepted in variables.")
    5536           1 :         const advgetopt::option options[] =
    5537             :         {
    5538             :             advgetopt::define_option(
    5539             :                   advgetopt::Name("verbose")
    5540             :                 , advgetopt::ShortName('v')
    5541             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    5542             :                 , advgetopt::Help("print info as we work.")
    5543             :             ),
    5544             :             advgetopt::define_option(
    5545             :                   advgetopt::Name("--")
    5546             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_DEFAULT_OPTION>())
    5547             :                 , advgetopt::Help("default option.")
    5548             :             ),
    5549             :             advgetopt::end_options()
    5550             :         };
    5551             : 
    5552           1 :         advgetopt::options_environment environment_options;
    5553           1 :         environment_options.f_project_name = "unittest";
    5554           1 :         environment_options.f_options = options;
    5555           1 :         environment_options.f_help_header = "Usage: use '--' when no default option was defined.";
    5556           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    5557             : 
    5558           2 :         snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-- allowed.txt");
    5559             : 
    5560           1 :         char const * cargv[] =
    5561             :         {
    5562             :             "/usr/bin/arguments",
    5563             :             "--verbose",
    5564             :             "--",
    5565             :             "file.txt",
    5566             :             nullptr
    5567             :         };
    5568           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5569           1 :         char ** argv = const_cast<char **>(cargv);
    5570             : 
    5571           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option \"--\" is not supported on the command line.");
    5572           2 :         advgetopt::getopt opt(environment_options);
    5573             :         try
    5574             :         {
    5575           1 :             opt.finish_parsing(argc, argv);
    5576           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5577             :         }
    5578           2 :         catch(advgetopt::getopt_exit const & e)
    5579             :         {
    5580           1 :             CATCH_REQUIRE(e.code() == 1);
    5581           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5582             :         }
    5583           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5584             : 
    5585             :         // check that the result is valid
    5586             : 
    5587             :         // an invalid parameter, MUST NOT EXIST
    5588           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5589           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5590           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5591           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5592           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5593             : 
    5594             :         // no default
    5595           1 :         CATCH_REQUIRE(opt.get_option("--") != nullptr);
    5596           1 :         CATCH_REQUIRE(opt.is_defined("--"));
    5597           1 :         CATCH_REQUIRE(opt.get_string("--") == "allowed.txt");
    5598           1 :         CATCH_REQUIRE(opt.get_string("--", 0) == "allowed.txt");
    5599           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    5600           1 :         CATCH_REQUIRE(opt.size("--") == 1);
    5601             : 
    5602             :         // the valid parameter
    5603           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    5604           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    5605           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    5606           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    5607           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    5608             : 
    5609             :         // other parameters
    5610           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5611           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5612             :     CATCH_END_SECTION()
    5613             : 
    5614          18 :     CATCH_START_SECTION("Using a '--' in the environment variable when only accepted on the command line.")
    5615           1 :         const advgetopt::option options[] =
    5616             :         {
    5617             :             advgetopt::define_option(
    5618             :                   advgetopt::Name("verbose")
    5619             :                 , advgetopt::ShortName('v')
    5620             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    5621             :                 , advgetopt::Help("print info as we work.")
    5622             :             ),
    5623             :             advgetopt::define_option(
    5624             :                   advgetopt::Name("--")
    5625             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_DEFAULT_OPTION>())
    5626             :                 , advgetopt::Help("default option.")
    5627             :             ),
    5628             :             advgetopt::end_options()
    5629             :         };
    5630             : 
    5631           1 :         advgetopt::options_environment environment_options;
    5632           1 :         environment_options.f_project_name = "unittest";
    5633           1 :         environment_options.f_options = options;
    5634           1 :         environment_options.f_help_header = "Usage: use '--' when no default option was defined.";
    5635           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    5636             : 
    5637           2 :         snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", " -- file.txt ");
    5638             : 
    5639           1 :         char const * cargv[] =
    5640             :         {
    5641             :             "/usr/bin/arguments",
    5642             :             "--verbose",
    5643             :             "--",
    5644             :             "allowed.txt",
    5645             :             nullptr
    5646             :         };
    5647           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5648           1 :         char ** argv = const_cast<char **>(cargv);
    5649             : 
    5650           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option \"--\" is not supported in the environment variable.");
    5651           2 :         advgetopt::getopt opt(environment_options);
    5652             :         try
    5653             :         {
    5654           1 :             opt.finish_parsing(argc, argv);
    5655           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5656             :         }
    5657           2 :         catch(advgetopt::getopt_exit const & e)
    5658             :         {
    5659           1 :             CATCH_REQUIRE(e.code() == 1);
    5660           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5661             :         }
    5662           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5663             : 
    5664             :         // check that the result is valid
    5665             : 
    5666             :         // an invalid parameter, MUST NOT EXIST
    5667           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5668           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5669           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5670           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5671           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5672             : 
    5673             :         // no default
    5674           1 :         CATCH_REQUIRE(opt.get_option("--") != nullptr);
    5675           1 :         CATCH_REQUIRE(opt.is_defined("--"));
    5676           1 :         CATCH_REQUIRE(opt.get_string("--") == "allowed.txt");
    5677           1 :         CATCH_REQUIRE(opt.get_string("--", 0) == "allowed.txt");
    5678           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    5679           1 :         CATCH_REQUIRE(opt.size("--") == 1);
    5680             : 
    5681             :         // the valid parameter
    5682           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    5683           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    5684           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    5685           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    5686           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    5687             : 
    5688             :         // other parameters
    5689           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5690           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5691             :     CATCH_END_SECTION()
    5692             : 
    5693          18 :     CATCH_START_SECTION("Using a '-' when no default option is allowed.")
    5694           1 :         const advgetopt::option options[] =
    5695             :         {
    5696             :             advgetopt::define_option(
    5697             :                   advgetopt::Name("verbose")
    5698             :                 , advgetopt::ShortName('v')
    5699             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    5700             :                 , advgetopt::Help("print info as we work.")
    5701             :             ),
    5702             :             advgetopt::end_options()
    5703             :         };
    5704             : 
    5705           1 :         advgetopt::options_environment environment_options;
    5706           1 :         environment_options.f_project_name = "unittest";
    5707           1 :         environment_options.f_options = options;
    5708           1 :         environment_options.f_help_header = "Usage: use '-' when no default option was defined.";
    5709             : 
    5710           1 :         char const * cargv[] =
    5711             :         {
    5712             :             "/usr/bin/arguments",
    5713             :             "--verbose",
    5714             :             "-",
    5715             :             "file.txt",
    5716             :             nullptr
    5717             :         };
    5718           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5719           1 :         char ** argv = const_cast<char **>(cargv);
    5720             : 
    5721           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: no default options defined; thus \"-\" is not accepted by this program.");
    5722           2 :         advgetopt::getopt opt(environment_options);
    5723             :         try
    5724             :         {
    5725           1 :             opt.finish_parsing(argc, argv);
    5726           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5727             :         }
    5728           2 :         catch(advgetopt::getopt_exit const & e)
    5729             :         {
    5730           1 :             CATCH_REQUIRE(e.code() == 1);
    5731           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5732             :         }
    5733           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5734             : 
    5735             :         // check that the result is valid
    5736             : 
    5737             :         // an invalid parameter, MUST NOT EXIST
    5738           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5739           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5740           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5741           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5742           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5743             : 
    5744             :         // no default
    5745           1 :         CATCH_REQUIRE(opt.get_option("--") == nullptr);
    5746           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("--"));
    5747           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    5748           1 :         CATCH_REQUIRE(opt.size("--") == 0);
    5749             : 
    5750             :         // the valid parameter
    5751           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    5752           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    5753           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    5754           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    5755           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    5756             : 
    5757             :         // other parameters
    5758           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5759           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5760             :     CATCH_END_SECTION()
    5761             : 
    5762          18 :     CATCH_START_SECTION("Using a '-' when on the command line when only accepted in variables.")
    5763           1 :         const advgetopt::option options[] =
    5764             :         {
    5765             :             advgetopt::define_option(
    5766             :                   advgetopt::Name("verbose")
    5767             :                 , advgetopt::ShortName('v')
    5768             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    5769             :                 , advgetopt::Help("print info as we work.")
    5770             :             ),
    5771             :             advgetopt::define_option(
    5772             :                   advgetopt::Name("--")
    5773             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_DEFAULT_OPTION>())
    5774             :                 , advgetopt::Help("default option.")
    5775             :             ),
    5776             :             advgetopt::end_options()
    5777             :         };
    5778             : 
    5779           1 :         advgetopt::options_environment environment_options;
    5780           1 :         environment_options.f_project_name = "unittest";
    5781           1 :         environment_options.f_options = options;
    5782           1 :         environment_options.f_help_header = "Usage: use '-' when no default option was defined.";
    5783           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    5784             : 
    5785           2 :         snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "- allowed.txt");
    5786             : 
    5787           1 :         char const * cargv[] =
    5788             :         {
    5789             :             "/usr/bin/arguments",
    5790             :             "--verbose",
    5791             :             "-",
    5792             :             "file.txt",
    5793             :             nullptr
    5794             :         };
    5795           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5796           1 :         char ** argv = const_cast<char **>(cargv);
    5797             : 
    5798           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option \"-\" is not supported on the command line.");
    5799           2 :         advgetopt::getopt opt(environment_options);
    5800             :         try
    5801             :         {
    5802           1 :             opt.finish_parsing(argc, argv);
    5803           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5804             :         }
    5805           2 :         catch(advgetopt::getopt_exit const & e)
    5806             :         {
    5807           1 :             CATCH_REQUIRE(e.code() == 1);
    5808           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5809             :         }
    5810           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5811             : 
    5812             :         // check that the result is valid
    5813             : 
    5814             :         // an invalid parameter, MUST NOT EXIST
    5815           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5816           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5817           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5818           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5819           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5820             : 
    5821             :         // no default
    5822           1 :         CATCH_REQUIRE(opt.get_option("--") != nullptr);
    5823           1 :         CATCH_REQUIRE(opt.is_defined("--"));
    5824           1 :         CATCH_REQUIRE(opt.get_string("--") == "allowed.txt");
    5825           1 :         CATCH_REQUIRE(opt.get_string("--", 0) == "allowed.txt");
    5826           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    5827           1 :         CATCH_REQUIRE(opt.size("--") == 1);
    5828             : 
    5829             :         // the valid parameter
    5830           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    5831           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    5832           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    5833           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    5834           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    5835             : 
    5836             :         // other parameters
    5837           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5838           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5839             :     CATCH_END_SECTION()
    5840             : 
    5841          18 :     CATCH_START_SECTION("Using a '-' in the environment variable when only accepted on the command line.")
    5842           1 :         const advgetopt::option options[] =
    5843             :         {
    5844             :             advgetopt::define_option(
    5845             :                   advgetopt::Name("verbose")
    5846             :                 , advgetopt::ShortName('v')
    5847             :                 , advgetopt::Flags(advgetopt::standalone_command_flags())
    5848             :                 , advgetopt::Help("print info as we work.")
    5849             :             ),
    5850             :             advgetopt::define_option(
    5851             :                   advgetopt::Name("--")
    5852             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_DEFAULT_OPTION>())
    5853             :                 , advgetopt::Help("default option.")
    5854             :             ),
    5855             :             advgetopt::end_options()
    5856             :         };
    5857             : 
    5858           1 :         advgetopt::options_environment environment_options;
    5859           1 :         environment_options.f_project_name = "unittest";
    5860           1 :         environment_options.f_options = options;
    5861           1 :         environment_options.f_help_header = "Usage: use '-' when no default option was defined.";
    5862           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    5863             : 
    5864           2 :         snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", " -  file.txt ");
    5865             : 
    5866           1 :         char const * cargv[] =
    5867             :         {
    5868             :             "/usr/bin/arguments",
    5869             :             "--verbose",
    5870             :             "-",
    5871             :             "allowed.txt",
    5872             :             nullptr
    5873             :         };
    5874           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5875           1 :         char ** argv = const_cast<char **>(cargv);
    5876             : 
    5877           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option \"-\" is not supported in the environment variable.");
    5878           2 :         advgetopt::getopt opt(environment_options);
    5879             :         try
    5880             :         {
    5881           1 :             opt.finish_parsing(argc, argv);
    5882           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5883             :         }
    5884           2 :         catch(advgetopt::getopt_exit const & e)
    5885             :         {
    5886           1 :             CATCH_REQUIRE(e.code() == 1);
    5887           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5888             :         }
    5889           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5890             : 
    5891             :         // check that the result is valid
    5892             : 
    5893             :         // an invalid parameter, MUST NOT EXIST
    5894           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5895           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5896           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5897           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5898           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5899             : 
    5900             :         // no default
    5901           1 :         CATCH_REQUIRE(opt.get_option("--") != nullptr);
    5902           1 :         CATCH_REQUIRE(opt.is_defined("--"));
    5903           1 :         CATCH_REQUIRE(opt.get_string("--") == "allowed.txt");
    5904           1 :         CATCH_REQUIRE(opt.get_string("--", 0) == "allowed.txt");
    5905           1 :         CATCH_REQUIRE(opt.get_default("--").empty());
    5906           1 :         CATCH_REQUIRE(opt.size("--") == 1);
    5907             : 
    5908             :         // the valid parameter
    5909           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    5910           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    5911           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    5912           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    5913           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    5914             : 
    5915             :         // other parameters
    5916           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5917           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5918             :     CATCH_END_SECTION()
    5919           9 : }
    5920             : 
    5921             : 
    5922           9 : CATCH_TEST_CASE("invalid_options", "[invalid][getopt][arguments]")
    5923             : {
    5924          14 :     CATCH_START_SECTION("Long option with an equal sign but not name.")
    5925           1 :         const advgetopt::option options[] =
    5926             :         {
    5927             :             advgetopt::define_option(
    5928             :                   advgetopt::Name("size")
    5929             :                 , advgetopt::ShortName('s')
    5930             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    5931             :                 , advgetopt::Help("define the size.")
    5932             :             ),
    5933             :             advgetopt::end_options()
    5934             :         };
    5935             : 
    5936           1 :         advgetopt::options_environment environment_options;
    5937           1 :         environment_options.f_project_name = "unittest";
    5938           1 :         environment_options.f_options = options;
    5939           1 :         environment_options.f_help_header = "Usage: use a long name option without the long name.";
    5940             : 
    5941           1 :         char const * cargv[] =
    5942             :         {
    5943             :             "/usr/bin/arguments",
    5944             :             "--=591",
    5945             :             nullptr
    5946             :         };
    5947           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    5948           1 :         char ** argv = const_cast<char **>(cargv);
    5949             : 
    5950           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: name missing in \"--=591\".");
    5951           2 :         advgetopt::getopt opt(environment_options);
    5952             :         try
    5953             :         {
    5954           1 :             opt.finish_parsing(argc, argv);
    5955           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    5956             :         }
    5957           2 :         catch(advgetopt::getopt_exit const & e)
    5958             :         {
    5959           1 :             CATCH_REQUIRE(e.code() == 1);
    5960           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    5961             :         }
    5962           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    5963             : 
    5964             :         // check that the result is valid
    5965             : 
    5966             :         // an invalid parameter, MUST NOT EXIST
    5967           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    5968           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    5969           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    5970           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    5971           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    5972             : 
    5973             :         // the valid parameter
    5974           1 :         CATCH_REQUIRE(opt.get_option("size") != nullptr);
    5975           1 :         CATCH_REQUIRE(opt.get_option('s') != nullptr);
    5976           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("size"));
    5977           1 :         CATCH_REQUIRE(opt.get_default("size").empty());
    5978           1 :         CATCH_REQUIRE(opt.size("size") == 0);
    5979             : 
    5980             :         // other parameters
    5981           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    5982           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    5983             :     CATCH_END_SECTION()
    5984             : 
    5985          14 :     CATCH_START_SECTION("Unknown long option.")
    5986           1 :         const advgetopt::option options[] =
    5987             :         {
    5988             :             advgetopt::define_option(
    5989             :                   advgetopt::Name("size")
    5990             :                 , advgetopt::ShortName('s')
    5991             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    5992             :                 , advgetopt::Help("define the size.")
    5993             :             ),
    5994             :             advgetopt::end_options()
    5995             :         };
    5996             : 
    5997           1 :         advgetopt::options_environment environment_options;
    5998           1 :         environment_options.f_project_name = "unittest";
    5999           1 :         environment_options.f_options = options;
    6000           1 :         environment_options.f_help_header = "Usage: use an unknown long option.";
    6001             : 
    6002           1 :         char const * cargv[] =
    6003             :         {
    6004             :             "/usr/bin/arguments",
    6005             :             "--unknown=568",
    6006             :             nullptr
    6007             :         };
    6008           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    6009           1 :         char ** argv = const_cast<char **>(cargv);
    6010             : 
    6011           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option \"--unknown\" is not supported.");
    6012           2 :         advgetopt::getopt opt(environment_options);
    6013             :         try
    6014             :         {
    6015           1 :             opt.finish_parsing(argc, argv);
    6016           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    6017             :         }
    6018           2 :         catch(advgetopt::getopt_exit const & e)
    6019             :         {
    6020           1 :             CATCH_REQUIRE(e.code() == 1);
    6021           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    6022             :         }
    6023           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6024             : 
    6025             :         // check that the result is valid
    6026             : 
    6027             :         // an invalid parameter, MUST NOT EXIST
    6028           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    6029           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    6030           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    6031           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    6032           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    6033             : 
    6034             :         // the valid parameter
    6035           1 :         CATCH_REQUIRE(opt.get_option("size") != nullptr);
    6036           1 :         CATCH_REQUIRE(opt.get_option('s') != nullptr);
    6037           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("size"));
    6038           1 :         CATCH_REQUIRE(opt.get_default("size").empty());
    6039           1 :         CATCH_REQUIRE(opt.size("size") == 0);
    6040             : 
    6041             :         // other parameters
    6042           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    6043           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    6044             :     CATCH_END_SECTION()
    6045             : 
    6046          14 :     CATCH_START_SECTION("Long option not available in environment variable.")
    6047           1 :         const advgetopt::option options[] =
    6048             :         {
    6049             :             advgetopt::define_option(
    6050             :                   advgetopt::Name("size")
    6051             :                 , advgetopt::ShortName('s')
    6052             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    6053             :                 , advgetopt::Help("define the size.")
    6054             :             ),
    6055             :             advgetopt::end_options()
    6056             :         };
    6057             : 
    6058           1 :         advgetopt::options_environment environment_options;
    6059           1 :         environment_options.f_project_name = "unittest";
    6060           1 :         environment_options.f_options = options;
    6061           1 :         environment_options.f_help_header = "Usage: use an unknown long option.";
    6062           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    6063             : 
    6064           2 :         snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--size 4551");
    6065             : 
    6066           1 :         char const * cargv[] =
    6067             :         {
    6068             :             "/usr/bin/arguments",
    6069             :             "--size=568",
    6070             :             nullptr
    6071             :         };
    6072           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    6073           1 :         char ** argv = const_cast<char **>(cargv);
    6074             : 
    6075           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option \"--size\" is not supported in the environment variable.");
    6076           2 :         advgetopt::getopt opt(environment_options);
    6077             :         try
    6078             :         {
    6079           1 :             opt.finish_parsing(argc, argv);
    6080           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    6081             :         }
    6082           2 :         catch(advgetopt::getopt_exit const & e)
    6083             :         {
    6084           1 :             CATCH_REQUIRE(e.code() == 1);
    6085           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    6086             :         }
    6087           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6088             : 
    6089             :         // check that the result is valid
    6090             : 
    6091             :         // an invalid parameter, MUST NOT EXIST
    6092           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    6093           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    6094           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    6095           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    6096           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    6097             : 
    6098             :         // the valid parameter
    6099           1 :         CATCH_REQUIRE(opt.get_option("size") != nullptr);
    6100           1 :         CATCH_REQUIRE(opt.get_option('s') != nullptr);
    6101           1 :         CATCH_REQUIRE(opt.is_defined("size"));
    6102           1 :         CATCH_REQUIRE(opt.get_string("size") == "568");
    6103           1 :         CATCH_REQUIRE(opt.get_string("size", 0) == "568");
    6104           1 :         CATCH_REQUIRE(opt.get_long("size") == 568);
    6105           1 :         CATCH_REQUIRE(opt.get_long("size", 0) == 568);
    6106           1 :         CATCH_REQUIRE(opt.get_default("size").empty());
    6107           1 :         CATCH_REQUIRE(opt.size("size") == 1);
    6108             : 
    6109             :         // other parameters
    6110           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    6111           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    6112             :     CATCH_END_SECTION()
    6113             : 
    6114          14 :     CATCH_START_SECTION("Long option not available on command line.")
    6115           1 :         const advgetopt::option options[] =
    6116             :         {
    6117             :             advgetopt::define_option(
    6118             :                   advgetopt::Name("size")
    6119             :                 , advgetopt::ShortName('s')
    6120             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    6121             :                 , advgetopt::Help("define the size.")
    6122             :                 , advgetopt::DefaultValue("331")
    6123             :             ),
    6124             :             advgetopt::end_options()
    6125             :         };
    6126             : 
    6127           1 :         advgetopt::options_environment environment_options;
    6128           1 :         environment_options.f_project_name = "unittest";
    6129           1 :         environment_options.f_options = options;
    6130           1 :         environment_options.f_help_header = "Usage: use an unknown long option.";
    6131           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    6132             : 
    6133           2 :         snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--size 4551");
    6134             : 
    6135           1 :         char const * cargv[] =
    6136             :         {
    6137             :             "/usr/bin/arguments",
    6138             :             "--size=568",
    6139             :             nullptr
    6140             :         };
    6141           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    6142           1 :         char ** argv = const_cast<char **>(cargv);
    6143             : 
    6144           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option \"--size\" is not supported on the command line.");
    6145           2 :         advgetopt::getopt opt(environment_options);
    6146             :         try
    6147             :         {
    6148           1 :             opt.finish_parsing(argc, argv);
    6149           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    6150             :         }
    6151           2 :         catch(advgetopt::getopt_exit const & e)
    6152             :         {
    6153           1 :             CATCH_REQUIRE(e.code() == 1);
    6154           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    6155             :         }
    6156           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6157             : 
    6158             :         // check that the result is valid
    6159             : 
    6160             :         // an invalid parameter, MUST NOT EXIST
    6161           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    6162           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    6163           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    6164           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    6165           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    6166             : 
    6167             :         // the valid parameter
    6168           1 :         CATCH_REQUIRE(opt.get_option("size") != nullptr);
    6169           1 :         CATCH_REQUIRE(opt.get_option('s') != nullptr);
    6170           1 :         CATCH_REQUIRE(opt.is_defined("size"));
    6171           1 :         CATCH_REQUIRE(opt.get_string("size") == "4551");
    6172           1 :         CATCH_REQUIRE(opt.get_string("size", 0) == "4551");
    6173           1 :         CATCH_REQUIRE(opt.get_long("size") == 4551);
    6174           1 :         CATCH_REQUIRE(opt.get_long("size", 0) == 4551);
    6175           1 :         CATCH_REQUIRE(opt.get_default("size") == "331");
    6176           1 :         CATCH_REQUIRE(opt.size("size") == 1);
    6177             : 
    6178             :         // other parameters
    6179           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    6180           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    6181             :     CATCH_END_SECTION()
    6182             : 
    6183          14 :     CATCH_START_SECTION("Unknown short option.")
    6184           1 :         const advgetopt::option options[] =
    6185             :         {
    6186             :             advgetopt::define_option(
    6187             :                   advgetopt::Name("verbose")
    6188             :                 , advgetopt::ShortName('v')
    6189             :                 , advgetopt::Flags(advgetopt::standalone_command_flags<>())
    6190             :                 , advgetopt::Help("tell you about our work here.")
    6191             :             ),
    6192             :             advgetopt::define_option(
    6193             :                   advgetopt::Name("size")
    6194             :                 , advgetopt::ShortName('s')
    6195             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    6196             :                 , advgetopt::Help("define the size.")
    6197             :             ),
    6198             :             advgetopt::end_options()
    6199             :         };
    6200             : 
    6201           1 :         advgetopt::options_environment environment_options;
    6202           1 :         environment_options.f_project_name = "unittest";
    6203           1 :         environment_options.f_options = options;
    6204           1 :         environment_options.f_help_header = "Usage: use an unknown long option.";
    6205             : 
    6206           1 :         char const * cargv[] =
    6207             :         {
    6208             :             "/usr/bin/arguments",
    6209             :             "-vq 568",
    6210             :             nullptr
    6211             :         };
    6212           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    6213           1 :         char ** argv = const_cast<char **>(cargv);
    6214             : 
    6215           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option \"-q\" is not supported.");
    6216           2 :         advgetopt::getopt opt(environment_options);
    6217             :         try
    6218             :         {
    6219           1 :             opt.finish_parsing(argc, argv);
    6220           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    6221             :         }
    6222           2 :         catch(advgetopt::getopt_exit const & e)
    6223             :         {
    6224           1 :             CATCH_REQUIRE(e.code() == 1);
    6225           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    6226             :         }
    6227           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6228             : 
    6229             :         // check that the result is valid
    6230             : 
    6231             :         // an invalid parameter, MUST NOT EXIST
    6232           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    6233           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    6234           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    6235           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    6236           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    6237             : 
    6238             :         // verbose
    6239           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    6240           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    6241           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    6242           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    6243           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    6244           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    6245             : 
    6246             :         // the valid parameter
    6247           1 :         CATCH_REQUIRE(opt.get_option("size") != nullptr);
    6248           1 :         CATCH_REQUIRE(opt.get_option('s') != nullptr);
    6249           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("size"));
    6250           1 :         CATCH_REQUIRE(opt.get_default("size").empty());
    6251           1 :         CATCH_REQUIRE(opt.size("size") == 0);
    6252             : 
    6253             :         // other parameters
    6254           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    6255           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    6256             :     CATCH_END_SECTION()
    6257             : 
    6258          14 :     CATCH_START_SECTION("Short option not available in environment variable.")
    6259           1 :         const advgetopt::option options[] =
    6260             :         {
    6261             :             advgetopt::define_option(
    6262             :                   advgetopt::Name("size")
    6263             :                 , advgetopt::ShortName('s')
    6264             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    6265             :                 , advgetopt::Help("define the size.")
    6266             :             ),
    6267             :             advgetopt::define_option(
    6268             :                   advgetopt::Name("verbose")
    6269             :                 , advgetopt::ShortName('v')
    6270             :                 , advgetopt::Flags(advgetopt::standalone_command_flags<>())
    6271             :                 , advgetopt::Help("tell you about our work here.")
    6272             :             ),
    6273             :             advgetopt::end_options()
    6274             :         };
    6275             : 
    6276           1 :         advgetopt::options_environment environment_options;
    6277           1 :         environment_options.f_project_name = "unittest";
    6278           1 :         environment_options.f_options = options;
    6279           1 :         environment_options.f_help_header = "Usage: use an unknown long option.";
    6280           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    6281             : 
    6282           2 :         snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-s 4551");
    6283             : 
    6284           1 :         char const * cargv[] =
    6285             :         {
    6286             :             "/usr/bin/arguments",
    6287             :             "-sv",
    6288             :             "568",
    6289             :             nullptr
    6290             :         };
    6291           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    6292           1 :         char ** argv = const_cast<char **>(cargv);
    6293             : 
    6294           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option \"-s\" is not supported in the environment variable.");
    6295           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: no default options defined; we do not know what to do of \"4551\"; standalone parameters are not accepted by this program.");
    6296           2 :         advgetopt::getopt opt(environment_options);
    6297             :         try
    6298             :         {
    6299           1 :             opt.finish_parsing(argc, argv);
    6300           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    6301             :         }
    6302           2 :         catch(advgetopt::getopt_exit const & e)
    6303             :         {
    6304           1 :             CATCH_REQUIRE(e.code() == 1);
    6305           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    6306             :         }
    6307           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6308             : 
    6309             :         // check that the result is valid
    6310             : 
    6311             :         // an invalid parameter, MUST NOT EXIST
    6312           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    6313           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    6314           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    6315           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    6316           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    6317             : 
    6318             :         // the valid parameter
    6319           1 :         CATCH_REQUIRE(opt.get_option("size") != nullptr);
    6320           1 :         CATCH_REQUIRE(opt.get_option('s') != nullptr);
    6321           1 :         CATCH_REQUIRE(opt.is_defined("size"));
    6322           1 :         CATCH_REQUIRE(opt.get_string("size") == "568");
    6323           1 :         CATCH_REQUIRE(opt.get_string("size", 0) == "568");
    6324           1 :         CATCH_REQUIRE(opt.get_long("size") == 568);
    6325           1 :         CATCH_REQUIRE(opt.get_long("size", 0) == 568);
    6326           1 :         CATCH_REQUIRE(opt.get_default("size").empty());
    6327           1 :         CATCH_REQUIRE(opt.size("size") == 1);
    6328             : 
    6329             :         // verbose
    6330           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    6331           1 :         CATCH_REQUIRE(opt.get_option('v') != nullptr);
    6332           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    6333           1 :         CATCH_REQUIRE(opt.is_defined("verbose"));
    6334           1 :         CATCH_REQUIRE(opt.get_default("verbose").empty());
    6335           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    6336             : 
    6337             :         // other parameters
    6338           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    6339           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    6340             :     CATCH_END_SECTION()
    6341             : 
    6342          14 :     CATCH_START_SECTION("Long option not available on command line.")
    6343           1 :         const advgetopt::option options[] =
    6344             :         {
    6345             :             advgetopt::define_option(
    6346             :                   advgetopt::Name("size")
    6347             :                 , advgetopt::ShortName('s')
    6348             :                 , advgetopt::Flags(advgetopt::var_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    6349             :                 , advgetopt::Help("define the size.")
    6350             :                 , advgetopt::DefaultValue("331")
    6351             :             ),
    6352             :             advgetopt::define_option(
    6353             :                   advgetopt::Name("verbose")
    6354             :                 , advgetopt::ShortName('v')
    6355             :                 , advgetopt::Flags(advgetopt::standalone_command_flags<>())
    6356             :                 , advgetopt::Help("tell you about our work here.")
    6357             :             ),
    6358             :             advgetopt::end_options()
    6359             :         };
    6360             : 
    6361           1 :         advgetopt::options_environment environment_options;
    6362           1 :         environment_options.f_project_name = "unittest";
    6363           1 :         environment_options.f_options = options;
    6364           1 :         environment_options.f_help_header = "Usage: use an unknown long option.";
    6365           1 :         environment_options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    6366             : 
    6367           2 :         snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-s 4551");
    6368             : 
    6369           1 :         char const * cargv[] =
    6370             :         {
    6371             :             "/usr/bin/arguments",
    6372             :             "-sv 568",
    6373             :             nullptr
    6374             :         };
    6375           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    6376           1 :         char ** argv = const_cast<char **>(cargv);
    6377             : 
    6378           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: option \"-s\" is not supported on the command line.");
    6379             :         //SNAP_CATCH2_NAMESPACE::push_expected_log("error: no default options defined; we do not know what to do of \"4551\"; standalone parameters are not accepted by this program.");
    6380           2 :         advgetopt::getopt opt(environment_options);
    6381             :         try
    6382             :         {
    6383           1 :             opt.finish_parsing(argc, argv);
    6384           0 :             CATCH_REQUIRE(false);   // the library is expected to throw here
    6385             :         }
    6386           2 :         catch(advgetopt::getopt_exit const & e)
    6387             :         {
    6388           1 :             CATCH_REQUIRE(e.code() == 1);
    6389           1 :             CATCH_REQUIRE(e.what() == std::string("getopt_exception: errors were found on your command line, environment variable, or configuration file."));
    6390             :         }
    6391           1 :         SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6392             : 
    6393             :         // check that the result is valid
    6394             : 
    6395             :         // an invalid parameter, MUST NOT EXIST
    6396           1 :         CATCH_REQUIRE(opt.get_option("invalid-parameter") == nullptr);
    6397           1 :         CATCH_REQUIRE(opt.get_option('Z') == nullptr);
    6398           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("invalid-parameter"));
    6399           1 :         CATCH_REQUIRE(opt.get_default("invalid-parameter").empty());
    6400           1 :         CATCH_REQUIRE(opt.size("invalid-parameter") == 0);
    6401             : 
    6402             :         // the valid parameter
    6403           1 :         CATCH_REQUIRE(opt.get_option("size") != nullptr);
    6404           1 :         CATCH_REQUIRE(opt.get_option('s') != nullptr);
    6405           1 :         CATCH_REQUIRE(opt.is_defined("size"));
    6406           1 :         CATCH_REQUIRE(opt.get_string("size") == "4551");
    6407           1 :         CATCH_REQUIRE(opt.get_string("size", 0) == "4551");
    6408           1 :         CATCH_REQUIRE(opt.get_long("size") == 4551);
    6409           1 :         CATCH_REQUIRE(opt.get_long("size", 0) == 4551);
    6410           1 :         CATCH_REQUIRE(opt.get_default("size") == "331");
    6411           1 :         CATCH_REQUIRE(opt.size("size") == 1);
    6412             : 
    6413             :         // other parameters
    6414           1 :         CATCH_REQUIRE(opt.get_program_name() == "arguments");
    6415           1 :         CATCH_REQUIRE(opt.get_program_fullname() == "/usr/bin/arguments");
    6416             :     CATCH_END_SECTION()
    6417          13 : }
    6418             : 
    6419             : 
    6420             : #if 0
    6421             : // TODO: break this out in sections and even multiple tests
    6422             : //       the old version would check a command set of options which is
    6423             : //       not required (doable/useful) with version 2.x
    6424             : //
    6425             : //       also this test used to work but now that I heavily changed
    6426             : //       the configuration file loading process (specifically, added
    6427             : //       the cache), it fails since this test assumed that you can
    6428             : //       load a new copy of the same file over and over again
    6429             : 
    6430             : CATCH_TEST_CASE("invalid_parameters", "[invalid][getopt][arguments]")
    6431             : {
    6432             : 
    6433             :     CATCH_START_SECTION("Check all possible invalid argument")
    6434             : 
    6435             :         // default arguments
    6436             :         //
    6437             :         char const * cargv[] =
    6438             :         {
    6439             :             "tests/unittests/invalid_parameters",
    6440             :             "--ignore-parameters",
    6441             :             nullptr
    6442             :         };
    6443             :         const int argc = sizeof(cargv) / sizeof(cargv[0]) - 1;
    6444             :         char **argv = const_cast<char **>(cargv);
    6445             : 
    6446             :         // no options available
    6447             :         //
    6448             :         const advgetopt::option options_empty_list[] =
    6449             :         {
    6450             :             {
    6451             :                 '\0',
    6452             :                 advgetopt::GETOPT_FLAG_END,
    6453             :                 nullptr,
    6454             :                 nullptr,
    6455             :                 nullptr,
    6456             :                 nullptr
    6457             :             }
    6458             :         };
    6459             : 
    6460             :         advgetopt::options_environment options_empty;
    6461             :         options_empty.f_project_name = "unittest";
    6462             :         options_empty.f_options = options_empty_list;
    6463             :         options_empty.f_help_header = "Usage: try this one and we get a throw (empty list)";
    6464             : 
    6465             :         {
    6466             :             CATCH_REQUIRE_THROWS_AS(std::make_shared<advgetopt::getopt>(options_empty, argc, argv), advgetopt::getopt_logic_error);
    6467             :         }
    6468             : 
    6469             :         // option without a name and "wrong" type
    6470             :         //
    6471             :         const advgetopt::option options_no_name_list[] =
    6472             :         {
    6473             :             {
    6474             :                 '\0',
    6475             :                 advgetopt::GETOPT_FLAG_REQUIRED,
    6476             :                 nullptr,
    6477             :                 "we can have a default though",
    6478             :                 nullptr,
    6479             :                 nullptr
    6480             :             },
    6481             :             {
    6482             :                 '\0',
    6483             :                 advgetopt::GETOPT_FLAG_END,
    6484             :                 nullptr,
    6485             :                 nullptr,
    6486             :                 nullptr,
    6487             :                 nullptr
    6488             :             }
    6489             :         };
    6490             : 
    6491             :         advgetopt::options_environment options_no_name;
    6492             :         options_no_name.f_project_name = "unittest";
    6493             :         options_no_name.f_options = options_no_name_list;
    6494             :         options_no_name.f_help_header = "Usage: try this one and we get a throw (no name)";
    6495             : 
    6496             :         {
    6497             :             CATCH_REQUIRE_THROWS_AS(std::make_shared<advgetopt::getopt>(options_no_name, argc, argv), advgetopt::getopt_logic_error);
    6498             :         }
    6499             : 
    6500             :         // long options must be 2+ characters
    6501             :         //
    6502             :         const advgetopt::option options_2chars_minimum_list[] =
    6503             :         {
    6504             :             {
    6505             :                 '\0',
    6506             :                 advgetopt::GETOPT_FLAG_MULTIPLE,
    6507             :                 "", // cannot be empty string (use nullptr instead)
    6508             :                 nullptr,
    6509             :                 "long option must be 2 characters long at least",
    6510             :                 nullptr
    6511             :             },
    6512             :             {
    6513             :                 '\0',
    6514             :                 advgetopt::GETOPT_FLAG_END,
    6515             :                 nullptr,
    6516             :                 nullptr,
    6517             :                 nullptr,
    6518             :                 nullptr
    6519             :             }
    6520             :         };
    6521             : 
    6522             :         advgetopt::options_environment options_2chars_minimum;
    6523             :         options_2chars_minimum.f_project_name = "unittest";
    6524             :         options_2chars_minimum.f_options = options_2chars_minimum_list;
    6525             :         options_2chars_minimum.f_help_header = "Usage: try this one and we get a throw (2 chars minimum)";
    6526             : 
    6527             :         {
    6528             :             CATCH_REQUIRE_THROWS_AS(std::make_shared<advgetopt::getopt>(options_2chars_minimum, argc, argv), advgetopt::getopt_logic_error);
    6529             :         }
    6530             : 
    6531             :         // long options must be 2+ characters
    6532             :         //
    6533             :         const advgetopt::option options_2chars_minimum2_list[] =
    6534             :         {
    6535             :             {
    6536             :                 '\0',
    6537             :                 advgetopt::GETOPT_FLAG_MULTIPLE,
    6538             :                 "f", // cannot be 1 character
    6539             :                 nullptr,
    6540             :                 "long option must be 2 characters long at least",
    6541             :                 nullptr
    6542             :             },
    6543             :             {
    6544             :                 '\0',
    6545             :                 advgetopt::GETOPT_FLAG_END,
    6546             :                 nullptr,
    6547             :                 nullptr,
    6548             :                 nullptr,
    6549             :                 nullptr
    6550             :             }
    6551             :         };
    6552             : 
    6553             :         advgetopt::options_environment options_2chars_minimum2;
    6554             :         options_2chars_minimum2.f_project_name = "unittest";
    6555             :         options_2chars_minimum2.f_options = options_2chars_minimum2_list;
    6556             :         options_2chars_minimum2.f_help_header = "Usage: try this one and we get a throw (2 chars minimum 2nd)";
    6557             : 
    6558             :         {
    6559             :             CATCH_REQUIRE_THROWS_AS(std::make_shared<advgetopt::getopt>(options_2chars_minimum2, argc, argv), advgetopt::getopt_logic_error);
    6560             :         }
    6561             : 
    6562             :         // same long option defined twice
    6563             :         //
    6564             :         const advgetopt::option options_defined_twice_list[] =
    6565             :         {
    6566             :             {
    6567             :                 '\0',
    6568             :                 advgetopt::GETOPT_FLAG_REQUIRED,
    6569             :                 "filename",
    6570             :                 nullptr,
    6571             :                 "options must be unique",
    6572             :                 nullptr
    6573             :             },
    6574             :             {
    6575             :                 '\0',
    6576             :                 advgetopt::GETOPT_FLAG_REQUIRED,
    6577             :                 "filename", // copy/paste problem maybe?
    6578             :                 nullptr,
    6579             :                 "options must be unique",
    6580             :                 nullptr
    6581             :             },
    6582             :             {
    6583             :                 '\0',
    6584             :                 advgetopt::GETOPT_FLAG_END,
    6585             :                 nullptr,
    6586             :                 nullptr,
    6587             :                 nullptr,
    6588             :                 nullptr
    6589             :             }
    6590             :         };
    6591             : 
    6592             :         advgetopt::options_environment options_defined_twice;
    6593             :         options_defined_twice.f_project_name = "unittest";
    6594             :         options_defined_twice.f_options = options_defined_twice_list;
    6595             :         options_defined_twice.f_help_header = "Usage: try this one and we get a throw (long defined twice)";
    6596             : 
    6597             :         {
    6598             :             CATCH_REQUIRE_THROWS_AS(std::make_shared<advgetopt::getopt>(options_defined_twice, argc, argv), advgetopt::getopt_logic_error);
    6599             :         }
    6600             : 
    6601             :         // same short option defined twice
    6602             :         //
    6603             :         const advgetopt::option options_short_defined_twice_list[] =
    6604             :         {
    6605             :             {
    6606             :                 'f',
    6607             :                 advgetopt::GETOPT_FLAG_REQUIRED,
    6608             :                 "from",
    6609             :                 nullptr,
    6610             :                 "options must be unique",
    6611             :                 nullptr
    6612             :             },
    6613             :             {
    6614             :                 'f',
    6615             :                 advgetopt::GETOPT_FLAG_REQUIRED,
    6616             :                 "to",
    6617             :                 nullptr,
    6618             :                 "options must be unique",
    6619             :                 nullptr
    6620             :             },
    6621             :             {
    6622             :                 '\0',
    6623             :                 advgetopt::GETOPT_FLAG_END,
    6624             :                 nullptr,
    6625             :                 nullptr,
    6626             :                 nullptr,
    6627             :                 nullptr
    6628             :             }
    6629             :         };
    6630             : 
    6631             :         advgetopt::options_environment options_short_defined_twice;
    6632             :         options_short_defined_twice.f_project_name = "unittest";
    6633             :         options_short_defined_twice.f_options = options_short_defined_twice_list;
    6634             :         options_short_defined_twice.f_help_header = "Usage: try this one and we get a throw (short defined twice)";
    6635             :         options_short_defined_twice.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    6636             : 
    6637             :         {
    6638             :             CATCH_REQUIRE_THROWS_AS(std::make_shared<advgetopt::getopt>(options_short_defined_twice, argc, argv), advgetopt::getopt_logic_error);
    6639             :         }
    6640             : 
    6641             :         // 2 default_multiple_argument's in the same list is invalid
    6642             :         //
    6643             :         const advgetopt::option options_two_default_multiple_arguments_list[] =
    6644             :         {
    6645             :             {
    6646             :                 '\0',
    6647             :                 advgetopt::GETOPT_FLAG_MULTIPLE | advgetopt::GETOPT_FLAG_DEFAULT_OPTION,
    6648             :                 "filenames",
    6649             :                 nullptr,
    6650             :                 "other parameters are viewed as filenames",
    6651             :                 nullptr
    6652             :             },
    6653             :             {
    6654             :                 '\0',
    6655             :                 advgetopt::GETOPT_FLAG_MULTIPLE | advgetopt::GETOPT_FLAG_DEFAULT_OPTION,
    6656             :                 "more",
    6657             :                 nullptr,
    6658             :                 "yet other parameters are viewed as \"more\" data--here it breaks, one default max.",
    6659             :                 nullptr
    6660             :             },
    6661             :             {
    6662             :                 '\0',
    6663             :                 advgetopt::GETOPT_FLAG_END,
    6664             :                 nullptr,
    6665             :                 nullptr,
    6666             :                 nullptr,
    6667             :                 nullptr
    6668             :             }
    6669             :         };
    6670             : 
    6671             :         advgetopt::options_environment options_two_default_multiple_arguments;
    6672             :         options_two_default_multiple_arguments.f_project_name = "unittest";
    6673             :         options_two_default_multiple_arguments.f_options = options_two_default_multiple_arguments_list;
    6674             :         options_two_default_multiple_arguments.f_help_header = "Usage: try this one and we get a throw (two defaults by flag, multiple args)";
    6675             : 
    6676             :         {
    6677             :             CATCH_REQUIRE_THROWS_AS(std::make_shared<advgetopt::getopt>(options_two_default_multiple_arguments, argc, argv), advgetopt::getopt_logic_error);
    6678             :         }
    6679             : 
    6680             :         // 2 default_argument's in the same list is invalid
    6681             :         //
    6682             :         const advgetopt::option options_two_default_arguments_list[] =
    6683             :         {
    6684             :             {
    6685             :                 '\0',
    6686             :                 0,
    6687             :                 "--",
    6688             :                 nullptr,
    6689             :                 "one other parameter is viewed as a filename",
    6690             :                 nullptr
    6691             :             },
    6692             :             {
    6693             :                 '\0',
    6694             :                 0,
    6695             :                 "--",
    6696             :                 nullptr,
    6697             :                 "yet other parameter viewed as \"more\" data--here it breaks, one default max.",
    6698             :                 nullptr
    6699             :             },
    6700             :             {
    6701             :                 '\0',
    6702             :                 advgetopt::GETOPT_FLAG_END,
    6703             :                 nullptr,
    6704             :                 nullptr,
    6705             :                 nullptr,
    6706             :                 nullptr
    6707             :             }
    6708             :         };
    6709             : 
    6710             :         advgetopt::options_environment options_two_default_arguments;
    6711             :         options_two_default_arguments.f_project_name = "unittest";
    6712             :         options_two_default_arguments.f_options = options_two_default_arguments_list;
    6713             :         options_two_default_arguments.f_help_header = "Usage: try this one and we get a throw (two default args by name)";
    6714             : 
    6715             :         {
    6716             :             CATCH_REQUIRE_THROWS_AS(std::make_shared<advgetopt::getopt>(options_two_default_arguments, argc, argv), advgetopt::getopt_logic_error);
    6717             :         }
    6718             : 
    6719             :         // mix of default arguments in the same list is invalid
    6720             :         //
    6721             :         const advgetopt::option options_mix_of_default_list[] =
    6722             :         {
    6723             :             {
    6724             :                 '\0',
    6725             :                 advgetopt::GETOPT_FLAG_MULTIPLE,
    6726             :                 "--",
    6727             :                 nullptr,
    6728             :                 "other parameters are viewed as filenames",
    6729             :                 nullptr
    6730             :             },
    6731             :             {
    6732             :                 '\0',
    6733             :                 0,
    6734             :                 "--",
    6735             :                 nullptr,
    6736             :                 "yet other parameter viewed as \"more\" data--here it breaks, one default max.",
    6737             :                 nullptr
    6738             :             },
    6739             :             {
    6740             :                 '\0',
    6741             :                 advgetopt::GETOPT_FLAG_END,
    6742             :                 nullptr,
    6743             :                 nullptr,
    6744             :                 nullptr,
    6745             :                 nullptr
    6746             :             }
    6747             :         };
    6748             : 
    6749             :         advgetopt::options_environment options_mix_of_default;
    6750             :         options_mix_of_default.f_project_name = "unittest";
    6751             :         options_mix_of_default.f_options = options_mix_of_default_list;
    6752             :         options_mix_of_default.f_help_header = "Usage: try this one and we get a throw (mix flags of defaults by name)";
    6753             :         options_mix_of_default.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    6754             : 
    6755             :         {
    6756             :             CATCH_REQUIRE_THROWS_AS(std::make_shared<advgetopt::getopt>(options_mix_of_default, argc, argv), advgetopt::getopt_logic_error);
    6757             :         }
    6758             : 
    6759             :         // try the - and -- without a default in the arguments
    6760             :         //
    6761             :         const advgetopt::option options_no_defaults_list[] =
    6762             :         {
    6763             :             {
    6764             :                 '\0',
    6765             :                 advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_FLAG,
    6766             :                 "verbose",
    6767             :                 nullptr,
    6768             :                 "just a flag to test.",
    6769             :                 0
    6770             :             },
    6771             :             {
    6772             :                 '\0',
    6773             :                 advgetopt::GETOPT_FLAG_END,
    6774             :                 nullptr,
    6775             :                 nullptr,
    6776             :                 nullptr,
    6777             :                 nullptr
    6778             :             }
    6779             :         };
    6780             : 
    6781             :         advgetopt::options_environment options_no_defaults;
    6782             :         options_no_defaults.f_project_name = "unittest";
    6783             :         options_no_defaults.f_options = options_no_defaults_list;
    6784             :         options_no_defaults.f_help_header = "Usage: try this one and we get a throw (no defaults)";
    6785             : 
    6786             :         {
    6787             :             // a filename by itself is a problem when there is no default
    6788             :             //
    6789             :             char const * sub_cargv[] =
    6790             :             {
    6791             :                 "tests/unittests/AdvGetOptUnitTests::invalid_parameters",
    6792             :                 "--verbose",
    6793             :                 "this",
    6794             :                 "filename",
    6795             :                 nullptr
    6796             :             };
    6797             :             const int sub_argc(sizeof(sub_cargv) / sizeof(sub_cargv[0]) - 1);
    6798             :             char ** sub_argv(const_cast<char **>(sub_cargv));
    6799             : 
    6800             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: no default options defined; we do not know what to do of \"this\"; standalone parameters are not accepted by this program.");
    6801             :             advgetopt::getopt opt(options_no_defaults, sub_argc, sub_argv);
    6802             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6803             :         }
    6804             :         {
    6805             :             // a '-' by itself is a problem when there is no default because it
    6806             :             // is expected to represent a filename (stdin)
    6807             :             //
    6808             :             char const * sub_cargv[] =
    6809             :             {
    6810             :                 "tests/unittests/AdvGetOptUnitTests::invalid_parameters",
    6811             :                 "--verbose",
    6812             :                 "-",
    6813             :                 nullptr
    6814             :             };
    6815             :             const int sub_argc(sizeof(sub_cargv) / sizeof(sub_cargv[0]) - 1);
    6816             :             char **sub_argv(const_cast<char **>(sub_cargv));
    6817             : 
    6818             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: no default options defined; thus - is not accepted by this program.");
    6819             :             advgetopt::getopt opt(options_no_defaults, sub_argc, sub_argv);
    6820             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6821             :         }
    6822             :         {
    6823             :             // the -- by itself would be fine, but since it represents a
    6824             :             // transition from arguments to only filenames (or whatever the
    6825             :             // program expects as default options) it generates an error if
    6826             :             // no default options are accepted
    6827             :             //
    6828             :             const char *sub_cargv[] =
    6829             :             {
    6830             :                 "tests/unittests/AdvGetOptUnitTests::invalid_parameters",
    6831             :                 "--verbose",
    6832             :                 "--", // already just by itself it causes problems
    6833             :                 nullptr
    6834             :             };
    6835             :             const int sub_argc = sizeof(sub_cargv) / sizeof(sub_cargv[0]) - 1;
    6836             :             char **sub_argv = const_cast<char **>(sub_cargv);
    6837             : 
    6838             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: no default options defined; thus -- is not accepted by this program.");
    6839             :             advgetopt::getopt opt(options_no_defaults, sub_argc, sub_argv);
    6840             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6841             :         }
    6842             :         {
    6843             :             const char *sub_cargv[] =
    6844             :             {
    6845             :                 "tests/unittests/AdvGetOptUnitTests::invalid_parameters",
    6846             :                 "--verbose",
    6847             :                 "--",
    6848             :                 "66",
    6849             :                 "--filenames",
    6850             :                 "extra",
    6851             :                 "--file",
    6852             :                 "names",
    6853             :                 nullptr
    6854             :             };
    6855             :             const int sub_argc = sizeof(sub_cargv) / sizeof(sub_cargv[0]) - 1;
    6856             :             char **sub_argv = const_cast<char **>(sub_cargv);
    6857             : 
    6858             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: no default options defined; thus -- is not accepted by this program.");
    6859             :             advgetopt::getopt opt(options_no_defaults, sub_argc, sub_argv);
    6860             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6861             :         }
    6862             :         {
    6863             :             // check that -v, that does not exist, generates a usage error
    6864             :             const char *sub_cargv[] =
    6865             :             {
    6866             :                 "tests/unittests/AdvGetOptUnitTests::invalid_parameters",
    6867             :                 "-v",
    6868             :                 nullptr
    6869             :             };
    6870             :             const int sub_argc = sizeof(sub_cargv) / sizeof(sub_cargv[0]) - 1;
    6871             :             char **sub_argv = const_cast<char **>(sub_cargv);
    6872             : 
    6873             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: option -v is not supported.");
    6874             :             advgetopt::getopt opt(options_no_defaults, sub_argc, sub_argv);
    6875             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6876             :         }
    6877             : 
    6878             :         // check -- when default does not allowed environment variables
    6879             :         //
    6880             :         const advgetopt::option options_no_defaults_in_envvar_list[] =
    6881             :         {
    6882             :             {
    6883             :                 '\0',
    6884             :                 advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_ENVIRONMENT_VARIABLE | advgetopt::GETOPT_FLAG_FLAG,
    6885             :                 "verbose",
    6886             :                 nullptr,
    6887             :                 "just a flag to test.",
    6888             :                 nullptr
    6889             :             },
    6890             :             {
    6891             :                 '\0',
    6892             :                 advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_MULTIPLE,
    6893             :                 "--",
    6894             :                 nullptr,
    6895             :                 "default multiple filenames",
    6896             :                 nullptr
    6897             :             },
    6898             :             {
    6899             :                 '\0',
    6900             :                 advgetopt::GETOPT_FLAG_END,
    6901             :                 nullptr,
    6902             :                 nullptr,
    6903             :                 nullptr,
    6904             :                 nullptr
    6905             :             }
    6906             :         };
    6907             : 
    6908             :         advgetopt::options_environment options_no_defaults_in_envvar;
    6909             :         options_no_defaults_in_envvar.f_project_name = "unittest";
    6910             :         options_no_defaults_in_envvar.f_options = options_no_defaults_in_envvar_list;
    6911             :         options_no_defaults_in_envvar.f_help_header = "Usage: try this one and we get a throw (no defaults in envvar)";
    6912             :         options_no_defaults_in_envvar.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    6913             : 
    6914             :         {
    6915             :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--verbose - no default here");
    6916             :             char const * sub_cargv[] =
    6917             :             {
    6918             :                 "tests/unittests/AdvGetOptUnitTests::invalid_parameters",
    6919             :                 "--verbose",
    6920             :                 "-",
    6921             :                 "here",
    6922             :                 "it",
    6923             :                 "works",
    6924             :                 nullptr
    6925             :             };
    6926             :             int const sub_argc = sizeof(sub_cargv) / sizeof(sub_cargv[0]) - 1;
    6927             :             char **sub_argv = const_cast<char **>(sub_cargv);
    6928             : 
    6929             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: option - is not supported in the environment variable.");
    6930             :             advgetopt::getopt opt(options_no_defaults_in_envvar, sub_argc, sub_argv);
    6931             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6932             :         }
    6933             :         {
    6934             :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--verbose no default here");
    6935             :             const char *sub_cargv[] =
    6936             :             {
    6937             :                 "tests/unittests/AdvGetOptUnitTests::invalid_parameters",
    6938             :                 "--verbose",
    6939             :                 "-",
    6940             :                 "here",
    6941             :                 "it",
    6942             :                 "works",
    6943             :                 nullptr
    6944             :             };
    6945             :             const int sub_argc = sizeof(sub_cargv) / sizeof(sub_cargv[0]) - 1;
    6946             :             char **sub_argv = const_cast<char **>(sub_cargv);
    6947             : 
    6948             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: default options are not supported in the environment variable.");
    6949             :             advgetopt::getopt opt(options_no_defaults_in_envvar, sub_argc, sub_argv);
    6950             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6951             :         }
    6952             :         {
    6953             :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--verbose -- foo bar blah");
    6954             :             const char *sub_cargv[] =
    6955             :             {
    6956             :                 "tests/unittests/AdvGetOptUnitTests::invalid_parameters",
    6957             :                 "--verbose",
    6958             :                 "here",
    6959             :                 "it",
    6960             :                 "works",
    6961             :                 "--",
    6962             :                 "66",
    6963             :                 "--filenames",
    6964             :                 "extra",
    6965             :                 "--file",
    6966             :                 "names",
    6967             :                 nullptr
    6968             :             };
    6969             :             const int sub_argc = sizeof(sub_cargv) / sizeof(sub_cargv[0]) - 1;
    6970             :             char **sub_argv = const_cast<char **>(sub_cargv);
    6971             : 
    6972             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: option -- is not supported in the environment variable.");
    6973             :             advgetopt::getopt opt(options_no_defaults_in_envvar, sub_argc, sub_argv);
    6974             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    6975             :         }
    6976             : 
    6977             :         // unnknown long options
    6978             :         //
    6979             :         const advgetopt::option valid_options_unknown_command_line_option_list[] =
    6980             :         {
    6981             :             {
    6982             :                 '\0',
    6983             :                 advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_MULTIPLE,
    6984             :                 "command",
    6985             :                 nullptr,
    6986             :                 "there is a --command, but the user tries --verbose!",
    6987             :                 nullptr
    6988             :             },
    6989             :             {
    6990             :                 '\0',
    6991             :                 advgetopt::GETOPT_FLAG_END,
    6992             :                 nullptr,
    6993             :                 nullptr,
    6994             :                 nullptr,
    6995             :                 nullptr
    6996             :             }
    6997             :         };
    6998             : 
    6999             :         advgetopt::options_environment valid_options_unknown_command_line_option;
    7000             :         valid_options_unknown_command_line_option.f_project_name = "unittest";
    7001             :         valid_options_unknown_command_line_option.f_options = valid_options_unknown_command_line_option_list;
    7002             :         valid_options_unknown_command_line_option.f_help_header = "Usage: try this one and we get a throw (unknown command line option)";
    7003             : 
    7004             :         {
    7005             :             const char *sub_cargv[] =
    7006             :             {
    7007             :                 "tests/unittests/AdvGetOptUnitTests::invalid_parameters",
    7008             :                 "--verbose",
    7009             :                 nullptr
    7010             :             };
    7011             :             const int sub_argc = sizeof(sub_cargv) / sizeof(sub_cargv[0]) - 1;
    7012             :             char **sub_argv = const_cast<char **>(sub_cargv);
    7013             : 
    7014             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --verbose is not supported.");
    7015             :             advgetopt::getopt opt(valid_options_unknown_command_line_option, sub_argc, sub_argv);
    7016             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7017             :         }
    7018             : 
    7019             :         // illegal short or long option in variable
    7020             :         //
    7021             :         const advgetopt::option options_illegal_in_variable_list[] =
    7022             :         {
    7023             :             {
    7024             :                 'v',
    7025             :                 advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_FLAG,
    7026             :                 "verbose",
    7027             :                 nullptr,
    7028             :                 "just a flag to test.",
    7029             :                 nullptr
    7030             :             },
    7031             :             {
    7032             :                 '\0',
    7033             :                 advgetopt::GETOPT_FLAG_END,
    7034             :                 nullptr,
    7035             :                 nullptr,
    7036             :                 nullptr,
    7037             :                 nullptr
    7038             :             }
    7039             :         };
    7040             : 
    7041             :         advgetopt::options_environment options_illegal_in_variable;
    7042             :         options_illegal_in_variable.f_project_name = "unittest";
    7043             :         options_illegal_in_variable.f_options = options_illegal_in_variable_list;
    7044             :         options_illegal_in_variable.f_help_header = "Usage: try this one and we get a throw (illegal in variable)";
    7045             :         options_illegal_in_variable.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    7046             : 
    7047             :         {
    7048             :             // long
    7049             :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "--verbose");
    7050             : 
    7051             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --verbose is not supported in the environment variable.");
    7052             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --ignore-parameters is not supported.");
    7053             :             advgetopt::getopt opt(options_illegal_in_variable, argc, argv);
    7054             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7055             :         }
    7056             :         {
    7057             :             // short
    7058             :             snapdev::safe_setenv env("ADVGETOPT_TEST_OPTIONS", "-v");
    7059             : 
    7060             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: option -v is not supported in the environment variable.");
    7061             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --ignore-parameters is not supported.");
    7062             :             advgetopt::getopt opt(options_illegal_in_variable, argc, argv);
    7063             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7064             :         }
    7065             : 
    7066             :         // configuration file options must have a long name
    7067             :         //
    7068             :         const advgetopt::option configuration_long_name_missing_list[] =
    7069             :         {
    7070             :             {
    7071             :                 'c',
    7072             :                 advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_CONFIGURATION_FILE,
    7073             :                 nullptr,
    7074             :                 nullptr,
    7075             :                 "a valid option",
    7076             :                 nullptr
    7077             :             },
    7078             :             {
    7079             :                 '\0',
    7080             :                 advgetopt::GETOPT_FLAG_END,
    7081             :                 nullptr,
    7082             :                 nullptr,
    7083             :                 nullptr,
    7084             :                 nullptr
    7085             :             }
    7086             :         };
    7087             : 
    7088             :         advgetopt::options_environment configuration_long_name_missing;
    7089             :         configuration_long_name_missing.f_project_name = "unittest";
    7090             :         configuration_long_name_missing.f_options = configuration_long_name_missing_list;
    7091             :         configuration_long_name_missing.f_help_header = "Usage: try this one and we get a throw (long name missing)";
    7092             :         configuration_long_name_missing.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    7093             : 
    7094             :         {
    7095             :             CATCH_REQUIRE_THROWS_AS(std::make_shared<advgetopt::getopt>(configuration_long_name_missing, argc, argv), advgetopt::getopt_logic_error);
    7096             :         }
    7097             : 
    7098             :         // create invalid configuration files
    7099             :         //
    7100             :         const advgetopt::option valid_options_list[] =
    7101             :         {
    7102             :             {
    7103             :                 '\0',
    7104             :                 advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_CONFIGURATION_FILE,
    7105             :                 "valid",
    7106             :                 nullptr,
    7107             :                 "a valid option",
    7108             :                 nullptr
    7109             :             },
    7110             :             {
    7111             :                 '\0',
    7112             :                 advgetopt::GETOPT_FLAG_COMMAND_LINE,
    7113             :                 "command",
    7114             :                 nullptr,
    7115             :                 "a valid command, but not a valid configuration option",
    7116             :                 nullptr
    7117             :             },
    7118             :             {
    7119             :                 '\0',
    7120             :                 advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_MULTIPLE | advgetopt::GETOPT_FLAG_DEFAULT_OPTION,
    7121             :                 "filename",
    7122             :                 nullptr,
    7123             :                 "other parameters are viewed as filenames",
    7124             :                 nullptr
    7125             :             },
    7126             :             {
    7127             :                 '\0',
    7128             :                 advgetopt::GETOPT_FLAG_END,
    7129             :                 nullptr,
    7130             :                 nullptr,
    7131             :                 nullptr,
    7132             :                 nullptr
    7133             :             }
    7134             :         };
    7135             : 
    7136             :         std::string tmpdir(SNAP_CATCH2_NAMESPACE::g_tmp_dir);
    7137             :         tmpdir += "/.config";
    7138             :         std::stringstream ss;
    7139             :         ss << "mkdir -p " << tmpdir;
    7140             :         if(system(ss.str().c_str()) != 0)
    7141             :         {
    7142             :             std::cerr << "fatal error: creating sub-temporary directory \"" << tmpdir << "\" failed.\n";
    7143             :             exit(1);
    7144             :         }
    7145             : 
    7146             :         std::string const config_filename(tmpdir + "/advgetopt.config");
    7147             :         char const * invalid_confs[] =
    7148             :         {
    7149             :             config_filename.c_str(),
    7150             :             nullptr
    7151             :         };
    7152             : 
    7153             :         advgetopt::options_environment valid_options;
    7154             :         valid_options.f_project_name = "unittest";
    7155             :         valid_options.f_options = valid_options_list;
    7156             :         valid_options.f_help_header = "Usage: try this one and we get a throw (valid options!)";
    7157             :         valid_options.f_configuration_files = invalid_confs;
    7158             : 
    7159             :         {
    7160             :             // '=' operator missing
    7161             :             {
    7162             :                 std::ofstream config_file;
    7163             :                 config_file.open(config_filename, std::ios_base::out | std::ios_base::binary | std::ios_base::trunc);
    7164             :                 CATCH_REQUIRE(config_file.good());
    7165             :                 config_file <<
    7166             :                     "# Auto-generated\n"
    7167             :                     "valid param\n"
    7168             :                     "# no spaces acceptable in param names\n"
    7169             :                 ;
    7170             :             }
    7171             :             {
    7172             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option name from \"valid param\" on line 2 in configuration file \""
    7173             :                                         + config_filename
    7174             :                                         + "\" cannot include a space, missing assignment operator?");
    7175             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --ignore-parameters is not supported.");
    7176             :                 advgetopt::getopt opt(valid_options, argc, argv);
    7177             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7178             :             }
    7179             :         }
    7180             :         {
    7181             :             // same effect with a few extra spaces
    7182             :             {
    7183             :                 std::ofstream config_file;
    7184             :                 config_file.open(config_filename, std::ios_base::out | std::ios_base::binary | std::ios_base::trunc);
    7185             :                 CATCH_REQUIRE(config_file.good());
    7186             :                 config_file <<
    7187             :                     "# Auto-generated\n"
    7188             :                     " valid param \n"
    7189             :                     "# no spaces acceptable in param names\n"
    7190             :                 ;
    7191             :             }
    7192             :             {
    7193             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option name from \" valid param \" on line 2 in configuration file \""
    7194             :                                         + config_filename
    7195             :                                         + "\" cannot include a space, missing assignment operator?");
    7196             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --ignore-parameters is not supported.");
    7197             :                 advgetopt::getopt opt(valid_options, argc, argv);
    7198             :                 SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7199             :             }
    7200             :         }
    7201             :         {
    7202             :             // param name missing
    7203             :             {
    7204             :                 std::ofstream config_file;
    7205             :                 config_file.open(config_filename, std::ios_base::out | std::ios_base::binary | std::ios_base::trunc);
    7206             :                 CATCH_REQUIRE(config_file.good());
    7207             :                 config_file <<
    7208             :                     "# Auto-generated\n"
    7209             :                     " = valid param\n"
    7210             :                     "# no spaces acceptable in param names\n"
    7211             :                 ;
    7212             :             }
    7213             :             {
    7214             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: no option name in \" = valid param\" on line 2 from configuration file \""
    7215             :                                         + config_filename
    7216             :                                         + "\", missing name before = sign?");
    7217             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --ignore-parameters is not supported.");
    7218             :                 advgetopt::getopt opt(valid_options, argc, argv);
    7219             :                 SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7220             :             }
    7221             :         }
    7222             :         {
    7223             :             // param name starts with a dash or more
    7224             :             {
    7225             :                 std::ofstream config_file;
    7226             :                 config_file.open(config_filename, std::ios_base::out | std::ios_base::binary | std::ios_base::trunc);
    7227             :                 CATCH_REQUIRE(config_file.good());
    7228             :                 config_file <<
    7229             :                     "# Auto-generated\n"
    7230             :                     "--valid=param\n"
    7231             :                     "# no spaces acceptable in param names\n"
    7232             :                 ;
    7233             :             }
    7234             :             {
    7235             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option names in configuration files cannot start with a dash or an underscore in \"--valid=param\" on line 2 from configuration file \""
    7236             :                                         + config_filename
    7237             :                                         + "\".");
    7238             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --ignore-parameters is not supported.");
    7239             :                 advgetopt::getopt opt(valid_options, argc, argv);
    7240             :                 SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7241             :             }
    7242             :         }
    7243             :         {
    7244             :             // unknown param name
    7245             :             {
    7246             :                 std::ofstream config_file;
    7247             :                 config_file.open(config_filename, std::ios_base::out | std::ios_base::binary | std::ios_base::trunc);
    7248             :                 CATCH_REQUIRE(config_file.good());
    7249             :                 config_file <<
    7250             :                     "# Auto-generated\n"
    7251             :                     "invalid=param\n"
    7252             :                     "# no spaces acceptable in param names\n"
    7253             :                 ;
    7254             :             }
    7255             :             {
    7256             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: unknown option \"invalid\" found in configuration file \""
    7257             :                                         + config_filename
    7258             :                                         + "\".");
    7259             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --ignore-parameters is not supported.");
    7260             :                 advgetopt::getopt opt(valid_options, argc, argv);
    7261             :                 SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7262             :             }
    7263             :         }
    7264             :         {
    7265             :             // known command, not valid in configuration file
    7266             :             {
    7267             :                 std::ofstream config_file;
    7268             :                 config_file.open(config_filename, std::ios_base::out | std::ios_base::binary | std::ios_base::trunc);
    7269             :                 CATCH_REQUIRE(config_file.good());
    7270             :                 config_file <<
    7271             :                     "# Auto-generated\n"
    7272             :                     "command=value\n"
    7273             :                     "# no spaces acceptable in param names\n"
    7274             :                 ;
    7275             :             }
    7276             :             {
    7277             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option \"command\" is not supported in configuration files (found in \""
    7278             :                                         + config_filename
    7279             :                                         + "\").");
    7280             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --ignore-parameters is not supported.");
    7281             :                 advgetopt::getopt opt(valid_options, argc, argv);
    7282             :                 SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7283             :             }
    7284             :         }
    7285             : 
    7286             : #if 0
    7287             :     // in version 2.x we do not have this case anymore
    7288             : 
    7289             :         // one of the options has an invalid mode; explicit option
    7290             :         {
    7291             :             const advgetopt::option options_list[] =
    7292             :             {
    7293             :                 {
    7294             :                     '\0',
    7295             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_SHOW_USAGE_ON_ERROR,
    7296             :                     "mode",
    7297             :                     nullptr,
    7298             :                     "an argument with an invalid mode to see that we get an exception",
    7299             :                     static_cast<advgetopt::getopt::argument_mode_t>(static_cast<int>(advgetopt::getopt::argument_mode_t::end_of_options) + 1)
    7300             :                 },
    7301             :                 {
    7302             :                     '\0',
    7303             :                     advgetopt::GETOPT_FLAG_END,
    7304             :                     nullptr,
    7305             :                     nullptr,
    7306             :                     nullptr,
    7307             :                     nullptr
    7308             :                 }
    7309             :             };
    7310             : 
    7311             :             advgetopt::options_environment options;
    7312             :             options.f_project_name = "unittest";
    7313             :             options.f_options = options_list;
    7314             :             options.f_help_header = "Usage: one of the options has an invalid mode";
    7315             : 
    7316             :             {
    7317             :                 const char *cargv2[] =
    7318             :                 {
    7319             :                     "tests/unittests/unittest_advgetopt",
    7320             :                     "--mode",
    7321             :                     "test",
    7322             :                     nullptr
    7323             :                 };
    7324             :                 const int argc2 = sizeof(cargv2) / sizeof(cargv2[0]) - 1;
    7325             :                 char **argv2 = const_cast<char **>(cargv2);
    7326             : 
    7327             :                 // here we hit the one in add_options() (plural)
    7328             :                 // the one in add_option() is not reachable because it is called only
    7329             :                 // when a default option is defined and that means the mode is
    7330             :                 // correct
    7331             :                 CATCH_REQUIRE_THROWS_AS( { advgetopt::getopt opt(argc2, argv2, options, confs, nullptr); }, advgetopt::getopt_invalid );
    7332             :             }
    7333             :             {
    7334             :                 const char *cargv2[] =
    7335             :                 {
    7336             :                     "tests/unittests/unittest_advgetopt",
    7337             :                     nullptr
    7338             :                 };
    7339             :                 const int argc2 = sizeof(cargv2) / sizeof(cargv2[0]) - 1;
    7340             :                 char **argv2 = const_cast<char **>(cargv2);
    7341             : 
    7342             :                 // this one checks that the --mode flag does indeed generate a
    7343             :                 // throw when not used on the command line but then gets shown
    7344             :                 // in the usage() function
    7345             :                 advgetopt::getopt opt(argc2, argv2, options, confs, nullptr);
    7346             :                 for(int i(static_cast<int>(advgetopt::getopt::status_t::no_error)); i <= static_cast<int>(advgetopt::getopt::status_t::fatal); ++i)
    7347             :                 {
    7348             :                     CATCH_REQUIRE_THROWS_AS( opt.usage(static_cast<advgetopt::getopt::status_t>(i), "test no error, warnings, errors..."), advgetopt::getopt_invalid);
    7349             :                 }
    7350             :             }
    7351             :         }
    7352             : #endif
    7353             : 
    7354             :         // a valid initialization, but not so valid calls afterward
    7355             :         {
    7356             :             advgetopt::option const options_list[] =
    7357             :             {
    7358             :                 {
    7359             :                     '\0',
    7360             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_FLAG,
    7361             :                     "validate",
    7362             :                     nullptr,
    7363             :                     "this is used to validate different things.",
    7364             :                     nullptr
    7365             :                 },
    7366             :                 {
    7367             :                     '\0',
    7368             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7369             :                     "long",
    7370             :                     nullptr,
    7371             :                     "used to validate that invalid numbers generate an error.",
    7372             :                     nullptr
    7373             :                 },
    7374             :                 {
    7375             :                     'o',
    7376             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7377             :                     "out-of-bounds",
    7378             :                     nullptr,
    7379             :                     "valid values from 1 to 9.",
    7380             :                     nullptr
    7381             :                 },
    7382             :                 {
    7383             :                     '\0',
    7384             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7385             :                     "not-specified-and-no-default",
    7386             :                     nullptr,
    7387             :                     "test long without having used the option and no default.",
    7388             :                     nullptr
    7389             :                 },
    7390             :                 {
    7391             :                     '\0',
    7392             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7393             :                     "not-specified-with-invalid-default",
    7394             :                     "123abc",
    7395             :                     "test long with an invalid default value.",
    7396             :                     nullptr
    7397             :                 },
    7398             :                 {
    7399             :                     '\0',
    7400             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7401             :                     "not-specified-string-without-default",
    7402             :                     nullptr,
    7403             :                     "test long with an invalid default value.",
    7404             :                     nullptr
    7405             :                 },
    7406             :                 {
    7407             :                     '\0',
    7408             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7409             :                     "string",
    7410             :                     nullptr,
    7411             :                     "test long with an invalid default value.",
    7412             :                     nullptr
    7413             :                 },
    7414             :                 {
    7415             :                     '\0',
    7416             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_MULTIPLE | advgetopt::GETOPT_FLAG_DEFAULT_OPTION,
    7417             :                     "filename",
    7418             :                     nullptr,
    7419             :                     "other parameters are viewed as filenames",
    7420             :                     nullptr
    7421             :                 },
    7422             :                 {
    7423             :                     '\0',
    7424             :                     advgetopt::GETOPT_FLAG_END,
    7425             :                     nullptr,
    7426             :                     nullptr,
    7427             :                     nullptr,
    7428             :                     nullptr
    7429             :                 }
    7430             :             };
    7431             :             char const * cargv2[] =
    7432             :             {
    7433             :                 "tests/unittests/unittest_advgetopt",
    7434             :                 "--validate",
    7435             :                 "--long",
    7436             :                 "123abc",
    7437             :                 "--out-of-bounds",
    7438             :                 "123",
    7439             :                 "--string",
    7440             :                 "string value",
    7441             :                 nullptr
    7442             :             };
    7443             :             int const argc2 = sizeof(cargv2) / sizeof(cargv2[0]) - 1;
    7444             :             char ** argv2 = const_cast<char **>(cargv2);
    7445             : 
    7446             :             advgetopt::options_environment options;
    7447             :             options.f_project_name = "unittest";
    7448             :             options.f_options = options_list;
    7449             :             options.f_help_header = "Usage: one of the options has an invalid mode";
    7450             :             options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    7451             : 
    7452             :             advgetopt::getopt opt(options, argc2, argv2);
    7453             : 
    7454             :             // cannot get the default without a valid name!
    7455             :             CATCH_REQUIRE_THROWS_AS( opt.get_default(""), advgetopt::getopt_logic_error);
    7456             : 
    7457             :             // cannot get a long named "blah"
    7458             :             CATCH_REQUIRE_THROWS_AS( opt.get_long("blah"), advgetopt::getopt_logic_error);
    7459             :             // existing "long", but only 1 entry
    7460             :             CATCH_REQUIRE_THROWS_AS( opt.get_long("long", 100), advgetopt::getopt_undefined);
    7461             :             long l(-1);
    7462             :             CATCH_REQUIRE_THROWS_AS( l = opt.get_long("not-specified-and-no-default", 0), advgetopt::getopt_logic_error);
    7463             :             CATCH_REQUIRE(l == -1);
    7464             :             CATCH_REQUIRE_THROWS_AS( l = opt.get_long("not-specified-with-invalid-default", 0), advgetopt::getopt_logic_error);
    7465             :             CATCH_REQUIRE(l == -1);
    7466             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: invalid number (123abc) in parameter --long.");
    7467             :             l = opt.get_long("long");
    7468             :             CATCH_REQUIRE(l == -1);
    7469             :             SNAP_CATCH2_NAMESPACE::push_expected_log("error: 123 is out of bounds (1..9 inclusive) in parameter --out-of-bounds.");
    7470             :             l = opt.get_long("out-of-bounds", 0, 1, 9);
    7471             :             CATCH_REQUIRE(l == -1);
    7472             :             std::string s;
    7473             :             CATCH_REQUIRE_THROWS_AS( s = opt.get_string("not-specified-string-without-default", 0), advgetopt::getopt_logic_error);
    7474             :             CATCH_REQUIRE(s.empty());
    7475             :             CATCH_REQUIRE_THROWS_AS( s = opt.get_string("string", 100), advgetopt::getopt_undefined);
    7476             :             CATCH_REQUIRE(s.empty());
    7477             : 
    7478             :             SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7479             : 
    7480             :             // reuse all those invalid options with the reset() function
    7481             :             // and expect the same result
    7482             :             // (the constructor is expected to call reset() the exact same way)
    7483             :             //  -- this changed in version 2.x; we can't reset the option definitions
    7484             :             //
    7485             :             //CATCH_REQUIRE_THROWS_AS( opt.reset(argc, argv, options_empty_list, confs, nullptr), advgetopt::getopt_invalid);
    7486             :             //CATCH_REQUIRE_THROWS_AS( opt.reset(argc, argv, options_no_name_list, confs, nullptr), advgetopt::getopt_invalid);
    7487             :             //CATCH_REQUIRE_THROWS_AS( opt.reset(argc, argv, options_2chars_minimum, confs, nullptr), advgetopt::getopt_invalid);
    7488             :             //CATCH_REQUIRE_THROWS_AS( opt.reset(argc, argv, options_2chars_minimum2, confs, nullptr), advgetopt::getopt_invalid);
    7489             :             //CATCH_REQUIRE_THROWS_AS( opt.reset(argc, argv, options_defined_twice, confs, "ADVGETOPT_TEST_OPTIONS"), advgetopt::getopt_invalid);
    7490             :             //CATCH_REQUIRE_THROWS_AS( opt.reset(argc, argv, options_short_defined_twice, confs, nullptr), advgetopt::getopt_invalid);
    7491             :             //CATCH_REQUIRE_THROWS_AS( opt.reset(argc, argv, options_two_default_multiple_arguments, confs, nullptr), advgetopt::getopt_invalid_default);
    7492             :             //CATCH_REQUIRE_THROWS_AS( opt.reset(argc, argv, options_two_default_arguments, confs, "ADVGETOPT_TEST_OPTIONS"), advgetopt::getopt_invalid_default);
    7493             :             //CATCH_REQUIRE_THROWS_AS( opt.reset(argc, argv, options_mix_of_default, confs, nullptr), advgetopt::getopt_invalid_default);
    7494             :         }
    7495             : 
    7496             :         // valid initialization + usage calls
    7497             :         {
    7498             :             const advgetopt::option options_list[] =
    7499             :             {
    7500             :                 {
    7501             :                     '\0',
    7502             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_FLAG,
    7503             :                     "validate",
    7504             :                     nullptr,
    7505             :                     "this is used to validate different things.",
    7506             :                     nullptr
    7507             :                 },
    7508             :                 {
    7509             :                     '\0',
    7510             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7511             :                     "long",
    7512             :                     nullptr,
    7513             :                     "used to validate that invalid numbers generate an error.",
    7514             :                     nullptr
    7515             :                 },
    7516             :                 {
    7517             :                     'o',
    7518             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7519             :                     "out-of-bounds",
    7520             :                     nullptr,
    7521             :                     "valid values from 1 to 9.",
    7522             :                     nullptr
    7523             :                 },
    7524             :                 {
    7525             :                     '\0',
    7526             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7527             :                     "not-specified-and-no-default",
    7528             :                     nullptr,
    7529             :                     "test long without having used the option and no default.",
    7530             :                     nullptr
    7531             :                 },
    7532             :                 {
    7533             :                     '\0',
    7534             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED | advgetopt::GETOPT_FLAG_MULTIPLE,
    7535             :                     "not-specified-with-invalid-default",
    7536             :                     "123abc",
    7537             :                     "test long with an invalid default value.",
    7538             :                     nullptr
    7539             :                 },
    7540             :                 {
    7541             :                     '\0',
    7542             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7543             :                     "not-specified-string-without-default",
    7544             :                     nullptr,
    7545             :                     "test long with an invalid default value.",
    7546             :                     nullptr
    7547             :                 },
    7548             :                 {
    7549             :                     '\0',
    7550             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7551             :                     "string",
    7552             :                     nullptr,
    7553             :                     "test long with an invalid default value.",
    7554             :                     nullptr
    7555             :                 },
    7556             :                 {
    7557             :                     'u',
    7558             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE,
    7559             :                     "unique",
    7560             :                     nullptr,
    7561             :                     "test long with an invalid default value.",
    7562             :                     nullptr
    7563             :                 },
    7564             :                 {
    7565             :                     'q',
    7566             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_MULTIPLE,
    7567             :                     "quiet",
    7568             :                     nullptr,
    7569             :                     "test long with an invalid default value.",
    7570             :                     nullptr
    7571             :                 },
    7572             :                 {
    7573             :                     '\0',
    7574             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_MULTIPLE | advgetopt::GETOPT_FLAG_DEFAULT_OPTION,
    7575             :                     "filename",
    7576             :                     nullptr,
    7577             :                     "other parameters are viewed as filenames.",
    7578             :                     nullptr
    7579             :                 },
    7580             :                 {
    7581             :                     '\0',
    7582             :                     advgetopt::GETOPT_FLAG_END,
    7583             :                     nullptr,
    7584             :                     nullptr,
    7585             :                     nullptr,
    7586             :                     nullptr
    7587             :                 }
    7588             :             };
    7589             :             char const * cargv2[] =
    7590             :             {
    7591             :                 "tests/unittests/unittest_advgetopt",
    7592             :                 "--validate",
    7593             :                 "--long",
    7594             :                 "123abc",
    7595             :                 "--out-of-bounds",
    7596             :                 "123",
    7597             :                 "--string",
    7598             :                 "string value",
    7599             :                 nullptr
    7600             :             };
    7601             :             int const argc2 = sizeof(cargv2) / sizeof(cargv2[0]) - 1;
    7602             :             char ** argv2 = const_cast<char **>(cargv2);
    7603             : 
    7604             :             advgetopt::options_environment options;
    7605             :             options.f_project_name = "unittest";
    7606             :             options.f_options = options_list;
    7607             :             options.f_help_header = "Usage: try this one and we get a throw (valid options + usage calls)";
    7608             :             options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    7609             : 
    7610             :             // this initialization works as expected
    7611             :             advgetopt::getopt opt(options, argc2, argv2);
    7612             : 
    7613             :             // all of the following have the exiting exception
    7614             :             CATCH_REQUIRE(opt.usage(advgetopt::GETOPT_FLAG_SHOW_ALL) ==
    7615             :     "Usage: try this one and we get a throw (valid options + usage calls)\n"
    7616             :     "   --long <arg>               used to validate that invalid numbers generate an\n"
    7617             :     "                              error.\n"
    7618             :     "   --not-specified-and-no-default <arg>\n"
    7619             :     "                              test long without having used the option and no\n"
    7620             :     "                              default.\n"
    7621             :     "   --not-specified-string-without-default <arg>\n"
    7622             :     "                              test long with an invalid default value.\n"
    7623             :     "   --not-specified-with-invalid-default <arg> {<arg>} (default is \"123abc\")\n"
    7624             :     "                              test long with an invalid default value.\n"
    7625             :     "   --out-of-bounds or -o <arg>\n"
    7626             :     "                              valid values from 1 to 9.\n"
    7627             :     "   --quiet or -q {<arg>}      test long with an invalid default value.\n"
    7628             :     "   --string <arg>             test long with an invalid default value.\n"
    7629             :     "   --unique or -u [<arg>]     test long with an invalid default value.\n"
    7630             :     "   --validate                 this is used to validate different things.\n"
    7631             :     "   [default arguments]        other parameters are viewed as filenames.\n"
    7632             :                             );
    7633             :         }
    7634             : 
    7635             :         // valid initialization + usage calls with a few different options
    7636             :         {
    7637             :             const advgetopt::option options_list[] =
    7638             :             {
    7639             :                 {
    7640             :                     '\0',
    7641             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_FLAG,
    7642             :                     "validate",
    7643             :                     nullptr,
    7644             :                     "this is used to validate different things.",
    7645             :                     nullptr
    7646             :                 },
    7647             :                 {
    7648             :                     '\0',
    7649             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7650             :                     "long",
    7651             :                     nullptr,
    7652             :                     "used to validate that invalid numbers generate an error.",
    7653             :                     nullptr
    7654             :                 },
    7655             :                 {
    7656             :                     'o',
    7657             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7658             :                     "out-of-bounds",
    7659             :                     nullptr,
    7660             :                     "valid values from 1 to 9.",
    7661             :                     nullptr
    7662             :                 },
    7663             :                 {
    7664             :                     '\0',
    7665             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7666             :                     "not-specified-and-no-default",
    7667             :                     nullptr,
    7668             :                     "test long without having used the option and no default.",
    7669             :                     nullptr
    7670             :                 },
    7671             :                 {
    7672             :                     '\0',
    7673             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED | advgetopt::GETOPT_FLAG_MULTIPLE,
    7674             :                     "not-specified-with-invalid-default",
    7675             :                     "123abc",
    7676             :                     "test long with an invalid default value.",
    7677             :                     nullptr
    7678             :                 },
    7679             :                 {
    7680             :                     '\0',
    7681             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7682             :                     "not-specified-string-without-default",
    7683             :                     nullptr,
    7684             :                     "test long with an invalid default value.",
    7685             :                     nullptr
    7686             :                 },
    7687             :                 {
    7688             :                     '\0',
    7689             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7690             :                     "string",
    7691             :                     nullptr,
    7692             :                     "test long with an invalid default value.",
    7693             :                     nullptr
    7694             :                 },
    7695             :                 {
    7696             :                     'u',
    7697             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE,
    7698             :                     "unique",
    7699             :                     nullptr,
    7700             :                     "test long with an invalid default value.",
    7701             :                     nullptr
    7702             :                 },
    7703             :                 {
    7704             :                     'q',
    7705             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_MULTIPLE,
    7706             :                     "quiet",
    7707             :                     nullptr,
    7708             :                     "test long with an invalid default value.",
    7709             :                     nullptr
    7710             :                 },
    7711             :                 {
    7712             :                     'l',
    7713             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED,
    7714             :                     "not-in-v2-though",
    7715             :                     nullptr,
    7716             :                     "long with just a letter.",
    7717             :                     nullptr
    7718             :                 },
    7719             :                 {
    7720             :                     '\0',
    7721             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE,
    7722             :                     "--",
    7723             :                     nullptr,
    7724             :                     "other parameters are viewed as filenames; and we need at least one option with a very long help to check that it wraps perfectly (we'd really need to get the output of the command and check that against what is expected because at this time the test is rather blind in that respect! FIXED IN v2!)",
    7725             :                     nullptr
    7726             :                 },
    7727             :                 {
    7728             :                     '\0',
    7729             :                     advgetopt::GETOPT_FLAG_END,
    7730             :                     nullptr,
    7731             :                     nullptr,
    7732             :                     nullptr,
    7733             :                     nullptr
    7734             :                 }
    7735             :             };
    7736             : 
    7737             :             advgetopt::options_environment options;
    7738             :             options.f_project_name = "unittest";
    7739             :             options.f_options = options_list;
    7740             :             options.f_help_header = "Usage: try this one and we get a throw (valid options + usage calls bis)";
    7741             :             options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    7742             : 
    7743             :             {
    7744             :                 // make sure that --long (REQUIRED) fails if the
    7745             :                 // long value is not specified
    7746             :                 //
    7747             :                 char const * cargv2[] =
    7748             :                 {
    7749             :                     "tests/unittests/unittest_advgetopt",
    7750             :                     "--validate",
    7751             :                     "--long",
    7752             :                     "--out-of-bounds",
    7753             :                     "123",
    7754             :                     "--string",
    7755             :                     "string value",
    7756             :                     nullptr
    7757             :                 };
    7758             :                 int const argc2 = sizeof(cargv2) / sizeof(cargv2[0]) - 1;
    7759             :                 char ** argv2 = const_cast<char **>(cargv2);
    7760             : 
    7761             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --long expects an argument.");
    7762             :                 advgetopt::getopt opt(options, argc2, argv2);
    7763             :                 SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7764             :             }
    7765             :             {
    7766             :                 // again with the lone -l (no long name)
    7767             :                 //
    7768             :                 char const * cargv2[] =
    7769             :                 {
    7770             :                     "tests/unittests/unittest_advgetopt",
    7771             :                     "--validate",
    7772             :                     "-l",
    7773             :                     "--out-of-bounds",
    7774             :                     "123",
    7775             :                     "--string",
    7776             :                     "string value",
    7777             :                     nullptr
    7778             :                 };
    7779             :                 int const argc2 = sizeof(cargv2) / sizeof(cargv2[0]) - 1;
    7780             :                 char ** argv2 = const_cast<char **>(cargv2);
    7781             : 
    7782             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --not-in-v2-though expects an argument.");
    7783             :                 advgetopt::getopt opt(options, argc2, argv2);
    7784             :                 SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7785             :             }
    7786             :             {
    7787             :                 char const * cargv2[] =
    7788             :                 {
    7789             :                     "tests/unittests/unittest_advgetopt",
    7790             :                     "--validate",
    7791             :                     "--long",
    7792             :                     "123abc",
    7793             :                     "--out-of-bounds",
    7794             :                     "123",
    7795             :                     "--string",
    7796             :                     "string value",
    7797             :                     nullptr
    7798             :                 };
    7799             :                 int const argc2 = sizeof(cargv2) / sizeof(cargv2[0]) - 1;
    7800             :                 char ** argv2 = const_cast<char **>(cargv2);
    7801             : 
    7802             :                 // this initialization works as expected
    7803             :                 advgetopt::getopt opt(options, argc2, argv2);
    7804             : 
    7805             :                 // all of the following have the exiting exception
    7806             :     //            for(int i(static_cast<int>(advgetopt::getopt::status_t::no_error)); i <= static_cast<int>(advgetopt::getopt::status_t::fatal); ++i)
    7807             :     //            {
    7808             :     //                CATCH_REQUIRE_THROWS_AS( opt.usage(static_cast<advgetopt::getopt::status_t>(i), "test no error, warnings, errors..."), advgetopt::getopt_exit);
    7809             :     //            }
    7810             :                 CATCH_REQUIRE(opt.usage(advgetopt::GETOPT_FLAG_SHOW_ALL) ==
    7811             :     "Usage: try this one and we get a throw (valid options + usage calls bis)\n"
    7812             :     "   --long <arg>               used to validate that invalid numbers generate an\n"
    7813             :     "                              error.\n"
    7814             :     "   --not-in-v2-though or -l <arg>\n"
    7815             :     "                              long with just a letter.\n"
    7816             :     "   --not-specified-and-no-default <arg>\n"
    7817             :     "                              test long without having used the option and no\n"
    7818             :     "                              default.\n"
    7819             :     "   --not-specified-string-without-default <arg>\n"
    7820             :     "                              test long with an invalid default value.\n"
    7821             :     "   --not-specified-with-invalid-default <arg> {<arg>} (default is \"123abc\")\n"
    7822             :     "                              test long with an invalid default value.\n"
    7823             :     "   --out-of-bounds or -o <arg>\n"
    7824             :     "                              valid values from 1 to 9.\n"
    7825             :     "   --quiet or -q {<arg>}      test long with an invalid default value.\n"
    7826             :     "   --string <arg>             test long with an invalid default value.\n"
    7827             :     "   --unique or -u [<arg>]     test long with an invalid default value.\n"
    7828             :     "   --validate                 this is used to validate different things.\n"
    7829             :     "   [default argument]         other parameters are viewed as filenames; and we\n"
    7830             :     "                              need at least one option with a very long help to\n"
    7831             :     "                              check that it wraps perfectly (we'd really need to\n"
    7832             :     "                              get the output of the command and check that\n"
    7833             :     "                              against what is expected because at this time the\n"
    7834             :     "                              test is rather blind in that respect! FIXED IN\n"
    7835             :     "                              v2!)\n"
    7836             :                             );
    7837             :             }
    7838             :         }
    7839             : 
    7840             :         // strange entry without a name
    7841             :         {
    7842             :             advgetopt::option const options_list[] =
    7843             :             {
    7844             :                 {
    7845             :                     '\0',
    7846             :                     advgetopt::GETOPT_FLAG_SHOW_USAGE_ON_ERROR | advgetopt::GETOPT_FLAG_FLAG,
    7847             :                     nullptr,
    7848             :                     nullptr,
    7849             :                     "this entry has help, but no valid name...",
    7850             :                     nullptr
    7851             :                 },
    7852             :                 {
    7853             :                     'v',
    7854             :                     advgetopt::GETOPT_FLAG_FLAG,
    7855             :                     "verbose",
    7856             :                     nullptr,
    7857             :                     "show more stuff when found on the command line.",
    7858             :                     nullptr
    7859             :                 },
    7860             :                 {
    7861             :                     '\0',
    7862             :                     advgetopt::GETOPT_FLAG_END,
    7863             :                     nullptr,
    7864             :                     nullptr,
    7865             :                     nullptr,
    7866             :                     nullptr
    7867             :                 }
    7868             :             };
    7869             : 
    7870             :             advgetopt::options_environment options;
    7871             :             options.f_project_name = "unittest";
    7872             :             options.f_options = options_list;
    7873             :             options.f_help_header = "Usage: try this one and we get a throw (strange empty entry!)";
    7874             :             options.f_environment_variable_name = "ADVGETOPT_TEST_OPTIONS";
    7875             : 
    7876             :             {
    7877             :                 char const * cargv2[] =
    7878             :                 {
    7879             :                     "tests/unittests/unittest_advgetopt/AdvGetOptUnitTests::invalid_parameters/test-with-an-empty-entry",
    7880             :                     nullptr
    7881             :                 };
    7882             :                 int const argc2 = sizeof(cargv2) / sizeof(cargv2[0]) - 1;
    7883             :                 char ** argv2 = const_cast<char **>(cargv2);
    7884             : 
    7885             :                 // this initialization works as expected
    7886             :                 //
    7887             :                 CATCH_REQUIRE_THROWS_AS(std::make_shared<advgetopt::getopt>(options, argc2, argv2), advgetopt::getopt_logic_error );
    7888             : 
    7889             :     //            // all of the following have the exiting exception
    7890             :     //            for(int i(static_cast<int>(advgetopt::getopt::status_t::no_error)); i <= static_cast<int>(advgetopt::getopt::status_t::fatal); ++i)
    7891             :     //            {
    7892             :     //                CATCH_REQUIRE_THROWS_AS( opt.usage(static_cast<advgetopt::getopt::status_t>(i), "test no error, warnings, errors..."), advgetopt::getopt_invalid);
    7893             :     //            }
    7894             :     //std::cout << "test usage output here? " << opt.usage(advgetopt::GETOPT_FLAG_SHOW_ALL) << "\n";
    7895             :             }
    7896             :         }
    7897             : 
    7898             :         // required multiple without arguments
    7899             :         {
    7900             :             advgetopt::option const options_list[] =
    7901             :             {
    7902             :                 {
    7903             :                     'f',
    7904             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED | advgetopt::GETOPT_FLAG_MULTIPLE | advgetopt::GETOPT_FLAG_DEFAULT_OPTION,
    7905             :                     "filenames",
    7906             :                     nullptr,
    7907             :                     "test a required multiple without any arguments and fail.",
    7908             :                     nullptr
    7909             :                 },
    7910             :                 {
    7911             :                     '\0',
    7912             :                     advgetopt::GETOPT_FLAG_END,
    7913             :                     nullptr,
    7914             :                     nullptr,
    7915             :                     nullptr,
    7916             :                     nullptr
    7917             :                 }
    7918             :             };
    7919             : 
    7920             :             advgetopt::options_environment options;
    7921             :             options.f_project_name = "unittest";
    7922             :             options.f_options = options_list;
    7923             :             options.f_help_header = "Usage: try this one and we get a throw (required multiple without args)";
    7924             : 
    7925             :             {
    7926             :                 // first with -f
    7927             :                 char const * cargv2[] =
    7928             :                 {
    7929             :                     "tests/unittests/unittest_advgetopt/AdvGetOptUnitTests::invalid_parameters/test-with-an-empty-entry",
    7930             :                     "-f",
    7931             :                     nullptr
    7932             :                 };
    7933             :                 int const argc2 = sizeof(cargv2) / sizeof(cargv2[0]) - 1;
    7934             :                 char ** argv2 = const_cast<char **>(cargv2);
    7935             : 
    7936             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --filenames expects an argument.");
    7937             :                 advgetopt::getopt opt(options, argc2, argv2);
    7938             :                 SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7939             :             }
    7940             :             {
    7941             :                 // second with --filenames
    7942             :                 const char *cargv2[] =
    7943             :                 {
    7944             :                     "tests/unittests/unittest_advgetopt/AdvGetOptUnitTests::invalid_parameters/test-with-an-empty-entry",
    7945             :                     "--filenames",
    7946             :                     nullptr
    7947             :                 };
    7948             :                 int const argc2 = sizeof(cargv2) / sizeof(cargv2[0]) - 1;
    7949             :                 char ** argv2 = const_cast<char **>(cargv2);
    7950             : 
    7951             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --filenames expects an argument.");
    7952             :                 advgetopt::getopt opt(options, argc2, argv2);
    7953             :                 SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7954             :             }
    7955             :         }
    7956             : 
    7957             :         // required multiple without arguments, short name only
    7958             :         {
    7959             :             advgetopt::option const options_list[] =
    7960             :             {
    7961             :                 {
    7962             :                     'f',
    7963             :                     advgetopt::GETOPT_FLAG_COMMAND_LINE | advgetopt::GETOPT_FLAG_REQUIRED | advgetopt::GETOPT_FLAG_MULTIPLE,
    7964             :                     "filenames",
    7965             :                     nullptr,
    7966             :                     "test a required multiple without any arguments and fail.",
    7967             :                     nullptr
    7968             :                 },
    7969             :                 {
    7970             :                     '\0',
    7971             :                     advgetopt::GETOPT_FLAG_END,
    7972             :                     nullptr,
    7973             :                     nullptr,
    7974             :                     nullptr,
    7975             :                     nullptr
    7976             :                 }
    7977             :             };
    7978             : 
    7979             :             advgetopt::options_environment options;
    7980             :             options.f_project_name = "unittest";
    7981             :             options.f_options = options_list;
    7982             :             options.f_help_header = "Usage: try this one and we get a throw (required multiple without args + short name)";
    7983             : 
    7984             :             {
    7985             :                 // -f only in this case
    7986             :                 char const * cargv2[] =
    7987             :                 {
    7988             :                     "tests/unittests/unittest_advgetopt/AdvGetOptUnitTests::invalid_parameters/test-with-an-empty-entry",
    7989             :                     "-f",
    7990             :                     nullptr
    7991             :                 };
    7992             :                 int const argc2 = sizeof(cargv2) / sizeof(cargv2[0]) - 1;
    7993             :                 char ** argv2 = const_cast<char **>(cargv2);
    7994             : 
    7995             :                 SNAP_CATCH2_NAMESPACE::push_expected_log("error: option --filenames expects an argument.");
    7996             :                 advgetopt::getopt opt(options, argc2, argv2);
    7997             :                 SNAP_CATCH2_NAMESPACE::expected_logs_stack_is_empty();
    7998             :             }
    7999             :         }
    8000             :     CATCH_END_SECTION()
    8001             : }
    8002             : #endif
    8003             : 
    8004             : 
    8005             : // vim: ts=4 sw=4 et

Generated by: LCOV version 1.13